LiveData 是一個(gè)可以被觀察的數(shù)據(jù)持有類(lèi),它可以感知 Activity、Fragment或Service 等組件的生命周期.
主要有以下優(yōu)點(diǎn):
1. 它可以做到在組件處于激活狀態(tài)的時(shí)候才會(huì)回調(diào)相應(yīng)的方法,從而刷新相應(yīng)的 UI。
2. 不用擔(dān)心發(fā)生內(nèi)存泄漏。
??? 這是因?yàn)長(zhǎng)iveData能夠感知到組件的生命周期,當(dāng)組件處于DESTROYED狀態(tài)時(shí),觀察者對(duì)象會(huì)被清除掉。
3. 當(dāng) config 導(dǎo)致 activity 重新創(chuàng)建的時(shí)候,不需要手動(dòng)取處理數(shù)據(jù)的儲(chǔ)存和恢復(fù)。它已經(jīng)幫我們封裝好了。
4. 當(dāng)Actiivty不是處于激活狀態(tài)的時(shí)候,如果你想livedata setValue之后立即回調(diào)obsever的onChange方法,而不是等到Activity處于激活狀態(tài)的時(shí)候才回調(diào) obsever的onChange方法。你可以使用 observeForever 方法,但是你必須在 onDestroy 的時(shí)候 removeObserver。
LiveData 使用
基本使用
? ? 添加依賴(lài):
// ViewModel and LiveData
implementation "android.arch.lifecycle:extensions:1.1.0"
// alternatively, just ViewModel
implementation "android.arch.lifecycle:viewmodel:1.1.0"
// alternatively, just LiveData
implementation "android.arch.lifecycle:livedata:1.1.0
annotationProcessor "android.arch.lifecycle:compiler:1.1.1"
使用LiveData步驟
1.創(chuàng)建持有某種類(lèi)型的LiveData對(duì)象。通常在ViewModel類(lèi)來(lái)實(shí)現(xiàn)該對(duì)象。
2.定義一個(gè)具有onChanged()方法的Observer對(duì)象,當(dāng)LiveData持有數(shù)據(jù)變化是回調(diào)該方法。通常在UI控制器類(lèi)中實(shí)現(xiàn)創(chuàng)建該Observer對(duì)象,如Activity或Fragment。
3.通過(guò)使用observe()方法,將上述的LiveData對(duì)象和Observer對(duì)象關(guān)聯(lián)在一起。這樣Observer對(duì)象就與LiveData產(chǎn)生了訂閱關(guān)系,當(dāng)LiveData數(shù)據(jù)發(fā)生變化時(shí)通知,而在Observer更新數(shù)據(jù),所以O(shè)bserver通常是Activity和Fragment
創(chuàng)建LiveData對(duì)象
可以把LiveData想象成一個(gè)可以與任何數(shù)據(jù)一起使用的包裝器,包括集合對(duì)象,列如:List。LiveData對(duì)象通常存儲(chǔ)在ViewModel對(duì)象中,并通過(guò)getter方法訪問(wèn)
public class NameViewModel extends ViewModel {
// 創(chuàng)建一個(gè)包含String的LiveData
private? MutableLiveData<String> mCurrentName;
public MutableLiveData<String> getCurrentName() {
????? if (mCurrentName == null) {
????????? mCurrentName = new? MutableLiveData();
????? }
??????? return? mCurrentName;
??? }
}
使用LiveData對(duì)象
public class NameActivity? extends AppCompatActivity {
??? private NameViewModel mModel;
??? @Override
??? protected void onCreate(Bundle? savedInstanceState) {
??????? super.onCreate(savedInstanceState);
??????? // 獲取ViewModel實(shí)例
??????? mModel =? ViewModelProviders.of(this).get(NameViewModel.class);
??????? // 創(chuàng)建更新UI的觀察者
??????? final Observer? nameObserver = new Observer() {
??????????? @Override
??????????? public void onChanged(@Nullable? final String newName) {
??????????????? // 更新UI
???????????????? mNameTextView.setText(newName);
??????????? }
??????? };
??????? // 觀察LiveData
??????? mModel.getCurrentName().observe(this,? nameObserver);
??? }
}
更新 LiveData 對(duì)象
???? // 這個(gè)方法必須在主線程調(diào)用
??????? protected void setValue (T value)
??????? // 這個(gè)方式主要用于在非主線程調(diào)用
???? protected void postValue (T value)? LiveData
轉(zhuǎn)換LiveData
??? 您可能想對(duì)存儲(chǔ)在LiveData對(duì)象中的值進(jìn)行更改后再分配給觀察者,或者您可能需要根據(jù)另一個(gè)LiveData實(shí)例返回不同的LiveData實(shí)例。
Lifecycle軟件包提供Transformations類(lèi),其中就包括支持這些場(chǎng)景的方法。
LiveData<Y> map (LiveData<X> source, Function<X, Y> func)
LiveData<Y> switchMap(LiveData<X> trigger, Function<X, LiveData<Y>> func)
map的例子:
MutableLiveData<DetailResult> resultLiveData = new MutableLiveData<>();
DetailResult detailResult = …..;
resultLiveData.postValue(detailResult);
//返回的值必須是LiveData<>,返回MutableLiveData<>會(huì)報(bào)錯(cuò)。
LiveData<String> poster = Transformations.map(resultLiveData, new Function<DetailResult,String>() {
??? @Override
??? public String apply(DetailResult input) {
??????? return input.getPoster();
??? }
});
// 使用Lamda,posterStr不用提前定義
LiveData<String> poster = Transformations.map(resultLiveData, posterStr -> {
??? return detailResult.getPoster();
}
LiveData<List<DetailProviderBean>> poster = Transformations.map(resultLiveData, new Function<DetailResult,List<DetailProviderBean>>() {
??? @Override
??? public List? apply(DetailResult input) {
??????? return input.getProvide_list();
??? }
});
// 使用Lamda,providerList不用提前定義
LiveData<List<DetailProviderBean>>
? providers = Transformations.map(resultLiveData, providerList -> {
?? return detailResut.getProvide_list();
}
switchMap的例子:
LiveData<String> poster = Transformations.switchMap(resultLiveData, new
????????????? Function<DetailResult,LiveData<String>>() {
??? @Override
??? public LiveData? apply(DetailResult input) {
??????? return getDes();
??? }
}
// 使用Lamda, posterStr不用提前定義
LiveData<String>? poster = Transformations.map(resultLiveData, posterStr -> {
??? return getDes();
}
要使用switchMap()需要先定義一個(gè)獲取LiveData<Object>數(shù)據(jù)的方法:
//要使用postValue,必須定義成MutableLiveData
MutableLiveData<String> strLiveData = new MutableLiveData<String>();
public LiveData<String> getDes() {
??? strLiveData.postValue(resultLiveData.getValue().getDes());
??? return strLiveData;
}