基于:
macOs:10.14/AS:3.4/Android build-tools:28.0.0
思路
看源碼前先考慮下如果要自己實(shí)現(xiàn) LiveData
應(yīng)該怎么做?
基本做法:
- 目標(biāo)數(shù)據(jù)私有;
- 開放
setter
方法用于更新目標(biāo)數(shù)據(jù); - 提供方法添加數(shù)據(jù)變化監(jiān)聽器(
Observer
);
擴(kuò)展:
- 允許子線程更新數(shù)據(jù), 因此
setter
需要考慮同步; - 項(xiàng)目中可能多個(gè)地方需要用到目標(biāo)數(shù)據(jù),因此回調(diào)監(jiān)聽器(
Observer
)需支持添加多個(gè); - 遍歷通知各
Observer
更新數(shù)據(jù)期間若數(shù)據(jù)發(fā)生了變化,要如何處理; - 數(shù)據(jù)變化時(shí)常常都需要更新UI,而UI有生命周期,因此
Observer
需要提供Lifecycle
相關(guān)邏輯支持,包括:- 定義處于哪些生命周期的
Observer
可以收到數(shù)據(jù)更新; -
onDestroy()
時(shí)自動(dòng)移除Observer
等;
- 定義處于哪些生命周期的
- 如何定義
數(shù)據(jù)變化
呢? 最簡單直接的做法是每次觸發(fā)setter
方法時(shí)都當(dāng)作數(shù)據(jù)發(fā)生了變化, 遍歷通知所有Observer
即可, 更進(jìn)一步的判定交給調(diào)用方;
......
簡單使用
// 定義 livedata
object ParaConfig {
// 定義一個(gè)私有的 `MutableLiveData`
private val msgLiveData = MutableLiveData<String>()
// 開放給外部獲取數(shù)據(jù)更新時(shí),提供不可變的 `LiveData` 即可;
fun getMsgLiveData(): LiveData<String> = msgLiveData
fun updateMsg(msg: String, inBgThread: Boolean = false) {
if (inBgThread) {
msgLiveData.postValue(msg) // 在子線程中更新數(shù)據(jù)
} else {
msgLiveData.value = msg // 在主線程中更新數(shù)據(jù)
}
}
}
// 添加 `Observer`
class LiveDataFrag : Fragment() {
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
// 添加一個(gè)跟生命周期相關(guān)的 `Observer`
ParaConfig.getMsgLiveData().observe(this, Observer<String> { newMsg ->
tv_msg.text = newMsg
})
// 無視生命周期, 每次數(shù)據(jù)變化時(shí)都會(huì)回調(diào),需要自行移除observer
ParaConfig.getMsgLiveData().observeForever {
Logger.d("observeForever: $it","tag_livedata")
}
}
}
看源碼我還是習(xí)慣從調(diào)用入口一步步往下看, 以下也是按照這種順序來;
實(shí)現(xiàn)
livedata
添加 Observer
// LiveData.java
public abstract class LiveData<T> {
private static final Object NOT_SET = new Object();
// 實(shí)際數(shù)據(jù),類型為 Object 而非 T
private volatile Object mData = NOT_SET;
// 存儲所有的 Observer
private SafeIterableMap<Observer<T>, ObserverWrapper> mObservers = new SafeIterableMap<>();
// 添加跟生命周期相關(guān)的 observer
// 目標(biāo)數(shù)據(jù)
@MainThread
public void observe(@NonNull LifecycleOwner owner, @NonNull Observer<T> observer) {
// 若 LifecycleOwner 已處于已被銷毀,則忽略該 observer
if (owner.getLifecycle().getCurrentState() == DESTROYED) {
return;
}
// 將 LifecycleOwner 和 Observer 功能進(jìn)行綁定包裝
// 生成支持生命周期感知的 Observer: LifecycleBoundObserver
LifecycleBoundObserver wrapper = new LifecycleBoundObserver(owner, observer);
// 避免重復(fù)添加相同的observer
ObserverWrapper existing = mObservers.putIfAbsent(observer, wrapper);
if (existing != null && !existing.isAttachedTo(owner)) {
throw new IllegalArgumentException("Cannot add the same observer"
+ " with different lifecycles");
}
if (existing != null) {
return;
}
// 實(shí)現(xiàn)對 LifecycleOwner 生命周期的感知
// 關(guān)鍵還是 LifecycleBoundObserver 類,我們馬上進(jìn)去看一下
owner.getLifecycle().addObserver(wrapper);
}
// 無視生命周期, 每次數(shù)據(jù)發(fā)生變化時(shí),都會(huì)回調(diào)通知 Observer
// 需要手動(dòng)在不需要時(shí)移除 Observer
@MainThread
public void observeForever(@NonNull Observer<T> observer) {
AlwaysActiveObserver wrapper = new AlwaysActiveObserver(observer);
ObserverWrapper existing = mObservers.putIfAbsent(observer, wrapper);
if (existing != null && existing instanceof LiveData.LifecycleBoundObserver) {
throw new IllegalArgumentException("Cannot add the same observer"
+ " with different lifecycles");
}
if (existing != null) {
return;
}
wrapper.activeStateChanged(true);
}
}
MutableLiveData
只是簡單重寫了 LiveData
的 setValue(T)
/postValue(T)
方法, 改為 public
而已;
數(shù)據(jù)如何傳遞的: setValue(T)
解析
// LiveData.java
@MainThread
protected void setValue(T value) {
// 只能在UI線程中調(diào)用,否則拋出異常,崩潰
assertMainThread("setValue");
mVersion++;
mData = value;
dispatchingValue(null);
}
private boolean mDispatchingValue;
// 若參數(shù) initiator 非空,則表示只通知特定的 ObserverWrapper, 否則是回調(diào)通知所有 ObserverWrapper
// 由于只在主線程中調(diào)用,因此不用做多線程處理
private void dispatchingValue(@Nullable ObserverWrapper initiator) {
// 小技巧: 在遍歷通知各 ObserverWrapper 期間, 若數(shù)據(jù)發(fā)生了變化, 則會(huì)重新遍歷通知
if (mDispatchingValue) {
mDispatchInvalidated = true;
return;
}
mDispatchingValue = true;
do {
mDispatchInvalidated = false;
if (initiator != null) {// initiator 非空時(shí),只更新特定 ObserverWrapper
considerNotify(initiator); // 實(shí)際更新數(shù)據(jù)的方法
initiator = null;
} else { // 否則遍歷更新所有 ObserverWrapper
for (Iterator<Map.Entry<Observer<T>, ObserverWrapper>> iterator =
mObservers.iteratorWithAdditions(); iterator.hasNext(); ) {
considerNotify(iterator.next().getValue());
// 若數(shù)據(jù)發(fā)生變化, 則退出for循環(huán)
// 而外層 do...while() 判定條件為true,就會(huì)重新遍歷通知各 ObserverWrapper;
if (mDispatchInvalidated) {
break;
}
}
}
} while (mDispatchInvalidated);
mDispatchingValue = false;
}
// 判斷是否要將數(shù)據(jù)分發(fā)到指定的 ObserverWrapper
private void considerNotify(ObserverWrapper observer) {
// 是否可以分發(fā)數(shù)據(jù)到指定的 observer, 由 mActive 來控制
// 所以 mActive 很重要,具體下一節(jié)解讀
if (!observer.mActive) {
return;
}
// 二次確認(rèn)狀態(tài), 可能生命周期發(fā)生了變化,但 mActive 并未改變
if (!observer.shouldBeActive()) {
// active -> inactive 時(shí)通知更新狀態(tài)
// inactive 狀態(tài)下就不需要分發(fā)數(shù)據(jù)了
observer.activeStateChanged(false);
return;
}
// 若 ObserverWrapper 持有的數(shù)據(jù)值已是最新版本, 自然也不用分發(fā)
if (observer.mLastVersion >= mVersion) {
return;
}
observer.mLastVersion = mVersion;
// 通知 observer 數(shù)據(jù)有更新
// observer.mObserver 是調(diào)用方實(shí)際傳入的
observer.mObserver.onChanged((T) mData);
}
用于子線程調(diào)用的 postValue(T)
會(huì)發(fā)射一個(gè) Runnable
到主線程中, 最終也是通過 setValue(T)
來實(shí)現(xiàn)數(shù)據(jù)分發(fā);
當(dāng)然, postValue(T)
也可以在主線程調(diào)用,不過是多此一舉,如:
// observer會(huì)先收到 "msgFromSetValue" 然后才收到 "msgFromPostValue"
someBtnView.setOnClickListener {
msgLiveData.postValue("msgFromPostValue")
msgLiveData.value = "msgFromSetValue"
}
ObserverWrapper
類解析
ObserverWrapper
// LiveData 的內(nèi)部抽象類
// 包裝用戶傳入的 Observer, 提供數(shù)據(jù)版本記錄以及active狀態(tài)(生命周期)判斷
private abstract class ObserverWrapper {
final Observer<T> mObserver;
boolean mActive; // 確定當(dāng)前 ObserverWrapper 是否生效,true時(shí)才可進(jìn)行數(shù)據(jù)更新
int mLastVersion = START_VERSION; // 當(dāng)前持有的數(shù)據(jù)版本號,初始值為 -1
ObserverWrapper(Observer<T> observer) {
mObserver = observer;
}
// 判斷該 Observer 是否有效, true 時(shí)才會(huì)觸發(fā) activeStateChanged()
abstract boolean shouldBeActive();
boolean isAttachedTo(LifecycleOwner owner) {
return false;
}
void detachObserver() {
}
// 更新本 ObserverWrapper 的狀態(tài)
void activeStateChanged(boolean newActive) {
// 若狀態(tài)沒變化,不需要更新,直接返回
if (newActive == mActive) {
return;
}
mActive = newActive;
boolean wasInactive = LiveData.this.mActiveCount == 0;
LiveData.this.mActiveCount += mActive ? 1 : -1;
// 處于 active 狀態(tài)的 observer 數(shù)量從0 -> 1時(shí),觸發(fā) onActive() 方法
if (wasInactive && mActive) {
onActive();
}
// 處于 active 狀態(tài)的 observer 數(shù)量從 1 -> 0時(shí),觸發(fā) onInactive() 方法
// 提供給觀察者釋放資源的機(jī)會(huì)
if (LiveData.this.mActiveCount == 0 && !mActive) {
onInactive();
}
// observer 從 inactive -> active 時(shí), 更新數(shù)據(jù)
if (mActive) {
// 將數(shù)據(jù)發(fā)送給該 observer
dispatchingValue(this);
}
}
}
此類并未給出 inactive/active 具體是何種狀態(tài), 具體應(yīng)是由 shouldBeActive()
來確定, 因此需要從子類查找;
子類 AlwaysActiveObserver
比較簡單, 只是將shouldBeActive()
固定返回 true
,表示一直生效, 每次數(shù)據(jù)發(fā)生變化時(shí)都需要發(fā)送通知;
我們看下 LifecycleBoundObserver
類;
LifecycleBoundObserver
解析
// LiveData 內(nèi)部類
// 將 LifecycleObserver 和 ObserverWrapper 結(jié)合,當(dāng)生命周期變化時(shí),通知 ObserverWrapper 更新數(shù)據(jù)
class LifecycleBoundObserver extends ObserverWrapper implements GenericLifecycleObserver {
@NonNull final LifecycleOwner mOwner;
LifecycleBoundObserver(@NonNull LifecycleOwner owner, Observer<T> observer) {
super(observer);
mOwner = owner;
}
@Override
boolean shouldBeActive() {
// 此處定義了哪些生命周期是 `active` 的
// 結(jié)合 Lifecycle.State 類 ,我們知道是: STARTED/RESUMED 兩種狀態(tài)
// 對應(yīng)于生命周期 `onStart()` 之后到 `onStop()` 之前
return mOwner.getLifecycle().getCurrentState().isAtLeast(STARTED);
}
// 生命周期變化時(shí)回調(diào)本方法
@Override
public void onStateChanged(LifecycleOwner source, Lifecycle.Event event) {
// 若當(dāng)前 LifecycleOwner onDestory() 了, 則自動(dòng)移除 observer, 避免內(nèi)存泄露
if (mOwner.getLifecycle().getCurrentState() == DESTROYED) {
removeObserver(mObserver);
return;
}
// 將 shouldBeActive() 返回的狀態(tài)當(dāng)做本 ObserverWrapper 的狀態(tài)
// 即 mActive = shouldBeActive()
activeStateChanged(shouldBeActive());
}
@Override
boolean isAttachedTo(LifecycleOwner owner) {
return mOwner == owner;
}
@Override
void detachObserver() {
mOwner.getLifecycle().removeObserver(this);
}
}
小結(jié)
- 只能在主線程中進(jìn)行
Observer
的添加:observe(@NonNull LifecycleOwner owner, @NonNull Observer<T> observer)
observeForever(@NonNull Observer<T> observer)
- 添加帶
LifecycleOwner
的Observer
時(shí), 若發(fā)生onDestory()
,則會(huì)自動(dòng)移除Observer
; - 數(shù)據(jù)只會(huì)在
LifecycleOwner
處于onStart()
/onResume()
/onPause()
生命周期時(shí),才會(huì)分發(fā); - 若處于 active 的
Observer
數(shù)量從 1 -> 0, 回調(diào)onInactive()
,適用于子類進(jìn)行資源釋放; - 若處于 active 的
Observer
數(shù)量從 0 -> 1, 回調(diào)onActive()
; -
LiveData
類和ObserverWrapper
類都會(huì)在內(nèi)部持有一個(gè)數(shù)據(jù)版本號; -
LiveData
數(shù)據(jù)發(fā)生變化時(shí),會(huì)切換到主線程,然后遍歷所有Observer
, 并將數(shù)據(jù)分發(fā)給處于 active 狀態(tài)并且數(shù)據(jù)版本號不一致的Observer
;