DataBinding容许您编写表达式去处理从View分发的工作。例如onClick()方法。工作特色称谓由监听器方法的称谓确认,但有少数破例。例如,View.OnClickListener有一个方法onClick(),因此此工作绑定的特色为android:onClick。

有一些专门的点击工作处理者(注:它们也接受View.OnClickListener参数)需求运用android:onClick以外的特色来防止抵触。您可以运用以下特色来防止这些类型的抵触:

Class Listener setter Attribute
SearchView setOnSearchClickListener(View.OnClickListener) android:onSearchClick
ZoomControls setOnZoomInClickListener(View.OnClickListener) android:onZoomIn
ZoomControls setOnZoomOutClickListener(View.OnClickListener) android:onZoomOut

您可以运用以下机制来处理工作:

  • 方法引用:在表达式中,可以引用契合监听器方法签名的方法。当表达式核算为方法引用时,DataBinding将方法引用和一切者方针封装到一个监听听器中,并设置到该View上。假设表达式的核算结果为null,则DataBinding不会创建监听器,该View这个特色的监听器为null。

  • 监听器绑定:这些是在工作发生时核算的lambda表达式。DataBinding总是创建一个监听器,并设置到这个View。当工作被分发时,监听器将核算lambda表达式。

1. 方法引用

工作可以直接绑定到处理方法上,类似于android:onClick可以分发到Activity中的方法。与View的onClick特色比较,一个首要优点是表达式在编译时处理,因此,假设该方法不存在或其签名不正确,则会收到编译时错误。
方法引用和监听器绑定之间的首要差异在于,实践的监听器完成是在绑定数据时创建的,而不是在触发工作时创建的。假设期望在工作发生时对表达式求值,则应运用监听器绑定。
若要将工作分配给其处理程序,请运用普通绑定表达式,该值为要调用的方法名。例如,考虑以下布局数据方针示例:

class MyHandlers {
    fun onClickFriend(view: View) { ... }
}

绑定表达式可以将视图的单击监听器分发给onClickFriend()方法,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">
   <data>
       <variable name="handlers" type="com.example.MyHandlers"/>
       <variable name="user" type="com.example.User"/>
   </data>
   <LinearLayout
       android:orientation="vertical"
       android:layout_width="match_parent"
       android:layout_height="match_parent">
       <TextView android:layout_width="wrap_content"
           android:layout_height="wrap_content"
           android:text="@{user.firstName}"
           android:onClick="@{handlers::onClickFriend}"/>
   </LinearLayout>
</layout>

注释:这里表达式里是直接引用的函数。这个函数的签名要和onClickListener的onClick的签名相同

2. 监听者绑定

监听者绑定是在工作发生时工作的绑定表达式。它们类似于方法引用,但容许您工作恣意的数据绑定表达式。此功用可与Gradle 2.0及更高版别的Android Gradle插件一同运用。
在方法引用中,方法的参数有必要与工作监听者的参数匹配。在监听者绑定中,只要回来值有必要与监听者的预期回来值匹配(除非它预期为void)即可。例如,考虑以下具有onSaveClick() 方法示例:

class Presenter {
    fun onSaveClick(task: Task){}
}

然后,您可以将click工作绑定到onSaveClick() 方法,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">
    <data>
        <variable name="task" type="com.android.example.Task" />
        <variable name="presenter" type="com.android.example.Presenter" />
    </data>
    <LinearLayout android:layout_width="match_parent" android:layout_height="match_parent">
        <Button android:layout_width="wrap_content" android:layout_height="wrap_content"
        android:onClick="@{() -> presenter.onSaveClick(task)}" />
    </LinearLayout>
</layout>

在表达式中运用回调时,DataBinding会自动创建必要的监听者并为工作注册它。当视图激起工作时,DataBinding将核算给定的表达式。与正则绑定表达式相同,在评估这些监听者表达式时,您依然可以获得DataBinding的空安全线程安全性。
在上面的例子中,咱们还没有界说传递给onClick(view)的视图参数。监听者绑定为监听者参数提供了两种挑选:可以忽略方法的一切参数,也可以命名一切参数。假设您喜欢命名参数,可以在表达式中运用它们。例如,上面的表达式可以写如下:

android:onClick="@{(view) -> presenter.onSaveClick(task)}"

或许,假设您想在表达式中运用参数,它可以按如下方法作业:

class Presenter {
    fun onSaveClick(view: View, task: Task){}
}
android:onClick="@{(theView) -> presenter.onSaveClick(theView, task)}"

可以将lambda表达式与多个参数一同运用:

class Presenter {
    fun onCompletedChanged(task: Task, completed: Boolean){}
}
<CheckBox android:layout_width="wrap_content" android:layout_height="wrap_content"
      android:onCheckedChanged="@{(cb, isChecked) -> presenter.completeChanged(task, isChecked)}" />

假设正在监听的工作回来的值的类型不是void,则表达式也有必要回来相同类型的值。例如,假设要监听长按工作,则表达式应回来布尔值。

class Presenter {
    fun onLongClick(view: View, task: Task): Boolean { }
}
android:onLongClick="@{(theView) -> presenter.onLongClick(theView, task)}"

假设因为null方针而无法核算表达式,则数据绑定将回来该类型的默认值。例如,引用类型回来null,int回来0,boolean回来false等。
假设需求将表达式与谓词一同运用(例如,三元),可以运用void作为一个符号值。

android:onClick="@{(v) -> v.isVisible() ? doSomething() : void}"

3. 防止凌乱的监听者

监听者表达式非常健壮,可以使代码非常易于阅览。另一方面,包括凌乱表达式的监听者会使布局难以阅览和维护。这些表达式应该像将可用数据从UI传递到回调方法相同简单。您应该在监听者表达式调用的回调方法中完成任何事务逻辑。(注:事务逻辑都写到ViewModel的一个入口函数,databing绑定那个函数即可)

重视公众号:Android老皮!!!欢迎大家来找我评论交流