文章目录

    • 前言
    • Lifecycles 体系
      • Lifecycle
      • LifecycleOwner
      • LifecycleObserver
    • 源码分析
      • Activity 实现 LifecycleOwner
      • Fragment 实现 LifecycleOwner
      • 小结

前言

Android架构组件(Android Architecture Components,简称AAC),是 Android Jetpack的一部分。Jetpack是谷歌的一整套开发库,具体包括下图中的内容:
Android架构组件(1)Lifecycles体系_第1张图片
谷歌对于AAC的介绍是:

Android architecture components are a collection of libraries that help you design robust, testable, and maintainable apps. Start with classes for managing your UI component lifecycle and handling data persistence.

具体而言:

  • Lifecycles: 用于更好的管理activity和fragment的生命周期。
  • LiveData:用于构建响应式的可感知生命周期的数据流。
  • ViewModel:用于独立于Android组件生命周期存储 UI 相关的数据。

此外AAC还包括其他的(比如Room)的很好用的库,但是我最感兴趣的就是这三个框架,因为LiveData提供了响应式框架(之前对响应式编程感兴趣而学习了一会儿RxJava,但是被复杂的API给劝退了,相较之下LiveData就很纯粹,搭建了响应式的架子,但没有Rx眼花缭乱的操作符);ViewModel看起来也解决了我一直以来在Android组件之间传递数据的痛点,而Lifecycles给LiveData提供了感知生命周期的能力。

以下所有源码基于androidx.lifecycle库,库的版本为2.1.0;androidx.appcompat库,库的版本为1.1.0

Lifecycles 体系

Lifecycles提供了一种通过订阅者模式来监听Activity和Fragment的生命周期变化的方式。之前,我们解决这种需求的方法是在Activity和Fragment的生命周期方法 onXX 系列方法中直接嵌入功能代码或调用回调,现在通过Lifecycles来实现监听可以有效减少耦合,隔离功能代码。
Lifecycles框架中包括三个角色: LifecycleLifecycleOwnerLifecycleObserver,其中Lifecycle包含有关组件(例如Activity或Fragment)生命周期状态的信息,并允许其他对象观察此状态;LifecycleOwner表示一个拥有Lifecycle的类,LifecycleObserver则是LifecycleOwner的生命周期状态的监听者。

Lifecycle

Lifecycle使用两个枚举StateEvent来表示其相关组件的状态和导致状态变化的事件,State包括5个值:DESTROYEDINITIALIZEDCREATEDSTARTEDRESUMEDEvent包括7个值:ON_CREATEON_STARTON_RESUMEON_PAUSEON_STOPON_DESTROYON_ANY,它们的关系如图:
Android架构组件(1)Lifecycles体系_第2张图片
这个图里没有ON_ANY,这是因为ON_ANY代表发生了“任一事件”,而不是特定的一种事件。可以看到Event对应了Activity和Fragment的生命周期方法。每两个相邻状态之间的转换只有一种特定事件。每个事件也只会在两种特定状态之间发生,因此可以把它们视作一个有向图,每个State是一个节点,而每个Event则是一条边。
Lifecycle的接口如下:

public abstract class Lifecycle {@MainThread    public abstract void addObserver(@NonNull LifecycleObserver observer);        @MainThread    public abstract void removeObserver(@NonNull LifecycleObserver observer);        @MainThread    public abstract State getCurrentState();}

Lifecycle 声明了三个方法:分别用来注册、反注册订阅者,以及获取当前所处状态。这三个方法都加了@MainThread注解(表示该方法只应该在主线程中调用),因此可以猜测,Lifecycle不是线程安全的。

LifecycleOwner

LifecycleOwner 的接口如下:

public interface LifecycleOwner {    Lifecycle getLifecycle();}

很简单,就只有一个给LifecycleObserver获取Lifecycle的接口。

LifecycleObserver

LifecycleObserver的接口如下:

public interface LifecycleObserver {}@Retention(RetentionPolicy.RUNTIME)@Target(ElementType.METHOD)public @interface OnLifecycleEvent {    Lifecycle.Event value();}

这是一个空接口,因为接受订阅事件的方法是需要通过OnLifecycleEvent注解添加,比如这样,onCreate方法会在ON_CREATE事件发生后调用:

 public static class TestObserver implements LifecycleObserver {         @OnLifecycleEvent(Event.ON_CREATE)        public void onCreate(LifecycleOwner owner) {            Log.d(TAG, "onCreate:  " + owner.getLifecycle().getCurrentState());        }}

LifecycleObserver还有几个子类

public interface LifecycleEventObserver extends LifecycleObserver {    void onStateChanged(LifecycleOwner source, Lifecycle.Event event);}interface FullLifecycleObserver extends LifecycleObserver {    void onCreate(LifecycleOwner owner);    void onStart(LifecycleOwner owner);    void onResume(LifecycleOwner owner);    void onPause(LifecycleOwner owner);    void onStop(LifecycleOwner owner);    void onDestroy(LifecycleOwner owner);}public interface DefaultLifecycleObserver extends FullLifecycleObserver {    default void onCreate(LifecycleOwner owner) { }    default void onStart(LifecycleOwner owner) { }    default void onResume(LifecycleOwner owner) { }    default void onPause(LifecycleOwner owner) { }    default void onStop(LifecycleOwner owner) { }    default void onDestroy(LifecycleOwner owner) { }}

创建LifecycleObserver一般可以通过直接继承LifecycleObserver或它的子类,但是使用DefaultLifecycleObserver需要使用Java1.8,因为它的实现用到了接口的default方法。

源码分析

Lifecycles 的接口以及看完了,接下来就来看它的实现,Lifecycles 的实现很明显是基于观察者模式的,并且观察者LifecycleObserver由我们自己实现,所以需要看的只由两部分:

  1. LifecycleOwner(实际上就是Android support库中的Activity和Fragment)是怎么发布事件和更新状态的。
  2. 注册和反注册,以及事件发布是如果管理的。

下面我就这两方面来看代码。

Activity 实现 LifecycleOwner

首先看Activity(androidx.appcompat.app.AppCompatActivity)的实现,LifecycleOwner接口的实现是在AppCompatActivity的父类ComponentActivity中,大概代码是下面这样(省略无关代码):

public class ComponentActivity  implements LifecycleOwner {private final LifecycleRegistry mLifecycleRegistry = new LifecycleRegistry(this);@Override    protected void onCreate(@Nullable Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        ReportFragment.injectIfNeededIn(this);    }    @Override    public Lifecycle getLifecycle() {        return mLifecycleRegistry;    }}

这里面我只保留了两个类:LifecycleRegistryReportFragment,它们是何许人也呢?
LifecycleRegistry的接口如下,

public class LifecycleRegistry extends Lifecycle {@MainThread    public void setCurrentState(@NonNull State state) {...}       public void handleLifecycleEvent(@NonNull Lifecycle.Event event){...}       @Override    public void addObserver(@NonNull LifecycleObserver observer){...}      @Override    public void removeObserver(@NonNull LifecycleObserver observer) {...}       public int getObserverCount() {...}        @Override    public State getCurrentState() {...}}

这个类的注释如下:

An implementation of Lifecycle that can handle multiple observers. It is used by Fragments and Support Library Activities. You can also directly use it if you have a custom LifecycleOwner.

由此可知,LifecycleRegistry就是我们要找的那个管理类,而ReportFragment,则是那个发布生命周期的类,ComponentActivity将发送事件的功能委托给了它。ReportFragment的方法大体如下:

public class ReportFragment extends Fragment {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();         manager.executePendingTransactions();     }}@Override    public void onStart() {        super.onStart();        dispatchStart(mProcessListener);        dispatch(Lifecycle.Event.ON_START);    }private void dispatch(Lifecycle.Event event) {        Activity activity = getActivity();        if (activity instanceof LifecycleRegistryOwner) {            ((LifecycleRegistryOwner) activity).getLifecycle().handleLifecycleEvent(event);            return;        }        if (activity instanceof LifecycleOwner) {            Lifecycle lifecycle = ((LifecycleOwner) activity).getLifecycle();            if (lifecycle instanceof LifecycleRegistry) {                ((LifecycleRegistry) lifecycle).handleLifecycleEvent(event);            }        }    }}

在Activity中调用的injectIfNeededIn方法里,ReportFragment检查了这个Activity有没有已经持有了ReportFragment ,如果没有就新增一个,这样ReportFragment就共享了该Activity的生命状态。然后在生命周期方法onXX方法中发送事件,发送的方式在dispatch方法里。也就是根据Activity的不同(实际上在我的这版代码里,LifecycleRegistryOwner已经被废弃了,因此实际上只会走activity instanceof LifecycleOwner这条线),调用getLifecycle获取Activity的Lifecycle(也就是LifecycleRegistry),然后调用它的handleLifecycleEvent方法,将事件发送出去。

Fragment 实现 LifecycleOwner

接下来看Fragment(androidx.fragment.app.Fragment)的实现了。其实Fragment的实现更简单,它直接实现了LifecycleOwner接口:

public class Fragment implements LifecycleOwner {LifecycleRegistry mLifecycleRegistry;public Lifecycle getLifecycle() {        return mLifecycleRegistry;    }    private void initLifecycle() {        mLifecycleRegistry = new LifecycleRegistry(this);    //...    }    void performCreate(Bundle savedInstanceState) {     //...     mLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE);}void performPause() {//...        mLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_PAUSE);    }}

Fragment同样是通过LifecycleRegistry来发送生命周期事件和管理订阅者的。

小结

通过上面的介绍,LIfecycles体系的大体样子已经描述出来了,Activity 和 Fragment 通过继承LifecycleOwner 来提供getLifecycle接口,但实际上Lifecycle的功能实现是由LifecycleRegistry来完成的;如果我们要监听组件的生命周期,则需要继承LifecycleObserver或它的子类,通过相应注解或者override方法来在生命周期变化时获取对应生命周期改变事件的回调。然后通过该组件的getLifecycle方法获取到它的Lifecycle,再调用Lifecycle的addObserver方法完成订阅者的注册,还要在合适的时机调用removeObserver完成反注册。同时要注意的是,LIfecycles的大部分接口都规定了在主线程调用,因此,这个框架并不是线程安全的。
可以看出LifecycleRegistry是LIfecycles框架最重要的一个类,因此,我会在下一节里用一整节的篇幅详细分析它的实现。

更多相关文章

  1. android RadioButton文字居中的方法
  2. 编译NotificationManagerService.java文件的方法
  3. Android 下listview不能相应onItemClick事件
  4. Android应用程序获取ROOT权限的方法 (基础篇)
  5. Android在子线程中更新UI的方法汇总(共七种)
  6. Android 关闭(删除)FM Transmitter功能的方法
  7. Android临时数据缓存方法

随机推荐

  1. Camera.Parameters android相机参数
  2. Android TextView设置阴影效果
  3. Android(安卓)UI规范,就这么不受待见吗?
  4. Android 自定义View实现直播点赞特效
  5. Java环境变量和Android环境变量
  6. Binder系列1—Binder Driver初探
  7. Java加密解密工具(适用于JavaSE/JavaEE/An
  8. android图表引擎AchartEngine制作柱图源
  9. android Monkey test测试
  10. 自己在使用Android(安卓)Maps API 开发地