I'm working on an android project in kotlin and while trying to add an OnTouchListener
to several buttons, I have run into a problem: it cannot be done from XML and I want to keep my backing code clean. After a bit of research, I found out that I could add the XML support by using a method with the @BindingAdapter
annotation:
@BindingAdapter("onTouch")
fun Button.setXMLTouchListener(listener : View.OnTouchListener)
{
this.setOnTouchListener(listener);
}
to this method:
class MainActivity : AppCompatActivity()
{
...
...
fun goLeft(v : View, event : MotionEvent) : Boolean
{
// my code
}
}
and in the XML:
<layout
...>
<data>
<variable name="main_activity" type="my.path.to.MainActivity" />
</data>
<androidx.constraintLayout.widget.ConstraintLayout
...>
<Button
...
app:onTouch="@{main_activity.goLeft}" />
...
</androidx.constraintLayout.widget.ConstraintLayout>
</layout>
and enabled data binding in the build.gradle:
apply plugin: 'kotlin.kapt'
and
android {
...
dataBinding {
enabled = true
}
}
This obviously didn't work, these are the solutions I have tried:
After a bit of debugging, I also found out that the binding function doesn't run at all.
What could be the problem, and how can I solve it?
first write your data binding adapter like this.
@BindingAdapter("app:onTouch")
fun setXMLTouchListener(btn : Button , listener : View.OnTouchListener)
{
btn.setOnTouchListener(listener)
}
then chenge the goLeft()
fun to it
val goLeftListener = View.OnTouchListener { v, event ->
Log.d("goLeftListener " , "it Worked !")
return@goLeftListener true
}
and don't forget to set activity on your binding object in onCreate fun
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val binding: mainActivityBinding =
DataBindingUtil.setContentView(this, R.layout.main_activity)
binding.main_activity = this
}
and for the last step write onTouch attribute of Button in your xml layout like this
<Button
.
.
app:onTouch="@{main_activity.goLeftListener}"
.
/>