aac架构入门-android-lifecycles代码解析

前言

本文将通过lifecycle代码的阅读理解,来学习aac的一些概念,比如viewmodel,lifecycle,livedata。
代码地址 https://github.com/googlecodelabs/android-lifecycles.git
代码里的activity继承自 AppCompatActivity,而AppCompatActivity继承自FragmentActivity,这个FragmentActivity和我们以前见到的地址可不一样,他是androidx.fragment:fragment这个jar包里面的,对应的gradle库为 androidx.appcompat:appcompat

step1 一个简单的计时功能

此处使用了android的一个计时器控件,Chronometer,这个控件只要调用start就会开始计时。Chronometer是继承自TextView的

step2 使用viewmodel实现计时功能

step2与step1的唯一区别就是,数据的创建使用了viewmodel。
其实每个activity有个ViewModelStore,viewmodel的创建和获取方式为。每个activity对应一个viewmodel,想想这样有什么好处,我要取数据会非常方便,以前在activity和viewholder之间传数据往往要通过adapter或者设计接口的方式,现在直接通过如下方法去取,简单优雅。

ViewModelProviders.of(this).get(ChronometerViewModel.class)

而且viewmodel是有生命周期的,直接跟activity同步,在activity销毁的时候自动销毁,我们不用考虑内存泄露问题。

ViewModel是存储UI相关数据并不会因为旋转而销毁的类

step3_solution

由于step3是个中间态,我们直接跳过,看step3_solution好了。step3_solution在viewmodel的基础上引入了livedata。看代码,我们在viewmdel里面放了个MutableLiveData,表示这个数据是可变的。这里也不用Chronometer了,直接用TextView。

public class LiveDataTimerViewModel extends ViewModel {

    private static final int ONE_SECOND = 1000;

    private MutableLiveData<Long> mElapsedTime = new MutableLiveData<>();

    private long mInitialTime;
}

这里的关键是通过ViewModel里的liveData更新数据,如何通知页面。具体的说就是如何把当前的时间值传给textview。核心代码如下

//MutableLiveData<Long>
mElapsedTime.postValue(newValue);
//activity
    private void subscribe() {
        final Observer<Long> elapsedTimeObserver = new Observer<Long>() {
            @Override
            public void onChanged(@Nullable final Long aLong) {
                String newText = ChronoActivity3.this.getResources().getString(
                        R.string.seconds, aLong);
                ((TextView) findViewById(R.id.timer_textview)).setText(newText);
                Log.d("ChronoActivity3", "Updating timer");
            }
        };

        mLiveDataTimerViewModel.getElapsedTime().observe(this, elapsedTimeObserver);
    }

其实很简单就是一个观察者模式,通过postValue来修改LiveData的值,然后在activity里给livedata注册一个观察者。
这里注意一个事情,我们使用了observe,按以前的套路是要在ondestroy的时候,删除观察者的,不然会有内存泄露。这里为甚没有删除的代码呢?这就是aac的第一个好处,liveData是有生命周期的,他会自动在activity destroy的时候删除观察者,代码如下。

//LiveData
       @Override
        public void onStateChanged(LifecycleOwner source, Lifecycle.Event event) {
            if (mOwner.getLifecycle().getCurrentState() == DESTROYED) {
                removeObserver(mObserver);
                return;
            }
            activeStateChanged(shouldBeActive());
        }

step4 和step4_solution

这里主要介绍了,lifecycle。
在step4里面,我们需要在onresume的时候addLocationListener,在onpause的时候removeLocationListener,这种操作非常常见,在页面可见的时候做一些事情。
用了lifecycle,我们就不用写这么ugly的代码了,可以使用注解OnLifecycleEvent优雅实现这种需求。核心代码如下 lifecycleOwner可以是activity或fragment

//new 
lifecycleOwner.getLifecycle().addObserver(this);
//
 @OnLifecycleEvent(Lifecycle.Event.ON_RESUME)
        void addLocationListener() {...}
        
 @OnLifecycleEvent(Lifecycle.Event.ON_PAUSE)
        void removeLocationListener() {}

step6 和step6_solution

这里主要介绍一种SavedState的ViewModel,实现方式使用SavedStateVMFactory来创建ViewModel,其实和onSaveInstance里面放代码是类似 的,以后再详细分析

ref

https://www.jianshu.com/p/e8955f525f4c

猜你喜欢

转载自blog.csdn.net/litefish/article/details/88783861