1、Lifecycles
- 平时做的可能就是在View中的每个周期调用Present中获取数据的方法,然后在调用View的回调接口更新UI,但现在使用Lifecycles可以使用注解和观察的模式自动调用Observe中定义好的方法。
创建Observer,LifecycleObserver是一个标记接口。
class MyObserver implements LifecycleObserver {
Lifecycle lifecycle;
CallBack callBack;
MyObserver(Lifecycle lifecycle, CallBack callback) {
this.lifecycle = lifecycle;
this.callBack = callback;
}
@OnLifecycleEvent(Lifecycle.Event.ON_CREATE)
public void connectOnCreate() {
update("connectOnCreate");
}
@OnLifecycleEvent(Lifecycle.Event.ON_RESUME)
public void connectOnResume() {
update("connectOnResume");
}
@OnLifecycleEvent(Lifecycle.Event.ON_DESTROY)
public void disConnectOnDestroy() {
update("disConnectOnDestroy");
}
private void update(String str) {
callBack.update(str);
}
public interface CallBack {
void update(String str);
}
}
创建Activity并实现LifecyclesOwner。
public interface LifecycleOwner {
Lifecycle getLifecycle();
}
public class TestActivity extends AppCompatActivity implements LifecycleOwner {
LifecycleRegistry lifecycleRegistry = new LifecycleRegistry(this);
MyObserver myObserver = new MyObserver(lifecycleRegistry,
str -> Toast.makeText(TestActivity.this, str, Toast.LENGTH_SHORT).show());
@NonNull
public Lifecycle getLifecycle() {
return lifecycleRegistry;
}
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
lifecycleRegistry.addObserver(myObserver);
lifecycleRegistry.markState(Lifecycle.State.CREATED);
}
@Override
protected void onResume() {
super.onResume();
lifecycleRegistry.markState(Lifecycle.State.RESUMED);
}
@Override
protected void onDestroy() {
super.onDestroy();
lifecycleRegistry.markState(Lifecycle.State.DESTROYED);
}
}
AppCompatActivity继承SupportActivity,而SupportActivity本身就实现了LifecycleOwner,上述TestActivity中的很多操作都已经在SupportActivity中完成了,那么上述的使用可以直接更简化为:
public class TestActivity extends AppCompatActivity implements LifecycleOwner {
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
MyObserver myObserver = new MyObserver(getLifecycle(),
str -> Toast.makeText(TestActivity.this, str, Toast.LENGTH_SHORT).show());
getLifecycle().addObserver(myObserver);
}
}
SupportActivity在onCrate的方法中初始化了一个ReportFragment,ReportFragment在其生命周期中dispatch相应的Event生命周期,如 dispatch(Lifecycle.Event.ON_CREATE);
ReportFragment.injectIfNeededIn(this);
原文:https://blog.csdn.net/Alexwll/article/details/80638905
@OnLifecycleEvent:运行注解
// LifecycleOwner使用了弱引用
private final WeakReference<LifecycleOwner> mLifecycleOwner;
public LifecycleRegistry(@NonNull LifecycleOwner provider) {
mLifecycleOwner = new WeakReference<>(provider);
mState = INITIALIZED;
}
public void handleLifecycleEvent(@NonNull Lifecycle.Event event) {
State next = getStateAfter(event);
moveToState(next);
}
// Fragment中调用
mLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE);
2、ViewModel
SharedViewModel model = ViewModelProviders.of(getActivity()).get(SharedViewModel.class);
-
使用onSaveInstanceState()方法从中恢复其数据 onCreate(),但此方法仅适用于可以序列化然后反序列化的少量数据,如果要恢复的数据量比较大,此时就时VIewModel的厉害之处了。ViewModel之所以能在Activity重建时保存并恢复数据,因为Activity初次创建时会初始化创建VIewModel,在Activity销毁时,ViewModel对象不会销毁,在新的Activity重新创建后,仍然会执行之前的获取ViewModel的过程,Android系统采取了处理机制,使现在拿到的ViewModel就是前一次创建的对象。
-
因为ViewModel在Activity销毁时是不会重新创建的,这也意味者ViewModel中不可以引用Activity的对象,否则会有内存泄露的问题,那么当Model中需要Context呢?Android为我们提供了AndroidViewModel,只需继承AndroidViewModel即可
-
ViewModel原理:将数据保存到ViewModel中,然后为活动中添加一个HolderFragment,HolderFragment中保存了ViewStore的实例,ViewStore中使用Map保存了ViewModel,从而在活动重新创建时获取到原来的ViewModel
-
HolderFragment中保存了ViewStore的实例
-
如何保证两次创建的activity(旋转前后)获取到的为同一个ViewModel?在获取Fragment时,创建过HolderFragment后,会保存在Map中,Map的键就是Activity的实例,所以无论多少次创建都是此Activity的实例,也就获得唯一的一个对应的Fragment。
-
传入的Activity的对象一致,那获取到就是同一个Fragment,存储的也是同一个ViewStore,那设想一下,如果一个Activity中有多个Fragment,利用这个特性就可以实现Fragment之间数据交互,例如:两个Fragment之间。一个显示标题列表,点击某一个标题,另一个Fragment显示内容,此时使用一个ViewModel实现两者的传递。
原文:https://blog.csdn.net/Alexwll/article/details/82459614
3、LiveData
- LiveData是一个具有生命周期感知特性的可观察的数据保持类,使用LiveData保存数据时,在每次订阅或数据更新时会自动回调设置的观察者从而更新数据,真正的实现了数据驱动的效果。
- LiveData的创建基本会在ViewModel中,从而使数据在界面销毁时继续保持。
- LiveData 认为观察者的生命周期处于STARTED状态或RESUMED状态下,表示观察者处于活动状态,LiveData只通知活跃的观察者更新数据。
- 注册一个实现该LifecycleOwner 接口的对象配对的观察者,当相应Lifecycle对象的状态改变为DESTROYED时移除观察者
class TestViewModel : ViewModel() {
var mCurrent: MutableLiveData<String>? = null
get() {
if (field == null) {
field = MutableLiveData() // 创建一个LiveData实例来保存某种类型的数据
} // LiveData对象必须在ViewModel中
return field
}
}
-------------------------
val nameObservable = Observer<String> { // 创建观察者对象
textView.text = it // 创建一个定义onChanged()方法的Observer对象,在数据变化时回调
}
-------------------------
// 使用LifecycleOwner的observe() 方法将观察者对象附加到LiveData对象,这将观察对象向LiveData对象订阅,以便通知其更改
mModel = ViewModelProviders.of(this).get(TestViewModel::class.java)
// mCurrent 订阅观察
mModel.mCurrent!!.observe(this, nameObservable)
原文:https://blog.csdn.net/Alexwll/article/details/82996003
4、Navigation
- 导航架构组件简化了Android应用程序中导航的实现,通过在xml中添加元素并指定导航的起始和目的地,从而在Fragment之间建立连接在Activity中调用xml中设置的导航action从而跳转界面到目的地。Navigation多数作用于Fragment中。
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/second" app:startDestination="@id/fragmentT">
<fragment android:id="@+id/fragmentT" android:name="com.example.administrator.navigation.FragmentT"
android:label="fragment_fragment_t" tools:layout="@layout/fragment_fragment_t">
<action android:id="@+id/action_fragmentT_to_fragmentOther" app:destination="@id/fragmentOther"/>
</fragment>
<fragment android:id="@+id/fragmentOther" android:name="com.example.administrator.navigation.FragmentOther"
android:label="fragment_fragment_other" tools:layout="@layout/fragment_fragment_other"/>
</navigation>
btnActivity.setOnClickListener {
val option = ActivityOptionsCompat.makeSceneTransitionAnimation(activity as Activity, imageView, "image")
val exeras = ActivityNavigator.Extras(option)
Navigation.findNavController(btnFragment)
.navigate(R.id.action_blankFragment_to_secondActivity2, null, null, exeras)
网友评论