LiveDataBus
解决粘连问题;反射找到mLastVersion,赋值为 mVersion; mLastVersion hook起点在mObservers
public static class xxMutableLiveData<T> extends MutableLiveData<T>{
@override
public void observer(@NonNull LifecycleOwner owner,@NonNull Observer<? super T> observer){
super.observer(owner, observer);
hook(observer);
}
}
private void hook(Observer<? super T> observer){
try{
Class<LiveData> liveDataClass = LiveData.class;
Field mObserversField = liveDataClass.getDeclaredField("mObservers");
mObserversField.setAccessible(true);
Object observersObject = mObserversField.get(this);
Class<?> observersClass = observersObject.getClass();
Method get = observersClass.getDeclaredMethod("get",Object.class);
get.setAccessible(true);
Object invokeEntry = get.invoke(observersObject, observer);
Object observerWrapper = null;
if(invokeEntry!=null&&invokeEntry instanceof Map.Entry){
observerWrapper = ((Map.Entry)invokeEntry).getValue();
}
Class<?> superClass = observerWrapper.getClass().getSuperclass();
Field mLastVersion = superClass.getDeclaredField("mLastVersion");
mLastVersion.setAccessible(true);
Field mVersion = liveDataClass.getDeclaredField("mVersion");
mVersion.setAccessible(true);
Object mVersionEntry = mVersion.get(this);
mLastVersion.set(observerWrapper,mVersionEntry);
}catch(Exception e){
}
}
DataBinding
使用
public class xxVM extends BaseObservable{
private String xx1;
private String xx2;
@Bindable
public String getXx1(){
return xx1;
}
public void setXx1(String xx1){
this.xx1 = xx1;
notifyPropertyChanged(BR.xx1);
}
@Bindable
public String getXx2(){
return xx2;
}
public void setXx2(String xx2){
this.xx2 = xx2;
notifyPropertyChanged(BR.xx2);
}
}
<layout>
<data>
<variable
name = "xxVM"
type = "com.xx.xx.xxVM"
/>
</data>
</layout>
android:text = "{xxVM.xx1}"
...XxActivity extends AppCompatActivity...
XxActivityBinding xxBinding;
XxVM xxVM;
...onCreate...{
xxBinding= DataBindingUtil.setContentView(this,R.layout.xx);
xxBinding.setXxVM(xxVM);
}
//赋值
...
xxVM.setXx1("xyz");//可以自动更新到界面上
...
...
原理
- xxBinding= DataBindingUtil.setC...:apt生成的代码里面 xml会被分离成两部分,并且加了tag
- xxBinding.setXxVM(xxVM):从apt代码中找,跳转到ViewDataBinding中 mLocalFieldObservers 存储了xml中的各个节点的数据,比如有3个节点就会处理3个监听
- xxActivityBindingImpl 的executeBindings()来处理设置数据到界面上
- BR 用来处理和界面上的绑定,这里用到了位的或运算提升速度