我们在构建MVVM应用的时候数据时双向流动的,比如:用户输入了数据,那么我们的model层的数据也要自动跟着更新或者我们校验了数据,是图层也要给用户反馈;网络请求完成,我们的视图层的数据也要跟着更新。
定义model层
代码语言:javascript复制package com.xiangshike.live.model
import androidx.databinding.ObservableField
data class UserModel(
val username: ObservableField<String> = ObservableField(""),
val password: ObservableField<String> = ObservableField("")
) {
override fun toString(): String {
return "UserModel(username=
}
}
ObservableField表示这是一个可以被观察的String类型数据,我们在用户的model层定义了两个可以被观察的变量,我们可以和视图进行双向绑定
Activity
代码语言:javascript复制package com.xiangshike.live
import android.util.Log
import com.xiangshike.live.base.BaseActivity
import com.xiangshike.live.databinding.ActivityMainBinding
import com.xiangshike.live.model.UserModel
import kotlinx.android.synthetic.main.activity_main.*
class MainActivity : BaseActivity<ActivityMainBinding>() {
private val mUserModel: UserModel by lazy { UserModel() }
override fun getLayoutId(): Int = R.layout.activity_main
override fun initData() {
mDataBind.userModel = mUserModel
}
override fun initView() {
loginBtn.setOnClickListener {
login()
}
}
private fun login() {
val username = mUserModel.username.get().toString()
val password: String = mUserModel.password.get().toString()
username.isEmpty().let {
when (it) {
true -> usernameLayout.error = "用户名不可以为空"
false -> usernameLayout.isErrorEnabled = false
}
}
password.isEmpty().also {
when (it) {
true -> passwordLayout.error = "密码不可以为空"
false -> passwordLayout.isErrorEnabled = false
}
}
Log.d("mUserModel", "username:
}
}
首先,我们给登录按钮增加点击事件
代码语言:javascript复制override fun initView() {
loginBtn.setOnClickListener {
login()
}
}
其次,我们定义了login的方法,在这里我们实现了视图和model的双向绑定
代码语言:javascript复制 private fun login() {
val username = mUserModel.username.get().toString()
val password: String = mUserModel.password.get().toString()
username.isEmpty().let {
when (it) {
true -> usernameLayout.error = "用户名不可以为空"
false -> usernameLayout.isErrorEnabled = false
}
}
password.isEmpty().also {
when (it) {
true -> passwordLayout.error = "密码不可以为空"
false -> passwordLayout.isErrorEnabled = false
}
}
Log.d("mUserModel", "username:
}
view层
代码语言:javascript复制
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<data>
<variable
name="userModel"
type="com.xiangshike.live.model.UserModel" />
</data>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<com.google.android.material.textfield.TextInputLayout
android:id="@ id/usernameLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="66dp">
<com.google.android.material.textfield.TextInputEditText
android:id="@ id/username"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="@string/username"
android:singleLine="true"
android:text="@={userModel.username}" />
</com.google.android.material.textfield.TextInputLayout>
<com.google.android.material.textfield.TextInputLayout
android:id="@ id/passwordLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="66dp"
app:passwordToggleEnabled="true">
<com.google.android.material.textfield.TextInputEditText
android:id="@ id/password"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="@string/password"
android:inputType="textPassword"
android:text="@={userModel.password}" />
</com.google.android.material.textfield.TextInputLayout>
<Button
android:id="@ id/loginBtn"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/login" />
</LinearLayout>
</layout>
我们的密码框和model双向绑定
代码语言:javascript复制@={userModel.username} 实现的双向绑定,model<=>view的双向数据流通
<com.google.android.material.textfield.TextInputEditText
android:id="@ id/username"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="@string/username"
android:singleLine="true"
android:text="@={userModel.username}" />
我们输入内容,点击登录,查看控制台输出
代码语言:javascript复制2020-04-14 11:28:00.886 10583-10583/? D/mUserModel: username:1111 password:11111