08.DatabindingUI更新数据更新
UI更新->数据更新
前面我们是数据更新了,UI跟着更新,接下来我们是UI更新,数据跟着更新。这跟我们前面学习到的Vue.js是不是很像呀,不过我们需要做一些处理。当我们输入框变化的时候,当我们数字选择器内容改变的时候,单选框状态改变的时候,我们的数据也要跟着变化了。
应用场景,比如说我们在交易股票的时候,你输入数量,会动态地计算你的成交以后的钱是多少。
使用传统的做法,我们得监听输入股票数量的输入框的内容变化,然后再进行计算,设置到最终成交金额的控件上。
如果使用DataBinding,这个怎么做呢?
UI布局
<?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"
xmlns:tools="http://schemas.android.com/tools">
<data>
<variable
name="stock"
type="com.sunofbeaches.databindingdemo.domain.ObservableStock" />
<import
type="com.sunofbeaches.databindingdemo.converter.Converter" />
</data>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="@+id/textView11"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="出售数量"
app:layout_constraintBottom_toTopOf="@+id/guideline8"
app:layout_constraintEnd_toStartOf="@+id/guideline10"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline8"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_begin="70dp" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline9"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_begin="140dp" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline11"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_begin="210dp" />
<androidx.constraintlayout.widget.Guideline
android:id="@+id/guideline10"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintGuide_begin="140dp" />
<TextView
android:id="@+id/textView12"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="当前股价"
app:layout_constraintBottom_toTopOf="@+id/guideline9"
app:layout_constraintEnd_toStartOf="@+id/guideline10"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/guideline8" />
<TextView
android:id="@+id/textView13"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="预计成交总价"
app:layout_constraintBottom_toTopOf="@+id/guideline11"
app:layout_constraintEnd_toStartOf="@+id/guideline10"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/guideline9" />
<EditText
android:id="@+id/editTextTextPersonName"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:inputType="number"
android:text="@={Converter.int2String(stock.sellCount)}"
app:layout_constraintBottom_toTopOf="@+id/guideline8"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="@+id/guideline10"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/textView14"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{String.valueOf(stock.currentPrise)}"
app:layout_constraintBottom_toTopOf="@+id/guideline9"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="@+id/guideline10"
app:layout_constraintTop_toTopOf="@+id/guideline8" />
<TextView
android:id="@+id/textView15"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{String.valueOf(stock.totalPrise)}"
app:layout_constraintBottom_toTopOf="@+id/guideline11"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="@+id/guideline10"
app:layout_constraintTop_toTopOf="@+id/guideline9" />
</androidx.constraintlayout.widget.ConstraintLayout>
</layout>
Activity代码
class TwoWayBindingActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val contentView =
DataBindingUtil.setContentView<ActivityTowWayBindingBinding>(
this,
R.layout.activity_tow_way_binding
)
val stock = ObservableStock()
contentView.stock = stock
stock.addOnPropertyChangedCallback(object : Observable.OnPropertyChangedCallback() {
override fun onPropertyChanged(sender: Observable?, propertyId: Int) {
if (sender is ObservableStock) {
sender.totalPrise = sender.sellCount * sender.currentPrise
}
}
})
}
}
相关的Bean类
class ObservableStock :
BaseObservable() {
var sellCount: Int = 0
set(value) {
if (value != field) {
field = value
notifyChange()
}
}
var currentPrise: Float = 11.0f
var totalPrise: Float = 0.0f
}
转换器,EditText只接受String,所以我们需要一个转换器,来把String转成int类型,把int类型转成String类型
object Converter {
@InverseMethod("string2Int")
@JvmStatic
fun int2String(
value: Int
): String {
return value.toString()
}
@JvmStatic
fun string2Int(value: String): Int {
if (value.isEmpty()) {
return 0
}
return value.toInt()
}
}
运行结果: