因为最近写了了MVVM框架的使用,有兴趣的朋友看看这里谈谈Android框架 MVC、MVP、MVVM的区,用到了DataBinding,所以今天写写它的介绍。

一、什么是DataBinding以及它的发展历程

DataBinding是一个用来解决界面逻辑的Android数据绑定框架,由去年谷歌 I/O大会上随同MVVM框架一同推出。

android databinding 不能使用 安卓 databinding_MVVM

Paste_Image.png

二、使用DataBinding有什么好处

对于每个Android开发人员来说,每个Activity的findViewById是一种重复、费力且傻瓜式的操作。于是有了很多注解框架来解决这一类问题,如(ButterKnife、Dagger),但是View层的数据解析还是要写。而DataBinding不仅解决了findViewById的重复操作,它的数据解析更是在XML层上解决,因此如果我们使用DataBinding,数据解析就会更快,这也是官网文档说DataBinding能提高解析XML的速度原因。并且使用DataBinding,你会发现代码真的是省了很多,同时它配合MVVM框架的使用更是比MVP框架提高了提高可维护性(解决了MVP大量的手动View和Model同步的问题,提供双向绑定机制)。同时它没有空指针的问题。

三、DataBinding缺点

1.复杂的布局处理起来很困难
2.IDE不够完善

四、如何使用DataBinding

DataBinding的使用如下图所示:

android databinding 不能使用 安卓 databinding_MVVM_02

Paste_Image.png

在Module的build.gradle中添加下面代码,注意的是保证Gradle插件版本不低于1.5.0-alpha1

android {
    compileSdkVersion 25
    buildToolsVersion "25.0.2"
    ...
    dataBinding {
        enabled true//添加这个
    }
}

activity_main
其中 type 属性就是我们在 Java 文件中定义的 User 类。而 name中的User 是类型的变量,然后把它跟布局文件中声明的变量进行绑定。

<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">

    <data>

        <import type="com.haijia.mvvp.bean.User" />

        <variable
            name="user"
            type="User" />

    </data>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">

        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@{String.valueOf(user.id)}" />

        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="@{user.realName}" />


    </LinearLayout>

</layout>

MainActivity

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        ActivityMainBinding binding = DataBindingUtil.setContentView(this, R.layout.activity_main);
        binding.setUser(new User(123,"黄海佳"));
    }
}

就是这么简单就搞定了MVVM的框架,但是这里面有很多细节,下面我们谈谈这些细节。

六、注意细节
1. android:text 中只能写" @{...}"的形式
<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="@{user.name}" />

输出:黄海佳

不能这样写:

<TextView
    ...
    android:text="姓名@{user.name}" />

输出:姓名@{user.name}

不能这样写:

<TextView
    ...
    android:text="姓名+@{user.name}" />

输出:姓名+@{user.name}
2.注意 android:text 中是 String 类型

假如值 user.id 是 int 类型的话,一定要记得转成 String 类型(String.valueOf())

<TextView
    ...
    android:text="@{String.valueOf(user.id)}" />
3.属性的使用(可用表达式):
<TextView
    ...
    android:text="@{user.name}"
    android:marginTop="@{true ? @dimen/largeMargin : @dimen/smallMartin}"/>
4.属性的使用(可使用外部静态方法):

如你有一个工具类的方法

public class MyStringUtils {
    public static String capitalize(final String word) {
        if (word.length() > 1) {
            return String.valueOf(word.charAt(0)).toUpperCase() + word.substring(1);
        }
        return word;
    }
}
<!--导入类-->
<import type="android.databinding.utils.MyStringUtils" />
<TextView
    ...
    android:text="@{StringUtils.capitalize(user.name)}"
    android:marginTop="@{1>0? @dimen/largeMargin : @dimen/smallMartin}"/>
5.使用资源或者属性时,记得引包

因为用了View属性和Color属性,需要引入包。

<import type="android.view.View" />
<import type="android.graphics.Color"/>
<!--显示-->
<TextView
    ...
     android:visibility="@{true? View.INVISIBLE : View.VISIBLE}"/>

<!--颜色-->
<TextView
    ...
    android:textColor="@{true? Color.RED : Color.YELLOW}"/>
6.自定义绑定类名称注意包名

如果项目结构如下

|--com
    |--dataBinding
        |--adapter
        |--ui
            |--CustomView
        |--adapter

那么引入包,我们可以写 com.databinding.CustomView也可以写 com.databinding.ui.CustomView,只要在项目包中即可。

<import class="com.databinding.CustomView" />
<import class="com.databinding.ui.CustomView" />
7.XML文件中不能包含< >符号

如果你的项目里面有用到 "< >" 这样的格式,需要转移一下,例如"<"写成"<"

<!--错误写法-->
<data>
    <import type="android.databinding.ObservableMap" />
    <variable
        name="muser"
        type="ObservableMap<String, Object>" />
</data>


<!--正确写法-->
<data>
    <import type="android.databinding.ObservableMap" />
    <variable
        name="muser"
        type="ObservableMap<String, Object>" />
</data>
7.Null Coalescing 运算符
<!--写法1-->
android:text="@{user.displayName ?? user.lastName}"


<!--写法2-->
android:text="@{user.displayName != null ? user.displayName : user.lastName}"
8.类型别名

如果我们在 data 节点了导入了两个同名的类怎么办?为导入的类添加别名即可

<import type="com.databinding.bean.User" />
<import type="com.databinding.data.User" alias="DetailUser" />
<variable name="user" type="DetailUser" />

暂时就写这些,后面有机会深入研究再分享