前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Android Jetpack系列——DataBinding 使用进阶

Android Jetpack系列——DataBinding 使用进阶

作者头像
Demo_Yang
发布2019-06-15 14:57:08
1.3K0
发布2019-06-15 14:57:08
举报
文章被收录于专栏:yang0range
看了谷歌官方文章确实写的太简略了,甚至看完之后有很多地方还不知道怎么回事儿或者怎么用,那么接下来我将通过几篇文章全面介绍一下 DataBinding 以及 DataBinding 的使用。
GitHub传送门 欢迎Star 下载

背景

上一篇文章https://cloud.tencent.com/developer/article/1428728

,我们介绍了DataBinding以及DataBinding的简单的使用。可以看到,我们上一篇文章只是简单介绍了一下DataBinding,并没有详细介绍如何动态的加载数据。也就是说,这篇文章,我们将介绍,如何使用DataBinding让视图跟随这数据进行刷新变化。

观察者模式

观察者模式(Observer)完美的将观察者和被观察的对象分离开。举个例子,用户界面可以作为一个观察者,业务数据是被观察者,用户界面观察业务数据的变化,发现数据变化后,就显示在界面上。观察者模式有很多实现方式,从根本上说,该模式必须包含两个角色:观察者和被观察对象。

以上就是观察者模式的一个简单概念,而谷歌在这里开发的思想也是采用这种观察者模式的思想。

DataBinding的库,允许我们使用对象,字段,或者集合都可以进行观察。当其中的一个可观察者数据对象绑定到了视图当中,并且数据对象的属性发生更改变化的时候,视图将会自动更新。

ObservableField

ObservableField默认已经帮我们做了很多工作,比如实现了一系列的Observable接口的字段类型。

这其中包括

代码语言:javascript
复制
ObservableBoolean
ObservableByte
ObservableChar
ObservableShort
ObservableInt
ObservableLong
ObservableFloat
ObservableDouble
ObservableParcelable

在实际代码当中实际方式表现为。

通过代码实现的效果:

ObservableField.gif

我们的Model层为:

代码语言:javascript
复制
class Student {
    val name = ObservableField<String>()
    val age = ObservableInt()
}

代码当中实现为:

代码语言:javascript
复制
package com.yang.databindingdemo

import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import androidx.databinding.DataBindingUtil
import com.yang.databindingdemo.databinding.ActivityMainBinding
import com.yang.databindingdemo.model.Student

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        val binding: ActivityMainBinding = DataBindingUtil.setContentView(
            this, R.layout.activity_main
        )
        val studentInfo = Student()
        studentInfo.name.set("我叫朝阳杨大爷")
        studentInfo.age.set(20)
        binding.studentInfo = studentInfo

        binding.tvStudenname.setOnClickListener {
            studentInfo.name.set("我还是叫叫朝阳杨大爷")
        }
        binding.tvAge.setOnClickListener {
            studentInfo.age.set(18)
        }

    }


}

布局文件当中:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools"
        xmlns:app="http://schemas.android.com/apk/res-auto">
    <data>
        <import type="com.yang.databindingdemo.model.Student"/>
        <variable name="studentInfo"
                  type="Student"/>
    </data>
    <androidx.constraintlayout.widget.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            tools:context=".MainActivity">

        <TextView
                android:id="@+id/tv_studenname"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@{studentInfo.name,default = Yang}"
                android:textSize="20sp"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintRight_toRightOf="parent"
                app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="0.377"/>

        <TextView
                android:id="@+id/tv_age"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@{String.valueOf(studentInfo.age),default = 18}"
                android:textSize="20sp"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintRight_toRightOf="parent"
                app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="0.474"/>

    </androidx.constraintlayout.widget.ConstraintLayout>
</layout>

ObservableArrayMap/ObservableArrayLis/ObjservableMap

实现以上效果,我们还可以使用集合类型,这里为我们提供了三种数据结构类型。

代码语言:javascript
复制
ObservableArrayMap
ObservableArrayLis
ObjservableMap

这里我们以ObservableArrayMap为例:

我们在 Activity 当中代码为

代码语言:javascript
复制
class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        val binding: ActivityMainBinding = DataBindingUtil.setContentView(
            this, R.layout.activity_main
        )
        val map = ObservableArrayMap<String, Any>()
        map["name"] = "我叫杨大爷"
        map["age"] = 20
        binding.studentInfo = map
    }
}

然后布局文件当中为:

代码语言:javascript
复制
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools"
        xmlns:app="http://schemas.android.com/apk/res-auto">
    <data>
        <import type="androidx.databinding.ObservableArrayMap"/>
        <variable name="studentInfo" type="ObservableArrayMap&lt;String, Object&gt;"/>
    </data>
    <androidx.constraintlayout.widget.ConstraintLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            tools:context=".MainActivity">

        <TextView
                android:id="@+id/tv_studenname"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@{studentInfo[`name`],default = Yang}"
                android:textSize="20sp"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintRight_toRightOf="parent"
                app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="0.377"/>

        <TextView
                android:id="@+id/tv_age"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@{String.valueOf(studentInfo[`age`]),default = 18}"
                android:textSize="20sp"
                app:layout_constraintBottom_toBottomOf="parent"
                app:layout_constraintLeft_toLeftOf="parent"
                app:layout_constraintRight_toRightOf="parent"
                app:layout_constraintTop_toTopOf="parent" app:layout_constraintVertical_bias="0.474"/>

    </androidx.constraintlayout.widget.ConstraintLayout>
</layout>

几点注意事项

1.androidx的引用

注意,我们这里引用的 ObservableArrayMap 为 androidx 包下的,所以我们在布局文件当中引用的 ObservableArrayMap 为

代码语言:javascript
复制
androidx.databinding.ObservableArrayMap"

2.编译之后出现:与元素类型 "null" 相关联的 "type" 属性值不能包含 '<' 字符。的问题

在xml当中不能使用<应该用它的转义字符比如,<

所以,我们在代码当中需要修改为:

代码语言:javascript
复制
      <variable name="studentInfo" type="ObservableArrayMap&lt;String, Object&gt;"/>

3.编译之后出现:/ data binding error msg:Identifiers must have user defined types from the XML file. name is missing it问题

多是因为,在引用的时候的问题 ObservableArrayMap 的key的问题,

这里,我们在引用的时候,注意

代码语言:javascript
复制
  android:text="@{studentInfo[`name`],default = Yang}"

key上要有个英文的引号才可以。

4.当使用int给xml属性赋值时,如果该属性接受资源id,那么这个int会认为是资源的id。如果android:text=@{1}, 这样子text不会显示1,反而会报错,因为找不到id为1的资源

5.切记,达式里面不能有中文,否则会报错

6.在写表达式的时候,不能换行

最后

通过这篇文章,我们真正的了解如何使用 DataBinding 并且了解了数据绑定,对于数据绑定的使用。

使用 DataBinding 确实代码会显得更加优雅一些,很多 UI 逻辑在 xml 文件当中就能实现了。

但是,我们一定要注意的是,在使用 DataBinding 的时候,应当注意要保持 xml 的简洁性, 不要再 xml 当中加入 过多的业务逻辑。

接下来我们将继续深入介绍 DataBinding 尽请期待!

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2019.06.11 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 看了谷歌官方文章确实写的太简略了,甚至看完之后有很多地方还不知道怎么回事儿或者怎么用,那么接下来我将通过几篇文章全面介绍一下 DataBinding 以及 DataBinding 的使用。
  • GitHub传送门 欢迎Star 下载
  • 背景
  • 观察者模式
  • ObservableField
  • ObservableArrayMap/ObservableArrayLis/ObjservableMap
  • 几点注意事项
  • 最后
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档