写点什么

Jetpack- 在数据变化时如何优雅更新 Views 数据,ffmpeg 音视频开发实战 6 下载

用户头像
Android架构
关注
发布于: 刚刚

LiveData 可以包装任何数据,包括集合对象。LiveData 通常存储在 ViewM


《Android学习笔记总结+最新移动架构视频+大厂安卓面试真题+项目实战源码讲义》
浏览器打开:qq.cn.hn/FTe 免费领取
复制代码


odel 中,并通过 getter 方法获得。示例:


class NameViewModel : ViewModel() {


// Create a LiveData with a Stringval currentName: MutableLiveData<String> by lazy {MutableLiveData<String>()}


// Rest of the ViewModel...}


为什么是 ViewModel 持有 LiveData 而不是 Activity 或者 Fragment 中呢?


  • 这样导致 Activity 或 Fragment 代码臃肿,Activity 或 Fragment 一般用来展示数据而不是持有数据。

  • 将 LiveData 解耦,不和特定的 Activity 或 Fragment 绑定在一起。

创建 观察 LiveData 的对象

有了数据源之后,总需要有观察者来观察数据源,不然数据源就失去了存在的意义。


那么在哪里观察数据源呢?


在大多数情况下,在应用组件的onCreate()方法中访问 LiveData 是个合适的时机。这样可以确保系统不在 Activity 或 Fragment 的onResume()方法进行多余的调用;另外这样也确保 Activity 和 Fragment 尽早有数据可以进行显示。


class NameActivity : AppCompatActivity() {


private lateinit var model: NameViewModel


override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)


// Other code to setup the activity...


// Get the ViewModel.model = ViewModelProviders.of(this).get(NameViewModel::class.java)


// Create the observer which updates the UI.val nameObserver = Observer<String> { newName ->// Update the UI, in this case, a TextView.nameTextView.text = newName}


// Observe the LiveData, passing in this activity as the LifecycleOwner and the observer.model.currentName.observe(this, nameObserver)}}


在讲 nameObserver 对象传给 observe()方法后,存储在 LiveData 最近的值以参数的形式立即传递到 onChange()方法中。当然,如果此时 LiveData 没有存储值的话,onChange()方法不会被调用。

更新 LiveData 对象

LiveData 本身没有提供公共方法更新值。如果需要修改 LiveData 的数据的话,可以通过 MutableLiveData 来暴露共有方法setValue()postValue()。通常在在 ViewModel 中使用 MutableLiveData,而 MutableLiveData 暴露不可变的 LiveData 给 Observer。与 Observer 建立关系后,通过修改 LiveData 的值从而更新 Observer 中的视图。


button.setOnClickListener {val anotherName = "GitCode"model.currentName.setValue(anotherName)}


当单击 button 时,字符串GitCode会存储到 LiveData 中,nameTextView 的文本也会更新为GitCode。这里通过 button 的点击来给 LiveData 设置值,也可以网络或者本地数据库获取数据方式来设置值。

扩展 LiveData

可以通过下面的栗子来看看如何扩展 LiveData。


class StockLiveData(symbol: String) : LiveData<BigDecimal>() {private val stockManager = StockManager(symbol)


private val listener = { price: BigDecimal ->value = price}


override fun onActive() {stockManager.requestPriceUpdates(listener)}


override fun onInactive() {stockManager.removeUpdates(listener)}}


首先建立一个 StockLiveData 并继承自 LiveData,并重写两个重要方法。


  • onActivite() 当有活跃状态的订阅者订阅 LiveData 时会回调该方法。意味着需要在这里监听数据的变化。

  • onInactive() 当没有活跃状态的订阅者订阅 LiveData 时会回调该方法。此时没有必要保持 StockManage 服务象的连接。

  • setValue() 注意到value=price这里是调用了 setValue(price)方法,通过该方法更新 LiveData 的值,进而通知处于活跃状态的订阅者。


LiveData 会认为订阅者的生命周期处于STARTEDRESUMED状态时,该订阅者是活跃的。


那么如何使用 StockLiveData 呢?


override fun onActivityCreated(savedInstanceState: Bundle?) {super.onActivityCreated(savedInstanceState)val myPriceListener: LiveData<BigDecimal> = ...myPriceListener.observe(this, Observer<BigDecimal> { price: BigDecimal? ->// Update the UI.})}


以 Fragment 作 LifecycleOwner 的实例传递到 observer()方法中,这样就将 Observer 绑定到拥有生命周期的拥有者。由于 LiveData 可以在多个 Activity、Fragment 和 Service 中使用,所以可以创建单例模式。


class StockLiveData(symbol: String) : LiveData<BigDecimal>() {private val stockManager: StockManager = StockManager(symbol)


private val listener = { price: BigDecimal ->value = price}


override fun onActive() {stockManager.requestPriceUpdates(listener)}


override fun onInactive() {stockManager.removeUpdates(listener)}


companion object {private lateinit var sInstance: StockLiveData

用户头像

Android架构

关注

还未添加个人签名 2021.10.31 加入

还未添加个人简介

评论

发布
暂无评论
Jetpack-在数据变化时如何优雅更新Views数据,ffmpeg音视频开发实战6下载