Kotlin Android Button.onClickListener вызывает NoSuchMethodError

Я думаю, что я нашел причуду для использования kotlin для android, или есть некоторый пробел в моем понимании синтаксиса.

Попытка установить onClickListener для кнопки бросает NoSuchMethodError

Вот код, который виноват

 button.setOnClickListener(Button.OnClickListener { fun onClick(view: View){ val intent : Intent = Intent(this,DetailActivity::class.java) if(obj is String) { intent.putExtra("Topic", obj) } startActivity(intent) } }) 

И вот выведенная стек

  java.lang.NoSuchMethodError: No static method OnClickListener(Lkotlin/jvm/functions/Function1;)Landroid/view/View$OnClickListener; in class Landroid/widget/Button; or its super classes (declaration of 'android.widget.Button' appears in /system/framework/framework.jar:classes2.dex) 

Кто-нибудь знает что?

Solutions Collecting From Web of "Kotlin Android Button.onClickListener вызывает NoSuchMethodError"

Интересно, что я не получаю эту ошибку, ваш код компилируется для меня. Однако это не будет работать по другой причине: вы передаете лямбду в качестве слушателя внутри {} , а это значит, что его содержимое будет выполнено, когда произойдет событие щелчка. Внутри него нет кода, хотя вы просто определяете локальную функцию с именем onClick , которая никогда не будет вызвана.

 button.setOnClickListener(Button.OnClickListener { fun onClick(view: View){ ... } Log.d("TAG", "hi") // this is the code that would be executed on click events }) 

Есть два способа исправить ваш синтаксис:

Во-первых, вы можете использовать выражение object для создания слушателя, это довольно близко к тому, что вы написали, и находится в соответствии с классическим решением Java, оно явно создает анонимный класс (обратите внимание, что интерфейс OnClickListener фактически находится в View класс):

 button.setOnClickListener(object: View.OnClickListener { override fun onClick(v: View?) { val intent = ... } }) 

Или вы можете использовать более короткий, более похожий на Kotlin синтаксис, который IDE предложит при попытке использовать предыдущую длинную форму в любом случае, используя преобразование SAM :

 button.setOnClickListener { val intent = ... } 

Это решение использует лямбда так же, как и ваш исходный код, но просто не указывает, какой интерфейс он преобразует в явном виде, и отбрасывает () которого не требуется один параметр лямбда.

пытаться

 button.setOnClickListener { // Handler code here }