Jetpack全家桶之Lifecycle

首先,Lifecycle是什么?干什么?怎么用?

一、是什么?

Life生命,cycle周期,顾名思义:Lifecycle是生命周期的意思。它是Jetpack中的一个 生命周期感知型组件 ,可执行操作来感知响应另一个组件(如 Activity 和 Fragment)的生命周期状态的变化。什么意思怎么理解呢?我们看看干什么就应该能理解了。

二、干什么?

经常面试的时候,面试官上来就问:Activity的生命周期(Fragment的生命周期),为什么大家都关注生命周期,但是好像我们工作中生命周期又不是很常用?以至于面试的时候没有复习,突然被问到最基础的生命周期突然间语塞了。

其实生命周期这个词很重要,内存泄漏 这个词就和生命周期有相当大的关系,内存泄漏的根本原因是对象的内存无法被回收,短生命周期对象被长生命周期对象所引用时,短生命周期对象在不使用时无法被回收(至于为什么无法被回收,和JVM内存回收机制有关了,这个自己去了解GC相关内容,将来也会继续讲),就造成了内存泄漏。

先来回顾一下最常见的Activity的生命周期:onCreate...onDestory。假如现在有另外一个组件,并且这个组件需要持有这个Activity的引用,这个组件可能还需要根据Activity的各个生命周期做不同的操作,按照以前的写法我们就需要在Activity的onCreate、onDestory等各个生命周期回调方法中去写相应的逻辑,并且在onDestory时还要释放掉组件对Activity的引用,否则就会造成内存泄漏。

甚至还可能一个Activity对应N多个这样的组件,也还有可能这个组件用于N多个Activity/Fragment等其他组件中,并且多个组件间相互操作,组件间耦合性过大,也不利于后期维护迭代修改。有人说那没事,抽到Base类中就好了,总有办法的~是的,总有办法的,官方就替我们想到了这个办法-Lifecycle,自动感知其他组件生命周期变化的组件。就例如:Activity生命周期执行了onCreate方法之后,组件自动感知了Activity的生命周期变化,然后能够执行相应的操作,不需要在Activity的各个生命周期中去执行组件的相应操作了。
一句话概括:Lifecycle能够自动感知其他组件生命周期,能够降低组件间的耦合性。 这么神奇?感觉看看怎么用吧!

三、怎么用?

这里用有Lifecycle之前和有Lifecycle之后管理生命周期写法来举例比较。
假设我们有一个在屏幕上显示设备位置的 Activity。 例子引用自官网

  • Lifecycle之前
internal class MyLocationListener(
        private val context: Context,
        private val callback: (Location) -> Unit
) {

    fun start() {
        // 连接系统定位服务
    }

    fun stop() {
        // 断开系统定位服务
    }
}

class MyActivity : AppCompatActivity() {
    private lateinit var myLocationListener: MyLocationListener

    override fun onCreate(...) {
        myLocationListener = MyLocationListener(this) { location ->
            // 更新UI
        }
    }

    public override fun onStart() {
        super.onStart()
        myLocationListener.start()
        //管理其他需要响应activity生命周期的组件
    }

    public override fun onStop() {
        super.onStop()
        myLocationListener.stop()
        //管理其他需要响应activity生命周期的组件
    }
}

上面例子看上去好像没什么问题,但是如果有很多管理界面和其他组件的调用需要在生命周期函数中去调用的话(如:onStart、onStop等),会造成有大量的代码出现在生命周期函数中,项目变得难以维护。
此外,无法保证在 Activity停止之前启动myLocationListener,就可能导致LocationListener组件留存时间比Activity长,且LocationListener持有了Activity,也就是之前说过的可能导致了内存泄漏。如下例子:

class MyActivity : AppCompatActivity() {
    private lateinit var myLocationListener: MyLocationListener

    override fun onCreate(...) {
        myLocationListener = MyLocationListener(this) { location ->
             // 更新UI
        }
    }

    public override fun onStart() {
        super.onStart()
        Util.checkUserStatus { result ->
            //如果checkUserStatus耗时较长,在activity停止后才回调,那么myLocationListener启动后就没办法走stop()方法了,
            //又因为myLocationListener持有activity,所以会造成内存泄漏。
            if (result) {
                myLocationListener.start()
            }
        }
    }

    public override fun onStop() {
        super.onStop()
        myLocationListener.stop()
    }

}

即:在Lifecycle之前,可能出现两个问题

  1. activity的生命周期内有大量管理组件的代码,难以维护。
  2. 无法保证组件是否真实关联生命周期,可能造成内存泄漏。
  • 在Lifecycle之后
  1. 依赖,现在项目基本都已经使用androidx了,所以直接引入
implementation 'androidx.appcompat:appcompat:1.2.0'

即可。后续的viewModel、Livedata也不需要其他再引入了,也不再介绍。

  1. 使用
    1、生命周期拥有者(如Activity/Fragment) 使用getLifecycle()获取Lifecycle实例,然后调用addObserve()方法添加观察者。
    2、观察者实现 LifecycleObserver,方法上使用OnLifecycleEvent注解关注对应生命周期,生命周期触发时就会执行对应方法。如:
//实现LifecycleObserver观察者
class LocationListener: LifecycleObserver {

    @OnLifecycleEvent(value = Lifecycle.Event.ON_START)
    fun onStart(owner: LifecycleOwner){
        Log.e("AAAA", "Observer onStart")
        if(owner.lifecycle.currentState.isAtLeast(Lifecycle.State.STARTED)){
            //更新UI(这里能够感知到Activity状态为活跃状态)
        }
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_STOP)
    fun onStop(){
        Log.e("AAAA", "Observer onStop")
        //更新UI
    }
}

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        //获取Lifecycle并添加观察者
        lifecycle.addObserver(LocationListener())
    }

    override fun onStart() {
        super.onStart()
        Log.e("AAAAA", "Activity onStart ")
    }

    override fun onStop() {
        super.onStop()
        Log.e("AAAAA", "Activity onStop ")
    }
}

以上代码执行打印结果如下:


image.png

由此可见:观察者中感应Activity生命周期的顺序是:Activity 活跃状态时,Observer观察者感应其生命周期在之后,在Activity非活跃状态时,Observer观察者感应其生命周期在之前(结果摆这呢,后面看源码)。

在上述代码中,Activity生命周期函数中并未对LocationListener组件进行生命周期管理,只是LocationListener实现了LifecycleObserver接口成为观察者,在Activity中将其添加为观察者,LocationListener就有了感知Activity生命周期的能力。这里就解决了之前的问题1。
同时,在LocationListener的onStart方法中传入了LifecycleOwner对象,这个对象能够获得Activity的生命周期状态,即就可以在生命周期非活跃状态下,不执行逻辑,也就解决了之前问题2,不会在onStop之后再去执行onStart中的逻辑了。

这里要讲一下上述代码中, lifecycle.addObserver(LocationListener())中的 lifecycle 这个对象,以及观察者中的注解、方法参数。接下来,我们通过代码解刨学来一点点揭开Lifecycle的神奇之处。

四、揭开Lifecycle神奇的面纱
  1. Lifecycle对象
    在上述例子中,lifecycle对象是通过getLifecycle()方法获取:
//在ComponentActivity中
@NonNull
@Override
public Lifecycle getLifecycle() {
    return mLifecycleRegistry;
}

//在LifecycleOwner接口中定义
public interface LifecycleOwner {
    /**
     * Returns the Lifecycle of the provider.
     *
     * @return The lifecycle of the provider.
     */
    @NonNull
    Lifecycle getLifecycle();
}

首先我们先行了解一下Lifecycle:

public abstract class Lifecycle {
    //添加观察者
    @MainThread
    public abstract void addObserver(@NonNull LifecycleObserver observer);
    //移除观察者
    @MainThread
    public abstract void removeObserver(@NonNull LifecycleObserver observer);
    //获取当前状态
    public abstract State getCurrentState();

    //生命周期事件,对应Activity生命周期方法
    public enum Event {
        ON_CREATE,
        ON_START,
        ON_RESUME,
        ON_PAUSE,
        ON_STOP,
        ON_DESTROY,
        ON_ANY;  //可以响应任意一个事件

        //获取事件对应的状态
        @NonNull
        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");
        }
        //用来查询当前状态之后的事件
        @Nullable
        public static Event upFrom(@NonNull State state) {
            switch (state) {
                case INITIALIZED:
                    return ON_CREATE;
                case CREATED:
                    return ON_START;
                case STARTED:
                    return ON_RESUME;
                default:
                    return null;
            }
        }
        //用来查询当前状态之前的事件
        @Nullable
        public static Event downFrom(@NonNull State state) {
            switch (state) {
                case CREATED:
                    return ON_DESTROY;
                case STARTED:
                    return ON_STOP;
                case RESUMED:
                    return ON_PAUSE;
                default:
                    return null;
            }
        }
    }

    //生命周期状态,这些状态对应着上面的事件
    public enum State {
        DESTROYED,
        INITIALIZED,
        CREATED,
        STARTED,
        RESUMED;

        //判断至少是某一状态
        public boolean isAtLeast(@NonNull State state) {
            return compareTo(state) >= 0;
        }
}   

Lifecycle是一个抽象类,其具体实现是LifecycleRegistry类(这个稍后说),主要有三个方法:添加观察者、移除观察者、获取当前生命周期状态、两个枚举:

  • Event,生命周期事件,这些事件对应Activity/Fragment生命周期方法。
  • State,生命周期状态,某些事件发生前后的状态
    这里借用官网一张图来表示状态和事件之间的关系:
    image.png

    由此可见,Event触发的时机:
  • ON_CREATE、ON_START、ON_RESUME事件,是在生命周期拥有者(LifecycleOwner)对应的方法执行 之后 分发。
  • ON_PAUSE、ON_STOP、ON_DESTROY事件,是在生命周期拥有者(LifecycleOwner)对应的方法调用 之前 分发。

LifecycleOwner是一个接口,getLifecycle方法是接口LifecycleOwner中定义的,LifecycleOwner这个顾名思义:生命周期拥有者,在androidx下的Fragment/Activity都已经实现了这个接口,即androidx下的Activity都是生命周期的拥有者。接下来我们来看看它是如何做到生命周期与Activity同步的。

2、实现LifecycleOwner的Activity
既然LifecycleOwner是一个接口,那必然有实现LifecycleOwner的类,前面也提到过获取Lifecycle对象是通过getLifecycle方法获取的,而getLifecycle实现在ComponentActivity中

//androidx.activity.ComponentActivity
public class ComponentActivity extends androidx.core.app.ComponentActivity implements LifecycleOwner{
    //忽略其他代码,只看Lifecycle相关
    private final LifecycleRegistry mLifecycleRegistry = new LifecycleRegistry(this);
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        ReportFragment.injectIfNeededIn(this); //使用ReportFragment分发生命周期事件
    }
    @CallSuper
    @Override
    protected void onSaveInstanceState(@NonNull Bundle outState) {
        Lifecycle lifecycle = getLifecycle();
        if (lifecycle instanceof LifecycleRegistry) {
            ((LifecycleRegistry) lifecycle).setCurrentState(Lifecycle.State.CREATED);
        }
        super.onSaveInstanceState(outState);
    }

    @NonNull
    @Override
    public Lifecycle getLifecycle() {
        return mLifecycleRegistry;
    }
} 

上面的代码逻辑也比较简单,ComponentActivity实现了LifecycleOwner接口,实现了getLifecycle方法,返回一个LifecycleRegistry对象,而这个类上来就先初始化了一个LifecycleRegistry对象-mLifecycleRegistry。这个对象稍后再说(其实看英文单词也比较简单:生命周期登记处登记表的意思),先看ComponentActivity怎么对生命周期进行分发的。

可以看到onSaveInstanceState方法中通过getLifecycle方法获取了LifecycleRegistry对象,执行了setCurrentState方法,传入Lifecycle.State.CREATED状态,其他的状态怎么没有了?

如果有了解过Glide图片加载框架的人,这里就能很快找到入口(老司机找入口肯定快),没有了解过也没关系,这里告诉你。没错,Lifecycle管理生命周期和Glide类似,也是通过透明无布局的Fragment来进行生命周期管理的(当然Glide更加复杂,在不同线程、传入不同的Context都不大一样)

3、ReportFragment来实现生命周期管理分发
上面说管理,其实这里更应该说是分发事件来实现生命周期同步管理 (这里提个小问题:为什么不直接分发生命周期状态,要分发事件来实现状态同步呢?) ,直接上代码吧:

public class ReportFragment extends Fragment {

    public static void injectIfNeededIn(Activity activity) {
        if (Build.VERSION.SDK_INT >= 29) {
            //在API 29及以上,可以直接注册回调 获取生命周期
            LifecycleCallbacks.registerIn(activity);
        }
        //API29以前,使用fragment 获取生命周期
        android.app.FragmentManager manager = activity.getFragmentManager();
        if (manager.findFragmentByTag(REPORT_FRAGMENT_TAG) == null) {
            manager.beginTransaction().add(new ReportFragment(), REPORT_FRAGMENT_TAG).commit();
            manager.executePendingTransactions();
        }
    }
    //最后不管哪一种方式获取的生命周期,最终分发的方法
    @SuppressWarnings("deprecation")
    static void dispatch(@NonNull Activity activity, @NonNull Lifecycle.Event event) {
        if (activity instanceof LifecycleOwner) {
            Lifecycle lifecycle = ((LifecycleOwner) activity).getLifecycle();
            if (lifecycle instanceof LifecycleRegistry) {
                ((LifecycleRegistry) lifecycle).handleLifecycleEvent(event);//使用LifecycleRegistry的handleLifecycleEvent方法处理事件
            }
        }
    }

    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        //分发ON_CREATE事件
        dispatch(Lifecycle.Event.ON_CREATE);
    }
    @Override
    public void onStart() {
        super.onStart();
        //分发ON_START事件
        dispatch(Lifecycle.Event.ON_START);
    }
    //...省略onResume、onPause、onStop、onDestroy

    private void dispatch(@NonNull Lifecycle.Event event) {
        if (Build.VERSION.SDK_INT < 29) {
            dispatch(getActivity(), event);
        }
    }

    //在API 29及以上,使用的生命周期回调
    static class LifecycleCallbacks implements Application.ActivityLifecycleCallbacks {

        static void registerIn(Activity activity) {
            activity.registerActivityLifecycleCallbacks(new LifecycleCallbacks());
        }

        @Override
        public void onActivityPostCreated(@NonNull Activity activity,@Nullable Bundle savedInstanceState) {
            dispatch(activity, Lifecycle.Event.ON_CREATE);
        }

        @Override
        public void onActivityPostStarted(@NonNull Activity activity) {
            dispatch(activity, Lifecycle.Event.ON_START);
        }
    
        //省略onResume、onPause、onStop、onDestroy
    }
}

injectIfNeededIn传入activity对象,对应不同版本,用它来获取FragmentManager或者注册ActivityLifecycleCallbacks来获取生命周期,不管哪一种方式,最终都走到dispatch(@NonNull Activity activity, @NonNull Lifecycle.Event event)方法,这个方法中通过getLifecycle方法获取LifecycleRegistry对象,调用LifecycleRegistry对象中的handleLifecycleEvent方法进行事件分发。

到这里,生命周期事件分发就结束了,也就是说每个生命周期事件都分发出去了,交给了LifecycleRegistry这个类对象来处理。

4、Lifecycle具体实现LifecycleRegistry
LifecycleRegistry初始化在ComponentActivity中,传入了一个LifecycleOwner对象

private LifecycleRegistry(@NonNull LifecycleOwner provider, boolean enforceMainThread) {
    //弱引用
    mLifecycleOwner = new WeakReference<>(provider);
    //默认状态为初始化
    mState = INITIALIZED;
    //是否执行在主线程
    mEnforceMainThread = enforceMainThread;
}

这里需要特别关注的就是这个 弱引用 ,因为Activity/Fragment实现了LifecycleOwner接口(生命周期拥有者),LifecycleOwner对象持有了Activity/Fragment的引用,使用弱引用可以在Activity/Fragment销毁的时候,回收LifecycleOwner对象,从而不会造成Activity/Fragment的内存泄漏,并且在后续过程中,通过get方法来判断LifecycleOwner对象是否为空来进行分发拦截,如果为空表明Activity/Fragment(被观察者)已经销毁被回收了。

上面ReportFragment分发最后执行方法:handleLifecycleEvent(),通过代码看看是如何处理分发的那些事件的:

    /**
     * 设置当前状态并通知观察者。
     * 请注意,如果currentState与上次调用此方法的状态相同,则调用此方法无效。
     */
    public void handleLifecycleEvent(@NonNull Lifecycle.Event event) {
        enforceMainThreadIfNeeded("handleLifecycleEvent");//执行线程判断,无关紧要
        //getTargetState()方法获取事件对应的状态,定义在Lifecycle.Event枚举类中
        moveToState(event.getTargetState());    
    }

    //移到下一个状态
    private void moveToState(State next) {
        if (mState == next) {//状态相同不处理
            return;
        }
        mState = next;    //赋值新状态
        if (mHandlingEvent || mAddingObserverCounter != 0) {
            mNewEventOccurred = true;
            // 事件正在处理中或者有新的观察者加入时,不进行后续处理
            return;
        }
        mHandlingEvent = true;
        sync();//把生命周期状态mState同步给所有观察者
        mHandlingEvent = false;
    }

上面分发处理的事件的方法中,通过event.getTargetState()方法获取了事件对应的状态,通过moveToState 方法进行处理。当要同步的状态与当前状态相同时不处理,当事件正在处理中或有新的观察者加入时,也不处理,那怎么有新的观察者加入了就不处理了算是怎么回事??我们看看mAddingObserverCounter这个变量的值,发现在addObserver方法中有过改变


    public void addObserver(@NonNull LifecycleObserver observer) {
        enforceMainThreadIfNeeded("addObserver");
        //初始状态
        State initialState = mState == DESTROYED ? DESTROYED : INITIALIZED;
        //有状态的观察者
        ObserverWithState statefulObserver = new ObserverWithState(observer, initialState);
        //将有状态的观察者存入mObserverMap这个map中
        ObserverWithState previous = mObserverMap.putIfAbsent(observer, statefulObserver);

        if (previous != null) {
            return;
        }
        LifecycleOwner lifecycleOwner = mLifecycleOwner.get();
        if (lifecycleOwner == null) {
            // 和前面同样的,如果销毁了就不分发处理了
            return;
        }

        boolean isReentrance = mAddingObserverCounter != 0 || mHandlingEvent;
        //根据观察者获取目标状态
        State targetState = calculateTargetState(observer);
        mAddingObserverCounter++;
        //将观察者状态同步至最新状态mState
        while ((statefulObserver.mState.compareTo(targetState) < 0
                && mObserverMap.contains(observer))) {
            pushParentState(statefulObserver.mState);
            //upFrom方法是在Lifecycle.Event枚举中定义的方法,用来查询当前状态之后的事件
            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--;
    }

通过以上两段代码发现,不管是在添加观察者还是生命周期变化进行同步分事件的情况,最终两者之间都有其一会执行sync();方法去将当前状态同步给所有观察者。


    private void sync() {
        LifecycleOwner lifecycleOwner = mLifecycleOwner.get();
        //观察者是否回收...
        if (lifecycleOwner == null) {
            throw new IllegalStateException("LifecycleOwner of this LifecycleRegistry is already"
                    + "garbage collected. It is too late to change lifecycle state.");
        }
        //isSynced是否同步完成,遍历所有的观察者
        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;
    }

循环条件是!isSynced(),若最老的和最新的观察者的状态一致,且都是ower的当前状态,说明已经同步完了,退出循环同步。
循环体中,通过两个判断

  • 当前状态比最老观察者状态小,向后同步状态
  • 当前状态比最新观察者状态大,向前同步状态
    即以上,不管哪个状态下添加的观察者都可以得到所有状态的同步,可以做以下实验:

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        lifecycle.addObserver(LocationListener())

    }

    override fun onStart() {
        super.onStart()
    }

    override fun onResume() {
        super.onResume()
        //添加新的观察者
        lifecycle.addObserver(LocationListener2())
    }

}


class LocationListener: LifecycleObserver {
    @OnLifecycleEvent(value = Lifecycle.Event.ON_CREATE)
    fun onCreate(){
        Log.e("AAAA", "Observer onCreate")
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_START)
    fun onStart(owner: LifecycleOwner){
        Log.e("AAAA", "Observer onStart")
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_RESUME)
    fun onResume(){
        Log.e("AAAA", "Observer onResume")
    }

}

class LocationListener2: LifecycleObserver {
    @OnLifecycleEvent(value = Lifecycle.Event.ON_CREATE)
    fun onCreate(){
        Log.e("AAAABB", "Observer onCreate")
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_START)
    fun onStart(owner: LifecycleOwner){
        Log.e("AAAABB", "Observer onStart")
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_RESUME)
    fun onResume(){
        Log.e("AAAABB", "Observer onResume")
    }

}

以上,在MainActivity的onCreate方法中添加一个LocationListener观察者,在onResume中添加LocationListener2观察者,执行结果:

image.png

即, 不管多晚添加的观察者都会一一进行同步所有状态。 我们回到源码中的forwardPass()、backwardPass()这两个方法,这两个方法其实类似,来看一个:


    private void forwardPass(LifecycleOwner lifecycleOwner) {
        Iterator<Map.Entry<LifecycleObserver, ObserverWithState>> ascendingIterator =
                mObserverMap.iteratorWithAdditions();
        while (ascendingIterator.hasNext() && !mNewEventOccurred) {
            Map.Entry<LifecycleObserver, ObserverWithState> entry = ascendingIterator.next();
            ObserverWithState observer = entry.getValue();
            while ((observer.mState.compareTo(mState) < 0 && !mNewEventOccurred
                    && mObserverMap.contains(entry.getKey()))) {
                pushParentState(observer.mState);
                final Event event = Event.upFrom(observer.mState);
                if (event == null) {
                    throw new IllegalStateException("no event up from " + observer.mState);
                }
                //循环同步获取每个状态的事件,最后交给observer的dispatchEvent进行分发处理
                observer.dispatchEvent(lifecycleOwner, event);
                popParentState();
            }
        }
    }

其实不管是backwoardPass还是forwardPass方法(只是获取的状态对应的事件不同),最后都是通过observer.dispatchEvent(lifecycleOwner, event);进行分发处理。补充一点:observer对象是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();
            //当前状态,是LifecycleRegistry的全局变量,用来控制状态是否分发过了
            mState = min(mState, newState);
            //状态分发回调(平时说到回调的话,是不是就像接口一样的,要回调到我们自己的方法了???)
            mLifecycleObserver.onStateChanged(owner, event);
            mState = newState;
        }
    }

这里读到onStateChanged方法,onXXX方法在平时是不是很常见也很常写,就是回调或者自己要写接口回调时候的规范嘛。那看看LifecycleEventObserver它是个啥?

public interface LifecycleEventObserver extends LifecycleObserver {
    /**
     * 当事件状态发生变化时回调
     *
     * @param source 事件来源(生命周期拥有者)
     * @param event 事件
     */
    void onStateChanged(@NonNull LifecycleOwner source, @NonNull Lifecycle.Event event);
}

没错,LifecycleEventObserver就是一个接口,onStateChanged方法必定有实现的地方,mLifecycleObserver.onStateChanged中的mLifecycleObserver这个对象是通过Lifecycling.lifecycleEventObserver(observer);方法得到的:


    @NonNull
    static LifecycleEventObserver lifecycleEventObserver(Object object) {
        //这一段其实不用管了,我们传入的是LifecycleObserver类型的
        boolean isLifecycleEventObserver = object instanceof LifecycleEventObserver;
        boolean isFullLifecycleObserver = object instanceof FullLifecycleObserver;
        if (isLifecycleEventObserver && isFullLifecycleObserver) {
            return new FullLifecycleObserverAdapter((FullLifecycleObserver) object,
                    (LifecycleEventObserver) object);
        }
        if (isFullLifecycleObserver) {
            return new FullLifecycleObserverAdapter((FullLifecycleObserver) object, null);
        }

        if (isLifecycleEventObserver) {
            return (LifecycleEventObserver) object;
        }
        //这里去获取观察者的构造函数类型
        final Class<?> klass = object.getClass();
        int type = getObserverConstructorType(klass);
        //type返回的其实是REFLECTIVE_CALLBACK:反射回调
        if (type == GENERATED_CALLBACK) {
            List<Constructor<? extends GeneratedAdapter>> constructors =
                    sClassToAdapters.get(klass);
            if (constructors.size() == 1) {
                GeneratedAdapter generatedAdapter = createGeneratedAdapter(
                        constructors.get(0), object);
                return new SingleGeneratedAdapterObserver(generatedAdapter);
            }
            GeneratedAdapter[] adapters = new GeneratedAdapter[constructors.size()];
            for (int i = 0; i < constructors.size(); i++) {
                adapters[i] = createGeneratedAdapter(constructors.get(i), object);
            }
            return new CompositeGeneratedAdaptersObserver(adapters);
        }
        //最终LifecycleEventObserver的实现类是它
        return new ReflectiveGenericLifecycleObserver(object);
    }

Lifecycling.lifecycleEventObserver(observer)方法中,先做了一个观察者类型判断,之后通过判断观察者构造函数类型,最终我们需要关注的其实是ReflectiveGenericLifecycleObserver这个实现类:


class ReflectiveGenericLifecycleObserver implements LifecycleEventObserver {
    private final Object mWrapped;    //观察者
    private final CallbackInfo mInfo;    //观察者的回调信息

    ReflectiveGenericLifecycleObserver(Object wrapped) {
        mWrapped = wrapped;
        mInfo = ClassesInfoCache.sInstance.getInfo(mWrapped.getClass());
    }

    @Override
    public void onStateChanged(@NonNull LifecycleOwner source, @NonNull Event event) {
        //执行回调方法(实际上就是观察者中注解的方法)
        mInfo.invokeCallbacks(source, event, mWrapped);
    }
}

在ReflectiveGenericLifecycleObserver的构造函数中,通过单例获取到一个ClassesInfoCache对象,通过ClassesInfoCache对象获取一个CallbackInfo对象,之后在onStateChanged方法执行观察者的回调。


final class ClassesInfoCache {
    //恶汉式单例获取ClassesInfoCache对象,且是一种终态类型。
    static ClassesInfoCache sInstance = new ClassesInfoCache();
    //存储所有观察者的CallbackInfo信息
    private final Map<Class<?>, CallbackInfo> mCallbackMap = new HashMap<>();
    //通过反射获取观察者类方法信息
    private Method[] getDeclaredMethods(Class<?> klass) {
        try {
            return klass.getDeclaredMethods();
        } catch (NoClassDefFoundError e) {
            throw new IllegalArgumentException("The observer class has some methods that use "
                    + "newer APIs which are not available in the current OS version. Lifecycles "
                    + "cannot access even other methods so you should make sure that your "
                    + "observer classes only access framework classes that are available "
                    + "in your min API level OR use lifecycle:compiler annotation processor.", e);
        }
    }

    CallbackInfo getInfo(Class<?> klass) {
        //mCallbackMap存储了所有观察者类信息
        CallbackInfo existing = mCallbackMap.get(klass);
        if (existing != null) {
            return existing;
        }
        existing = createInfo(klass, null);
        return existing;
    }

    private CallbackInfo createInfo(Class<?> klass, @Nullable Method[] declaredMethods) {
        //通过反射获取观察者中的所有方法
        Method[] methods = declaredMethods != null ? declaredMethods : getDeclaredMethods(klass);
        boolean hasLifecycleMethods = false;
        for (Method method : methods) {
            //获取方法注解,如果没有注解的就不处理了
            OnLifecycleEvent annotation = method.getAnnotation(OnLifecycleEvent.class);
            if (annotation == null) {
                continue;
            }
            hasLifecycleMethods = true;
            //获取方法参数
            Class<?>[] params = method.getParameterTypes();
            int callType = CALL_TYPE_NO_ARG;
            if (params.length > 0) {
                //如果参数个数 > 0,第一个参数必须是LifecycleOwner
                callType = CALL_TYPE_PROVIDER;
                if (!params[0].isAssignableFrom(LifecycleOwner.class)) {
                    throw new IllegalArgumentException(
                            "invalid parameter type. Must be one and instanceof LifecycleOwner");
                }
            }
            Lifecycle.Event event = annotation.value();

            if (params.length > 1) {
                //如果有两个参数的,第二个参数必须是Event,且注解值只能是ON_ANY
                callType = CALL_TYPE_PROVIDER_WITH_EVENT;
                if (!params[1].isAssignableFrom(Lifecycle.Event.class)) {
                    throw new IllegalArgumentException(
                            "invalid parameter type. second arg must be an event");
                }
                if (event != Lifecycle.Event.ON_ANY) {
                    throw new IllegalArgumentException(
                            "Second arg is supported only for ON_ANY value");
                }
            }
            if (params.length > 2) {
                //参数不能超过两个
                throw new IllegalArgumentException("cannot have more than 2 params");
            }
            MethodReference methodReference = new MethodReference(callType, method);
            verifyAndPutHandler(handlerToEvent, methodReference, event, klass);
        }
        //存储观察者类信息
        CallbackInfo info = new CallbackInfo(handlerToEvent);
        mCallbackMap.put(klass, info);
        mHasLifecycleMethods.put(klass, hasLifecycleMethods);
        return info;
    }
}

ClassesInfoCache其实就是用来缓存观察类信息的,通过 反射 来获取观察者类信息(CallbackInfo),然后存储到一个HashMap中。在createInfo方法中,需要注意的是:
观察者中的注解方法可以无参数、有参数(一个参数和两个参数,一个参数必须是LifecycleOwner,两个参数,第二个参数必须是Lifecycle.Event且两个参数的情况,注解值必须是ON_ANY)
即:


    @OnLifecycleEvent(value = Lifecycle.Event.ON_CREATE)
    fun onCreate(){
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_START)
    fun onStart(owner: LifecycleOwner){
    }

    @OnLifecycleEvent(value = Lifecycle.Event.ON_ANY)
    fun onAny(owner: LifecycleOwner, event:Lifecycle.Event){
    }

回过头来看mInfo.invokeCallbacks(source, event, mWrapped);


    @SuppressWarnings("WeakerAccess")
    static class CallbackInfo {
        //Event对应的多个方法
        final Map<Lifecycle.Event, List<MethodReference>> mEventToHandlers;
        //要回调的方法
        final Map<MethodReference, Lifecycle.Event> mHandlerToEvent;
        //createInfo方法中最后有一个CallbackInfo构造方法,存储了Event对应的执行方法及要回调的方法
        CallbackInfo(Map<MethodReference, Lifecycle.Event> handlerToEvent) {
            mHandlerToEvent = handlerToEvent;
            mEventToHandlers = new HashMap<>();
            for (Map.Entry<MethodReference, Lifecycle.Event> entry : handlerToEvent.entrySet()) {
                Lifecycle.Event event = entry.getValue();
                List<MethodReference> methodReferences = mEventToHandlers.get(event);
                if (methodReferences == null) {
                    methodReferences = new ArrayList<>();
                    mEventToHandlers.put(event, methodReferences);
                }
                methodReferences.add(entry.getKey());
            }
        }

        @SuppressWarnings("ConstantConditions")
        void invokeCallbacks(LifecycleOwner source, Lifecycle.Event event, Object target) {
            //分发对应的事件
            invokeMethodsForEvent(mEventToHandlers.get(event), source, event, target);
            //不管哪一个事件,都会执行ON_ANY注解的方法
            invokeMethodsForEvent(mEventToHandlers.get(Lifecycle.Event.ON_ANY), source, event,
                    target);
        }

        private static void invokeMethodsForEvent(List<MethodReference> handlers,
                LifecycleOwner source, Lifecycle.Event event, Object mWrapped) {
            if (handlers != null) {
                for (int i = handlers.size() - 1; i >= 0; i--) {
                    //handlers.get方法就是获取的MethodReference对象
                    handlers.get(i).invokeCallback(source, event, mWrapped);
                }
            }
        }
    }

通过CallbackInfo中的invokeCallbacks方法可知,不管是哪一个事件,最终都会进行ON_ANY注解方法的分发,也就是说 如果观察者中有ON_ANY注解的方法,任何一个状态事件变化都会分发给ON_ANY注解方法

    @SuppressWarnings("WeakerAccess")
    static final class MethodReference {
        void invokeCallback(LifecycleOwner source, Lifecycle.Event event, Object target) {
            try {
                switch (mCallType) {
                    case CALL_TYPE_NO_ARG:
                        //没有参数的方法
                        mMethod.invoke(target);
                        break;
                    case CALL_TYPE_PROVIDER:
                        //一个参数的方法(参数必须是LifecycleOwner)
                        mMethod.invoke(target, source);
                        break;
                    case CALL_TYPE_PROVIDER_WITH_EVENT:
                        //两个参数的方法(LifecycleOwner,Event)
                        mMethod.invoke(target, source, event);
                        break;
                }
            } catch (InvocationTargetException e) {
                throw new RuntimeException("Failed to call observer method", e.getCause());
            } catch (IllegalAccessException e) {
                throw new RuntimeException(e);
            }
        }
    }

最后就是根据不同参数类型,通过反射执行对应方法。

这篇文章到这里也就差不多结束了,Lifecycle整个流程分析也就到这里了,再做一个总结:
Lifecycle能够做到生命周期同步整个过程:

  • 1、在ComponentActivity中,通过ReportFragment.injectIfNeededIn(this);方法将生命周期管理交给ReportFragment
  • 2、ReportFragment是一个没有任何视图只为了获取生命周期的,这样做的目的就是减少在Activity做生命周期管理,减少Activity的负担。类似Glide生命周期管理一样。通过handleLifecycleEvent方法将事件分发交给LifecycleRegistry对象
  • 3、LifecycleRegistry类持有的LifecycleOwner对象是弱引用的方式的,这就防止出现内存泄漏。通过sync方法循环遍历所有观察者,对每个观察者进行所有状态一一同步,最后通过dispatchEvent将事件交给ObserverWithState处理。
  • 4、ObserverWithState中通过调用LifecycleEventObserver的实现类ReflectiveGenericLifecycleObserver中的onStateChanged方法进行分发
  • 5、在ReflectiveGenericLifecycleObserver中,通过单例模式获取ClassesInfoCache对象,ClassesInfoCache中又通过反射的方式获取观察者的类信息方法信息注解信息等等存储到CallbackInfo中,再通过CallbackInfo的invokeCallbacks方法进行分发
  • 6、CallbackInfo中通过其存储的MethodReference类,最后交给MethodReference对象的invokeCallback方法进行分发处理,通过反射根据不同参数类型执行不同的观察者方法。

这里最后我们还需要知道,通过了解Lifecycle原理,我们知道其中除了逻辑,我们更需要去了解它为什么不会有内存泄漏的问题(即Java中的对象引用),还有用了注解知识,反射知识等等

断断续续的写了这么一篇文章终于是写完了,下一篇文章将对以上几个知识点进行一个补充,学习过程需要循序渐进!

最后分享最近特别喜欢的一句话:不与人相比,但愿超越自己!

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 151,829评论 1 331
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 64,603评论 1 273
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 101,846评论 0 226
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 42,600评论 0 191
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 50,780评论 3 272
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 39,695评论 1 192
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,136评论 2 293
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 29,862评论 0 182
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 33,453评论 0 229
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 29,942评论 2 233
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 31,347评论 1 242
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 27,790评论 2 236
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 32,293评论 3 221
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 25,839评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,448评论 0 181
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 34,564评论 2 249
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 34,623评论 2 249

推荐阅读更多精彩内容