Lifecycle原理解析,人人都能看得懂!

415 阅读4分钟

前言

之前虽然对Lifecycle的源码有一个大概的理解,但是感觉还是模棱两可,于是直接全面领略了一遍源码的风采。

今天就由浅入深直接带大家来了解一下它的原理。如果不想看长篇源码,可以直接跳**「总结」**

首先来看看它的使用

使用

首先我们先创建一个类实现DefaultLifecycleObserver,这样我们的观察者就定义好了

class SampleLifecycle : DefaultLifecycleObserver {
    override fun onCreate(owner: LifecycleOwner) {
        super.onCreate(owner)
        Log.e(TAG, "onCreate: ")
    }

    override fun onStart(owner: LifecycleOwner) {
        super.onStart(owner)
        Log.e(TAG, "onStart: ")
    }

    override fun onResume(owner: LifecycleOwner) {
        super.onResume(owner)
        Log.e(TAG, "onResume: ")
    }

    override fun onPause(owner: LifecycleOwner) {
        super.onPause(owner)
        Log.e(TAG, "onPause: ")
    }

    override fun onStop(owner: LifecycleOwner) {
        super.onStop(owner)
        Log.e(TAG, "onStop: ")
    }

    override fun onDestroy(owner: LifecycleOwner) {
        super.onDestroy(owner)
        Log.e(TAG, "onDestroy: ")
    }

    companion object {
        private const val TAG = "SampleLifecycle"
    }
}

在Activity 或者Fragment 添加监听

lifecycle.addObserver(SampleLifecycle())

这样当我们UI状态进行变化的时候就会接收到状态监听了。在使用上非常简单方便

接下来,就带领大家领略一下它的实现原理。

原理

添加观察者

首先我们从添加观察者说起,在Activity中,为什么可以获取到Lifecycle

    public Lifecycle getLifecycle() {
        return mLifecycleRegistry;
    }

跳转源码,可以看到在父类ComponentActivity中,实现 LifecycleOwner 接口, getLifecycle 返回了 mLifecycleRegistry

public class ComponentActivity extends androidx.core.app.ComponentActivity implements
        ContextAware,
        LifecycleOwner,
        ............
        {
    ............
    private final LifecycleRegistry mLifecycleRegistry = new LifecycleRegistry(this);
    ............       
 }

在 ComponentActivity 创建的时候,同时创建了 LifecycleRegistry ,LifecycleRegistry 是Lifecycle 子类。

看到这里就可以理解为什么可以在Activity 里 添加观察者了。

接下来我们看下,添加观察者。

LifecycleRegistry类   

@Override
    public void addObserver(@NonNull LifecycleObserver observer) {
        enforceMainThreadIfNeeded("addObserver");
        //初始状态
        State initialState = mState == DESTROYED ? DESTROYED : INITIALIZED;
        //通过ObserverWithState将观察者和状态进行包装
        ObserverWithState statefulObserver = new ObserverWithState(observer, initialState);
        //将包装类放到 FastSafeIterableMap<LifecycleObserver, ObserverWithState> 中 。
        ObserverWithState previous = mObserverMap.putIfAbsent(observer, statefulObserver);
        ............
        //将状态进行对齐  
        while ((statefulObserver.mState.compareTo(targetState) < 0
                && mObserverMap.contains(observer))) {
            pushParentState(statefulObserver.mState);
            final Event event = Event.upFrom(statefulObserver.mState);
            if (event == null) {
                throw new IllegalStateException("no event up from " +                statefulObserver.mState);
            }
            statefulObserver.dispatchEvent(lifecycleOwner, event);
            popParentState();         
            targetState = calculateTargetState(observer);
        }

        if (!isReentrance) {
            //同步状态 
            sync();
        }
        mAddingObserverCounter--;
    }

使用 ObserverWithState类 将观察者对象和状态进行包装,然后存储在 FastSafeIterableMap 中,这里先对ObserverWithState这个类有点印象, 在下文事件分发的时候,会再详细讲解。

FastSafeIterableMap 具有以下特性:

  • 支持键值对存储,用链表实现,模拟成Map的接口
  • 支持在遍历的过程中删除任意元素,不会触发ConcurrentModifiedException
  • 非线程安全

注释中提到的将状态进行对齐,是在添加观察者的时候,可能是在任何状态的时候进行添加的,lifecycle需要将这个状态进行对齐。

例如我们在onResume的回调中添加了观察者,此时我们的观察者就收到依次收到 onCreateonStartonResume的回调。

监听生命周期

我们的观察者是怎样收到Activity 的生命周期的监听的呢?

这里我们看下父类ComponentActivity的onCreate方法中,有一个这样的操作

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        ............
        ReportFragment.injectIfNeededIn(this);
        if (mContentLayoutId != 0) {
            setContentView(mContentLayoutId);
        }
    }
    public static void injectIfNeededIn(Activity activity) {
        ........
        android.app.FragmentManager manager = activity.getFragmentManager();
        if (manager.findFragmentByTag(REPORT_FRAGMENT_TAG) == null) {
            manager.beginTransaction().add(new ReportFragment(), REPORT_FRAGMENT_TAG).commit();
            // Hopefully, we are the first to make a transaction.
            manager.executePendingTransactions();
        }
    }

ComponentActivity 创建的时候,同时创建了ReportFragment,这个Fragment的作用就是用来分发生命周期状态的。

ReportFragment的每个生命周期的回调中,都对应的调用了 dispatch 方法 ,来进行状态分发。

最后 dispatch的方法中,又调用了 LifecycleRegistryhandleLifecycleEvent

    public void handleLifecycleEvent(@NonNull Lifecycle.Event event) {
        enforceMainThreadIfNeeded("handleLifecycleEvent");
        moveToState(event.getTargetState());
    }

我们当前的状态是通过 event.getTargetState()来获取的

        public State getTargetState() {
            switch (this) {
                case ON_CREATE:
                case ON_STOP:
                    return State.CREATED;
                case ON_START:
                case ON_PAUSE:
                    return State.STARTED;
                case ON_RESUME:
                    return State.RESUMED;
                case ON_DESTROY:
                    return State.DESTROYED;
                case ON_ANY:
                    break;
            }
            throw new IllegalArgumentException(this + " has no target state");
        }

这里是维护了一个状态机,可能有的同学不明白为什么ON_CREATE 和 ON_STOP 状态 都是属于 State.CREATED 状态,接下来用一张图来解释一下

State 一共维护了 DESTROYEDINITIALIZEDCREATEDSTARTEDRESUMED 五种状态

上图简要说明了一下 各个生命周期回调时,分别对应的状态,整个状态趋势 是分为 正在可见 和正在不可见。

通过状态机获取当前的状态之后,会将当前状态进行记录,然后会 执行 sync() 方法进行同步操作。

    private void sync() {
        LifecycleOwner lifecycleOwner = mLifecycleOwner.get();
        ......
        //当 mObserverMap 中存储的最新的状态(刚插入的) 与 最老的状态(最先插入的) 一致,并且当前状态等于最新的状态,停止同步。 
        while (!isSynced()) {
            mNewEventOccurred = false;
            if (mState.compareTo(mObserverMap.eldest().getValue().mState) < 0) {
                backwardPass(lifecycleOwner);
            }
            Map.Entry<LifecycleObserver, ObserverWithState> newest = mObserverMap.newest();
            if (!mNewEventOccurred && newest != null
                    && mState.compareTo(newest.getValue().mState) > 0) {
                forwardPass(lifecycleOwner);
            }
        }
        mNewEventOccurred = false;
    }

在这里会通过当前状态和存储的状态进行比较操作,判断当然流程 是 向正在可见发展 还是 正在向不可见发展,

例如当前执行的状态是START,与上个状态相比,如果上个状态是CREATE,相比结果就是>0 ,说明是正在可见;如果上个状态是RESUME ,相比结果<0 ,说明是正在不可见。

backwardPassforwardPass 主要有两点不同

1.在对mObserverMap 存储的状态进行遍历时,backwardPass 是以 栈的形式遍历,forwardPass是以队列的形式遍历。

2.对状态还原的时候,backwardPass 是不可见方向还原,也就是上图的粉色箭头方向,forwardPass 是以可见方向还原,也就是上图的 青绿色箭头方向。

最后是通过ObserverWithStatedispatchEvent 方法 进行了分发。

最后是怎样通知到我们对应的观察者对象的呢?

ObserverWithState 在上文有提到,是对观察者对象和状态进行了一个包装,在这里我们来详细看一下。

    static class ObserverWithState {
        State mState;
        LifecycleEventObserver mLifecycleObserver;

        ObserverWithState(LifecycleObserver observer, State initialState) {
            mLifecycleObserver = Lifecycling.lifecycleEventObserver(observer);
            mState = initialState;
        }

        void dispatchEvent(LifecycleOwner owner, Event event) {
            State newState = event.getTargetState();
            mState = min(mState, newState);
            mLifecycleObserver.onStateChanged(owner, event);
            mState = newState;
        }
    }

我们先看包装的时候的操作,是执行了一个 Lifecycling.lifecycleEventObserver(observer) 操作。

    static LifecycleEventObserver lifecycleEventObserver(Object object) {
        boolean isLifecycleEventObserver = object instanceof LifecycleEventObserver;
        boolean isFullLifecycleObserver = object instanceof FullLifecycleObserver;
        if (isLifecycleEventObserver && isFullLifecycleObserver) {
            return new FullLifecycleObserverAdapter((FullLifecycleObserverobject,
                    (LifecycleEventObserverobject);
        }
        if (isFullLifecycleObserver) {
            return new FullLifecycleObserverAdapter((FullLifecycleObserverobjectnull);
        }
}

是返回一个对应类型 的实例化对象 ,我们自定义的观察者,实现的是DefaultLifecycleObserver 接口,DefaultLifecycleObserver接口又继承了FullLifecycleObserver ,所以这里会新建一个 FullLifecycleObserverAdapter 对象,并返回,

再看 ObserverWithStatedispatchEvent 操作,调用了 onStateChanged 方法,然后就会调用到 FullLifecycleObserverAdapteronStateChanged 里面

在这里面 就是进行接口回调,然后我们的观察者就可以接收到生命周期的回调了。

分析到这里,我们就可以将整个 添加观察者,对应生命周期时间 分发 的过程全部联系起来了。

总结

在这里我们总结一下:

首先自定义观察者,实现了FullLifecycleObserver 接口,Activity 的父类ComponentActivity 实现了 LifecycleOwner ,所以可以添加观察者,并且自己的onCreate 方法中,创建并添加了一个ReportFragment ,用来感应自身的生命周期的回调, 并进行对应分发。

在分发过程中,Lifecycle 通过内部维护的状态机 将生命周期事件转化为State状态,并进行存储,在 分发过程中,通过状态比较来判断 当前过程是正在可见还是正在不可见,不同过程采用不同策略。最后通过调用 LifecycleEventObserveronStateChanged 方法 来进行回调。

写在最后

整体来说,整个框架原理并不是很难理解,主要是状态机那部分,需要多思考一下, 最好借助图像工具 具体的展示出来。

今天的分享就到这里,希望这篇文章在你学习Lifecycle的路上能够有所帮助。