Lifecycle的基本使用与原理解析

Lifecycle使用了观察者设计模式,Activity与Fragment这种具有生命周期的页面是被观察者,通过LifecycleObserver来观察生命周期。另外事件与状态的比变化是通过状态机实现的,文末有图总结该方式以及为什么这么设计?

Lifecycle的基本使用

首先需要定义一个LifecycleObserver:

less 复制代码
class MyLocationListener : LifecycleObserver {

    @OnLifecycleEvent(Lifecycle.Event.ON_CREATE)
    fun create() = Log.d("zxc", "create 正在启动系统定位服务中...")

    @OnLifecycleEvent(Lifecycle.Event.ON_START)
    fun start() = Log.d("zxc", "start 连接系统定位服务...")

    @OnLifecycleEvent(Lifecycle.Event.ON_RESUME)
    fun resume() = Log.d("zxc", "resume 系统定位的界面展示...")

    @OnLifecycleEvent(Lifecycle.Event.ON_PAUSE)
    fun pause() = Log.d("zxc", "pause 系统定位的界面关闭...")

    @OnLifecycleEvent(Lifecycle.Event.ON_STOP)
    fun stop() = Log.d("zxc", "stop 断开系统定位服务...")

    @OnLifecycleEvent(Lifecycle.Event.ON_DESTROY)
    fun destroy() = Log.d("zxc", "destroy 正在停止系统定位服务...")
}

然后在Activity中注册他就可以了:

kotlin 复制代码
override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    // 观察者 == MyLocationListener
    // 1.主线流程,支线流程不管(防止淹死源码)
    // 2.支线流程
    lifecycle.addObserver(MyLocationListener())
}

能这样使用的原因是Activity实现了LifecycleObserver接口。

或者也可以这样使用Lifecycle:

kotlin 复制代码
class MyObserver2 : DefaultLifecycleObserver {

    private val TAG = "MyObserver2"

    override fun onCreate(owner: LifecycleOwner) {
        super.onCreate(owner)
        Log.d(TAG,"onCreate run ...")
    }

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

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

DefaultLifecycleObserver 就是对 LifecycleObserver 二次封装 为了用户好用

另外,使用注解的方式也是可以的:

kotlin 复制代码
class MyObserver : LifecycleObserver {

    private val TAG = "MyObserver"

    @OnLifecycleEvent(Lifecycle.Event.ON_RESUME) // 画面可见 就连接
    fun connectListener() = Log.d(TAG,"connectListener run ...")

    @OnLifecycleEvent(Lifecycle.Event.ON_PAUSE)  // 画面不可见 就断开连接
    fun disconnectListener() = Log.d(TAG,"disconnectListener run ...")

}

但是这种方式有个问题,就是无法拿到当前运行的context,所以Lifecycle的写法有3种。

注册方式都可以通过lifecycle.addObserver(MyObserver())就可以了。

Lifecycle的原理分析:

Lifecycle使用的整体结构:

Activity作为被观察者,实现了LifecycleObserver的类作为观察者,在被观察者中通过添加Observer的方式,完成观察者的注册,然后当Activity生命周期发生变化的时候,这个被观察者就会将自己的状态分发给自己的观察者。

远吗分析,我们需要找一个切入点,对于Lifecycle,最好的切入点就是addObserver

addObserver流程分析:

less 复制代码
lifecycle.addObserver(MyLocationListener())

接着进入了

这是一个抽象方法,我们需要去找到他的实现:

kotlin 复制代码
public void addObserver(@NonNull LifecycleObserver observer) {
    // 这里源码很多,与我们的主线流程很多关系不大,我们要紧盯着observer不放,看他是怎么进行的。
    Lifecycle.State initialState = this.mState == State.DESTROYED ? State.DESTROYED : State.INITIALIZED;
    // ObserverWithState(observer, initialState)进入看看这里的源码,这段代码会对Observer进行解析
    ObserverWithState statefulObserver = new ObserverWithState(observer, initialState);
    ObserverWithState previous = (ObserverWithState)this.mObserverMap.putIfAbsent(observer, statefulObserver);
    if (previous == null) {
        LifecycleOwner lifecycleOwner = (LifecycleOwner)this.mLifecycleOwner.get();
        if (lifecycleOwner != null) {
            boolean isReentrance = this.mAddingObserverCounter != 0 || this.mHandlingEvent;
            Lifecycle.State targetState = this.calculateTargetState(observer);
            ++this.mAddingObserverCounter;

            while(statefulObserver.mState.compareTo(targetState) < 0 && this.mObserverMap.contains(observer)) {
                this.pushParentState(statefulObserver.mState);
                statefulObserver.dispatchEvent(lifecycleOwner, upEvent(statefulObserver.mState));
                this.popParentState();
                targetState = this.calculateTargetState(observer);
            }

            if (!isReentrance) {
                this.sync();
            }

            --this.mAddingObserverCounter;
        }
    }
}

进入:androidx.lifecycle.LifecycleRegistry.ObserverWithState,ObserverWithState是LifecycleRegistry的一个内部类。

ini 复制代码
static class ObserverWithState {
    Lifecycle.State mState;
    LifecycleEventObserver mLifecycleObserver;

    ObserverWithState(LifecycleObserver observer, Lifecycle.State initialState) {
        // observer 注册:
        this.mLifecycleObserver = Lifecycling.lifecycleEventObserver(observer);
        this.mState = initialState;
    }
    // 省略无关代码
}

后边会来到这里:

typescript 复制代码
static LifecycleEventObserver lifecycleEventObserver(Object object) {
    // 省略无关代码
    return new ReflectiveGenericLifecycleObserver(object);
}

在ReflectiveGenericLifecycleObserver里边,

less 复制代码
class ReflectiveGenericLifecycleObserver implements LifecycleEventObserver {
    private final Object mWrapped;
    private final CallbackInfo mInfo;
    // wrapped就是我们的observer.
    ReflectiveGenericLifecycleObserver(Object wrapped) {
        mWrapped = wrapped;
        // z这里为什么要获取class?因为后边需要使用反射来对observer的每一个方法进行解析。
        mInfo = ClassesInfoCache.sInstance.getInfo(mWrapped.getClass());
    }

    @Override
    public void onStateChanged(@NonNull LifecycleOwner source, @NonNull Event event) {
        mInfo.invokeCallbacks(source, event, mWrapped);
    }
}

这些就是要解析的东西。

getInfo的详细实现在这里:

js 复制代码
CallbackInfo getInfo(Class<?> klass) {
    // 为什么使用map,因为反射一般都会消耗性能,这里是出于提高一点点性能的考虑。而且framework中也存在大量的map用来提升性能。
    CallbackInfo existing = mCallbackMap.get(klass);
    if (existing != null) {
        return existing;
    }
    existing = createInfo(klass, null);
    return existing;
}

createInfo的详细实现,核心逻辑用来处理带有OnLifecycleEvent的注解方法,这里边是通过反射来处理的。

js 复制代码
private CallbackInfo createInfo(Class<?> klass, @Nullable Method[] declaredMethods) {
    Class<?> superclass = klass.getSuperclass();
    Map<MethodReference, Lifecycle.Event> handlerToEvent = new HashMap<>();
    if (superclass != null) {
        CallbackInfo superInfo = getInfo(superclass);
        if (superInfo != null) {
            handlerToEvent.putAll(superInfo.mHandlerToEvent);
        }
    }

    Class<?>[] interfaces = klass.getInterfaces();
    for (Class<?> intrfc : interfaces) {
        for (Map.Entry<MethodReference, Lifecycle.Event> entry : getInfo(
                intrfc).mHandlerToEvent.entrySet()) {
            verifyAndPutHandler(handlerToEvent, entry.getKey(), entry.getValue(), klass);
        }
    }

    Method[] methods = declaredMethods != null ? declaredMethods : getDeclaredMethods(klass);
    boolean hasLifecycleMethods = false;
    // 遍历所有的方法,解析observer中的方法的注解,只要有@OnLifecycleEvent,都需要处理并保存。
    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) {
            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) {
            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);
    // 将所有的方法存储到map中,用来提升一点点性能。
    mCallbackMap.put(klass, info);
    mHasLifecycleMethods.put(klass, hasLifecycleMethods);
    return info;
}

被观察者如何将状态分发给观察者流程分析:

所有的处理最终都会到ComponentActivity,该类实现了LifecycleObserver接口。

先看看他的onCreate方法:

typescript 复制代码
protected void onCreate(@Nullable Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    this.mSavedStateRegistryController.performRestore(savedInstanceState);
    ReportFragment.injectIfNeededIn(this);
    if (this.mContentLayoutId != 0) {
        this.setContentView(this.mContentLayoutId);
    }
}

public static void injectIfNeededIn(Activity activity) {
    if (VERSION.SDK_INT >= 29) {
        activity.registerActivityLifecycleCallbacks(new LifecycleCallbacks());
    }
    
    // 生成一个空白的Fragment(ReportFragment)黏贴到用户界面上来。
    FragmentManager manager = activity.getFragmentManager();
    if (manager.findFragmentByTag("androidx.lifecycle.LifecycleDispatcher.report_fragment_tag") == null) {
        manager.beginTransaction().add(new ReportFragment(), "androidx.lifecycle.LifecycleDispatcher.report_fragment_tag").commit();
        manager.executePendingTransactions();
    }
}

其实从这里来看,似乎代码写在Activity中也可以,为什么没有呢?这是以为Google考虑的是,你继承AppCompatActivity 可以,你继承 XXXXActivity 也可以。Fragment是可以放在任何Activity中。就是可以在任何Activity中都可以使用这个Lifecycle。

这里顺便提一下Fragement的生命周期与Activity生命周期的交互:

可以看到Activity先于Fragment创建而创建,后语Fragment的销毁而销毁。

生命周期事件的分发

首先将一些重要的状态列举出来:

事件驱动状态,Lifecycle的设计核心原理之一。

生命周期的留个枚举,也就是6个事件,对应了6个生命周期回调函数:

php 复制代码
public enum Event {
    /**
     * Constant for onCreate event of the {@link LifecycleOwner}.
     */
    ON_CREATE,
    /**
     * Constant for onStart event of the {@link LifecycleOwner}.
     */
    ON_START,
    /**
     * Constant for onResume event of the {@link LifecycleOwner}.
     */
    ON_RESUME,
    /**
     * Constant for onPause event of the {@link LifecycleOwner}.
     */
    ON_PAUSE,
    /**
     * Constant for onStop event of the {@link LifecycleOwner}.
     */
    ON_STOP,
    /**
     * Constant for onDestroy event of the {@link LifecycleOwner}.
     */
    ON_DESTROY,
    /**
     * An {@link Event Event} constant that can be used to match all events.
     */
    ON_ANY
}

这里是状态,状态通过上边的事件驱动。

php 复制代码
public enum State {
    /**
     * Destroyed state for a LifecycleOwner. After this event, this Lifecycle will not dispatch
     * any more events. For instance, for an {@link android.app.Activity}, this state is reached
     * <b>right before</b> Activity's {@link android.app.Activity#onDestroy() onDestroy} call.
     */
    DESTROYED,

    /**
     * Initialized state for a LifecycleOwner. For an {@link android.app.Activity}, this is
     * the state when it is constructed but has not received
     * {@link android.app.Activity#onCreate(android.os.Bundle) onCreate} yet.
     */
    INITIALIZED,

    /**
     * Created state for a LifecycleOwner. For an {@link android.app.Activity}, this state
     * is reached in two cases:
     * <ul>
     *     <li>after {@link android.app.Activity#onCreate(android.os.Bundle) onCreate} call;
     *     <li><b>right before</b> {@link android.app.Activity#onStop() onStop} call.
     * </ul>
     */
    CREATED,

    /**
     * Started state for a LifecycleOwner. For an {@link android.app.Activity}, this state
     * is reached in two cases:
     * <ul>
     *     <li>after {@link android.app.Activity#onStart() onStart} call;
     *     <li><b>right before</b> {@link android.app.Activity#onPause() onPause} call.
     * </ul>
     */
    STARTED,

    /**
     * Resumed state for a LifecycleOwner. For an {@link android.app.Activity}, this state
     * is reached after {@link android.app.Activity#onResume() onResume} is called.
     */
    RESUMED;

    /**
     * Compares if this State is greater or equal to the given {@code state}.
     *
     * @param state State to compare with
     * @return true if this State is greater or equal to the given {@code state}
     */
    public boolean isAtLeast(@NonNull State state) {
        return compareTo(state) >= 0;
    }
}

在ReportFragment进行事件的分发:

less 复制代码
static void dispatch(@NonNull Activity activity, @NonNull Lifecycle.Event event) {
    if (activity instanceof LifecycleRegistryOwner) {
        // 处理事件分发,这里就涉及到状态机了,这也是Lifecycle设计的核心原理。
        ((LifecycleRegistryOwner)activity).getLifecycle().handleLifecycleEvent(event);
    } else {
        if (activity instanceof LifecycleOwner) {
            Lifecycle lifecycle = ((LifecycleOwner)activity).getLifecycle();
            if (lifecycle instanceof LifecycleRegistry) {
                ((LifecycleRegistry)lifecycle).handleLifecycleEvent(event);
            }
        }

    }
}
```js
public void handleLifecycleEvent(@NonNull Lifecycle.Event event) {
    // 通过事件得到状态
    Lifecycle.State next = getStateAfter(event);
    // 状态对齐,就是让被观察者的状态变成与观察者一样的状态。
    this.moveToState(next);
}

事件驱动状态的转化函数:

csharp 复制代码
static Lifecycle.State getStateAfter(Lifecycle.Event event) {
    switch (event) {
        // 前进状态
        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:
        default:
            throw new IllegalArgumentException("Unexpected event value " + event);
    }
}

状态机进行状态转化:

js 复制代码
private void moveToState(Lifecycle.State next) {
    if (this.mState != next) {
        this.mState = next;
        if (!this.mHandlingEvent && this.mAddingObserverCounter == 0) {
            this.mHandlingEvent = true;
            this.sync();
            this.mHandlingEvent = false;
        } else {
            this.mNewEventOccurred = true;
        }
    }
}
js 复制代码
private void sync() {
    LifecycleOwner lifecycleOwner = (LifecycleOwner)this.mLifecycleOwner.get();
    if (lifecycleOwner == null) {
        throw new IllegalStateException("LifecycleOwner of this LifecycleRegistry is alreadygarbage collected. It is too late to change lifecycle state.");
    } else {
        while(!this.isSynced()) {
            this.mNewEventOccurred = false;
            // 通过枚举的大小来判断当前观察者的状态应该是前进还是后退
            if (this.mState.compareTo(((ObserverWithState)this.mObserverMap.eldest().getValue()).mState) < 0) {
                this.backwardPass(lifecycleOwner);
            }

            Map.Entry<LifecycleObserver, ObserverWithState> newest = this.mObserverMap.newest();
            if (!this.mNewEventOccurred && newest != null && this.mState.compareTo(((ObserverWithState)newest.getValue()).mState) > 0) {
                this.forwardPass(lifecycleOwner);
            }
        }

        this.mNewEventOccurred = false;
    }
}

// 倒退的过程中,我们对齐状态后,需要根据当前的状态获取事件,然后才能回调对应的生命周期函数。同理的前进也是一样的逻辑。
private static Lifecycle.Event downEvent(Lifecycle.State state) {
    switch (state) {
        case INITIALIZED:
            throw new IllegalArgumentException();
        case CREATED:
            return Event.ON_DESTROY;
        case STARTED:
            return Event.ON_STOP;
        case RESUMED:
            return Event.ON_PAUSE;
        case DESTROYED:
            throw new IllegalArgumentException();
        default:
            throw new IllegalArgumentException("Unexpected state value " + state);
    }
}

之后在通过androidx.lifecycle.ReflectiveGenericLifecycleObserver#onStateChanged进行事件的处理

csharp 复制代码
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(i).invokeCallback(source, event, mWrapped);
        }
    }
}

void invokeCallback(LifecycleOwner source, Lifecycle.Event event, Object target) {
    //noinspection TryWithIdenticalCatches
    try {
        switch (mCallType) {
            case CALL_TYPE_NO_ARG:
                // 通过反射完成生命周期的回调。
                mMethod.invoke(target);
                break;
            case CALL_TYPE_PROVIDER:
                mMethod.invoke(target, source);
                break;
            case CALL_TYPE_PROVIDER_WITH_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);
    }
}

状态变化与事件对应关系图

mActive只有在STARTED和RESUMED状态下才会是true,其余是false,livedata也是用该变量来刷新数据。

为什么弄这么复杂?因为这个框架需要给LiveData,ViewModel等一起使用,这是一个通用的框架,那么有没有其他方式来实现这么复杂的效果呢?通过平常的if else也可以,但是判断会比较复杂。

首先通过被观察者的生命周期完成状态机的状态变化,然后再通过状态机的状态获取被观察者应该回调的生命周期函数,最后通过反射来进行调用。这个状态机实现了被观察者与观察者的解耦,同时该状态机还可以再livedata, ViewModel等地方使用。

问题

1、如果在onResume中添加observer会怎么样?如果在onStop中注册呢?

onResume中:状态的变化是CREATE->START->RESUME,而不是直接就变成了RESUME;

onStop中:CREATE->DESTROY,整个流程的变化,INTIALIZED 一定会执行,从INTIALIZED->CREATE.因此CREATE状态一定是有的。 addObsever()的时候是初始状态(INTIALIZED),后面只执行了onDestroyed(),所以是onCreate和onDestroyed 详解可以看一下上边的状态机变化图。

相关推荐
CYRUS_STUDIO1 小时前
Frida 检测与对抗实战:进程、maps、线程、符号全特征清除
android·逆向
csj502 小时前
安卓基础之《(28)—Service组件》
android
lhbian4 小时前
PHP、C++和C语言对比:哪个更适合你?
android·数据库·spring boot·mysql·kafka
catoop5 小时前
Android 最佳实践、分层架构与全流程解析(2025)
android
ZHANG13HAO6 小时前
Android 13 特权应用(Android Studio 开发)调用 AOSP 隐藏 API 完整教程
android·ide·android studio
田梓燊6 小时前
leetcode 142
android·java·leetcode
angerdream6 小时前
Android手把手编写儿童手机远程监控App之JAVA基础
android
菠萝地亚狂想曲7 小时前
Zephyr_01, environment
android·java·javascript
sTone873757 小时前
跨端框架通信机制全解析:从 URL Schema 到 JSI 到 Platform Channel
android·前端
sTone873757 小时前
Java 注解完全指南:从 "这是什么" 到 "自己写一个"
android·前端