Android LiveData实现原理

2021-06-08  本文已影响0人  进击的包籽

1.了解LiveData

2.简单使用

class TestViewModel : ViewModel() {

    val  livedata = MutableLiveData<String>("bao")

    init {
        livedata.postValue("bao_post")
    }

    fun initData(){
        livedata.value = "bao_set"
    }
}
    
/* 观察数据变化 */
viewModel.livedata.observe(TestFragment@this, object : Observer<String> {
    override fun onChanged(t: String?) {
        t?.let {
            Log.d(TAG,it)
        }
    }
})

3. 对组件Lifecycle生命周期感知分析

3.1 observe 方法

    //map 的 key 为LiveData数据观察者,value为组件的Lifecycle观察者
    private SafeIterableMap<Observer<? super T>, ObserverWrapper> mObservers =
            new SafeIterableMap<>();

    @MainThread
    public void observe(@NonNull LifecycleOwner owner, @NonNull Observer<? super T> observer) {
        assertMainThread("observe");
        //判断当前生命周期的状态
        if (owner.getLifecycle().getCurrentState() == DESTROYED) {
            // ignore
            return;
        }
        //Lifecycle的生命周期变化逻辑在这里
        LifecycleBoundObserver wrapper = new LifecycleBoundObserver(owner, observer);
        //mObservers 保存
        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;
        }
        //感知lifecycle的生命周期变化
        owner.getLifecycle().addObserver(wrapper);
    }

3.2 LifecycleBoundObserver 做了什么

    class LifecycleBoundObserver extends ObserverWrapper implements LifecycleEventObserver {
        @NonNull
        //一般组件,比如Activity、fragment可以会实现LifecycleOwner ,可以拿到lifecycle
        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) {
            //获取当前生命周期状态
            Lifecycle.State currentState = mOwner.getLifecycle().getCurrentState();
            //如果组件已销毁了,就移除观察
            if (currentState == DESTROYED) {
                removeObserver(mObserver);
                return;
            }
            Lifecycle.State prevState = null;
            while (prevState != currentState) {
                prevState = currentState;
                activeStateChanged(shouldBeActive());
                currentState = mOwner.getLifecycle().getCurrentState();
            }
        }

        /* 判断是否绑定 */
        @Override
        boolean isAttachedTo(LifecycleOwner owner) {
            return mOwner == owner;
        }

        /* 移除观察 */
        @Override
        void detachObserver() {
            mOwner.getLifecycle().removeObserver(this);
        }
    }

3.3 activeStateChanged 方法

        void activeStateChanged(boolean newActive) {
            //组件状态如果不变返回
            if (newActive == mActive) {
                return;
            }
            // immediately set active state, so we'd never dispatch anything to inactive
            // owner
            mActive = newActive;
            changeActiveCounter(mActive ? 1 : -1);
            //如果是活动的就发送数据
            if (mActive) {
                dispatchingValue(this);
            }
        }

3.4 简易流程图

LiveData注册

4.发送数据分析

4.1 postValue 发送数据到主线程

    protected void postValue(T value) {
        boolean postTask;
        //加锁
        synchronized (mDataLock) {
            postTask = mPendingData == NOT_SET;
            //保存要发送的数据value
            mPendingData = value;
        }
        if (!postTask) {
            return;
        }
        //利用主线程Handler发送
        ArchTaskExecutor.getInstance().postToMainThread(mPostValueRunnable);
    }

4.2 postValue 其实就是 setValue

    private final Runnable mPostValueRunnable = new Runnable() {
        @SuppressWarnings("unchecked")
        @Override
        public void run() {
            Object newValue;
            synchronized (mDataLock) {
                newValue = mPendingData;
                mPendingData = NOT_SET;
            }
            setValue((T) newValue);
        }
    };

4.3 postToMainThread 主线程Handler

public class ArchTaskExecutor extends TaskExecutor {
    @NonNull
    private TaskExecutor mDelegate;

    @NonNull
    private TaskExecutor mDefaultTaskExecutor;
    
    private ArchTaskExecutor() {
        mDefaultTaskExecutor = new DefaultTaskExecutor();
        mDelegate = mDefaultTaskExecutor;
    }
    ...
    @Override
    public void postToMainThread(Runnable runnable) {
        mDelegate.postToMainThread(runnable);
    }
    ...
}

4.4 DefaultTaskExecutor 类

public class DefaultTaskExecutor extends TaskExecutor {
    @Nullable
    private volatile Handler mMainHandler;

    @Override
    public void postToMainThread(Runnable runnable) {
        if (mMainHandler == null) {
            synchronized (mLock) {
                if (mMainHandler == null) {
                    mMainHandler = createAsync(Looper.getMainLooper());
                }
            }
        }
        //noinspection ConstantConditions
        mMainHandler.post(runnable);
    }
}

4.5 setValue 方法

    @MainThread
    protected void setValue(T value) {
        assertMainThread("setValue");
        mVersion++;
        mData = value;
        dispatchingValue(null);
    }

4.6 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 传过来 initiator 为空,执行这里
                // mObservers 拿出来,逐个发送数据
                for (Iterator<Map.Entry<Observer<? super T>, ObserverWrapper>> iterator =
                        mObservers.iteratorWithAdditions(); iterator.hasNext(); ) {
                    considerNotify(iterator.next().getValue());
                    if (mDispatchInvalidated) {
                        break;
                    }
                }
            }
        } while (mDispatchInvalidated);
        mDispatchingValue = false;
    }

4.7 considerNotify 判断发送数据

    private void considerNotify(ObserverWrapper observer) {
        //组件是否活动
        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;
        }
        //校验是否发送过数据
        if (observer.mLastVersion >= mVersion) {
            return;
        }
        observer.mLastVersion = mVersion;
        //发送数据
        observer.mObserver.onChanged((T) mData);
    }

4.8 简易流程图

postValue

5.粘性事件

5.1 粘性事件分析

1.粘性事件就是先发送数据,后面再注册观察者,还能收到消息。
2.我们就从LiveData.observe 开始,新的页面注册LiveData观察者,也注册Lifecycle观察。

  1. 当新页面生命周期变化,就会执行 LifecycleBoundObserver.onStateChanged 的方法,如果忘记了回去看 3.2
  2. 接下来 activeStateChanged 方法,因为是新页面,组件状态是活动的,就走到 dispatchingValue 方法,看 3.3
  3. dispatchingValue 传进来当前新页面的 initiator 是不为空的,就只会给当前观察者发送数据。

5.2 简易流程图

粘性事件
上一篇 下一篇

猜你喜欢

热点阅读