(二)LiveData源码分析

LiveData是什么?

可观察的数据存储类,就有生命周期感知能力,遵循(Activity、Fragment、Service)的生命周期

可以确保LiveData仅更新处在活跃生命周期的应用组件观察者。

基本使用

object MyLiveData {

    // 创建LiveData实例
    val data1: MutableLiveData<String> by lazy {
        MutableLiveData<String>()
    }
}


class MyService : Service() {
    override fun onBind(p0: Intent?): IBinder? = null

    override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
        thread {
            for (i in 1..100000) {
                Log.d("server", "消息内容是$i ")
                // LiveData 发送消息
                MyLiveData.data1.postValue("服务器给你推送消息啦,消息内容是$i")
                Thread.sleep(2000)
            }

        }
        return super.onStartCommand(intent, flags, startId)
    }
}

MyLiveData.info1.observe(this, {
    textView.text = it
})

LiveData源码分析

订阅流程

// 1、第一个参数 持有被观察者Activity(代表宿主的生命周期当前的状态) ComponentActivity 会实现 LifecycleOwner 接口
// 宿主 == 生命周期
// onStart,onResume mActive = ture  代表存活
// 2、第二个参数 Observer
@MainThread
public void observe(@NonNull LifecycleOwner owner, @NonNull Observer<? super T> observer) {
    assertMainThread("observe");
    // 销毁状态做什么都不做 减少内存开销
    if (owner.getLifecycle().getCurrentState() == DESTROYED) {
        // ignore
        return;
    }
    // Observer 单纯的接口 无法感知生命周期 只能通过(LifecycleBoundObserver)二次封装  来获取宿主的生命周期
    LifecycleBoundObserver wrapper = new LifecycleBoundObserver(owner, 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;
    }
    owner.getLifecycle().addObserver(wrapper);
}

LifecycleBoundObserver 

class LifecycleBoundObserver extends ObserverWrapper implements LifecycleEventObserver {
    @NonNull
    final LifecycleOwner mOwner;

    LifecycleBoundObserver(@NonNull LifecycleOwner owner, Observer<? super T> observer) {
        super(observer);
        mOwner = owner;
    }
    // 获取时候是存活的状态
    @Override
    boolean shouldBeActive() {
        return mOwner.getLifecycle().getCurrentState().isAtLeast(STARTED);
    }
    
    // 每个生命周期都会调用的函数
    @Override
    public void onStateChanged(@NonNull LifecycleOwner source, @NonNull Lifecycle.Event event) {
        // 自动帮你销毁 Observer
        if (mOwner.getLifecycle().getCurrentState() == DESTROYED) {
            removeObserver(mObserver);
            return;
        }
        activeStateChanged(shouldBeActive());
    }
}

ObserverWrapper 

void activeStateChanged(boolean newActive) {
    if (newActive == mActive) {
        return;
    }
    // immediately set active state, so we'd never dispatch anything to inactive
    // owner
    mActive = newActive;
    boolean wasInactive = LiveData.this.mActiveCount == 0;
    LiveData.this.mActiveCount += mActive ? 1 : -1;
    // 给外界暴露一个存活的方法
    if (wasInactive && mActive) {
        onActive();
    }
    // 给外界暴露一个不存活的方法
    if (LiveData.this.mActiveCount == 0 && !mActive) {
        onInactive();
    }
    if (mActive) {
        // LiveData中分发
        dispatchingValue(this);
    }
}

LiveData-dispatchingValue

@SuppressWarnings("WeakerAccess") /* synthetic access */
void dispatchingValue(@Nullable ObserverWrapper initiator) {
    if (mDispatchingValue) {
        mDispatchInvalidated = true;
        return;
    }
    mDispatchingValue = true;
    do {
        mDispatchInvalidated = false;
        // 观察者不为空走订阅流程,反之走赋值流程
        if (initiator != null) {
            // 订阅流程
            considerNotify(initiator);
            initiator = null;
        } else {
            // setValue 和 postValue 调用时
            for (Iterator<Map.Entry<Observer<? super T>, ObserverWrapper>> iterator =
                    // mObservers 所有观察者的Map
                    mObservers.iteratorWithAdditions(); iterator.hasNext(); ) {
                considerNotify(iterator.next().getValue());
                if (mDispatchInvalidated) {
                    break;
                }
            }
        }
    } while (mDispatchInvalidated);
    mDispatchingValue = false;
}

considerNotify 

private void considerNotify(ObserverWrapper observer) {
    // 时时刻刻 获取Lifecycle 的生命周期 判断是否存活 (存活:继续工作   不存活:销毁)
    if (!observer.mActive) {
        return;
    }
    // Check latest state b4 dispatch. Maybe it changed state but we didn't get the event yet.
    //
    // we still first check observer.active to keep it as the entrance for events. So even if
    // the observer moved to an active state, if we've not received that event, we better not
    // notify for a more predictable notification order.
    // 不断的递归 当页面显示出来
    if (!observer.shouldBeActive()) {
        observer.activeStateChanged(false);
        return;
    }
    
    // LiveData 的粘性数据
    // observer.mLastVersion == -1  mVersion == 0
    // 避免数据错乱
    if (observer.mLastVersion >= mVersion) {
        return;
    }
    // 版本对齐
    observer.mLastVersion = mVersion;

    // 分发数据
    observer.mObserver.onChanged((T) mData);

setValue、postValue流程

// 这里以postValue来举例,后面最终都会走回setValue
LiveData.postValue(value)

// 使用了开闭原则 装饰者模式 父类的复杂流程进行简化 暴露最简单的东西给用户
public class MutableLiveData<T> extends LiveData<T> {
    @Override
    public void postValue(T value) {
        // 调用父类的 postValue方法
        super.postValue(value);
    }

    @Override
    public void setValue(T value) {
        super.setValue(value);
    }
}

LiveData

private final Runnable mPostValueRunnable = new Runnable() {
    @Override
    public void run() {
        Object newValue;
        synchronized (mDataLock) {
            // newValue 就是 postValue 传进来的 Value
            newValue = mPendingData;
            mPendingData = NOT_SET;
        }
        //noinspection unchecked
        // 最终还是要调用到 setValue
        setValue((T) newValue);
    }
};


protected void postValue(T value) {
    boolean postTask;
    synchronized (mDataLock) {
        postTask = mPendingData == NOT_SET;
        mPendingData = value;
    }
    if (!postTask) {
        return;
    }
    // 切换到我们的主线程  通过Handler切换到主线程
    ArchTaskExecutor.getInstance().postToMainThread(mPostValueRunnable);
}
@MainThread
protected void setValue(T value) {
    assertMainThread("setValue");
    mVersion++; // 初始值 为 -1 
    mData = value; // 数据复制

    // ObserverWrapper == null 遍历map 调用 considerNotify 方法
    dispatchingValue(null);
}

Ps.

1、先订阅 后 setValue 收到消息 正确

2、先setValue 后订阅 也收到了消息 数据粘性 不正确

如何去掉数据粘性 : hook 反射 动态修改源码 就可以去除


版权声明:本文为g182064900原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。