如何更新 LiveData 值?

How to update LiveData value?

我正在为我的数据使用新的分页库。创建 ViewModel 并首次初始化实时数据时,一切正常。问题是我无法更新我的实时数据的值,例如当我单击菜单项并想用一组不同的数据更新它时。然后我的片段中的 onChanged 方法不会被调用。我已经阅读了有关 MutableLiveData 以及可以更新实时数据的 setValue 和 postValue 等方法的信息,但就我而言,我使用的是 LivePagedListProvider 并且无法 return 来自数据库的 MutableLiveData。

道:

@Query("SELECT * FROM teams ORDER BY name ASC")
LivePagedListProvider<Integer, Team> getAllTeams();

片段:

mTeamViewModel.mTeamsList.observe(this, new Observer<PagedList<Team>>() {
        @Override
        public void onChanged(@Nullable PagedList<Team> teams) {
            mTeamAdapter.setList(teams);
        }
});

视图模型:

public LiveData<PagedList<Team>> mTeamsList;

@Inject
DatabaseManager mDatabaseManager;

void setTeamViewModel(final DatabaseManager databaseManager) {
    mDatabaseManager = databaseManager;

    mTeamsList = mDatabaseManager.getAllTeams().create(
            0,
            new PagedList.Config.Builder()
                    .setPageSize(50)
                    .setPrefetchDistance(50)
                    .setEnablePlaceholders(true)
                    .build());

}

boolean onOptionsItemSelected(final MenuItem item) {
    switch (item.getItemId()) {
        case R.id.action_favorite:
            mTeamsList = mDatabaseManager.getFavoriteTeams().create(
                    0,
                    new PagedList.Config.Builder()
                            .setPageSize(50)
                            .setPrefetchDistance(50)
                            .build());
            return true;
        default: return false;
    }
}

在您的模型中创建一个 isFavourite 列。那么:

@Query("SELECT * FROM teams WHERE isFavourite = true")
LivePagedListProvider<Integer, Team> getFavouriteTeams();

那么你应该有一个 ViewModel 和一个 function/field 那个 returns 一个 MutableLiveData<PagedList<Team>> 并且在你观察到的 Fragment/Activity到那个领域。在您的 Fragment/Activity 中,您告诉 ViewModel 您需要做的每项更改都显示在删除列表中。然后在 ViewModel 中为实时数据列表分配不同的值。

经过3天的奋斗终于找到了解决办法,

为了更新 LiveData<PagedList> 的值,我们可以使用 MediatorLiveData,如下所示,在您的 ViewModel class:

public LiveData<PagedList<RecipeListPojo>> liveData;
private MediatorLiveData<PagedList<RecipeListPojo>> mediatorLiveData;

public RecipeListViewModel(@NonNull Application application) {
    super(application);
    mediatorLiveData = new MediatorLiveData<>();
}

public MediatorLiveData<PagedList<RecipeListPojo>> init(RecipeDao recipeDao, RecipeFrom recipeFrom, String orderBy) {
    liveData = new LivePagedListBuilder(recipeDao.getAllRecipesList(simpleSQLiteQuery), 6).build();
    
    mediatorLiveData.addSource(liveData, new Observer<PagedList<RecipeListPojo>>() {
            @Override
            public void onChanged(@Nullable PagedList<RecipeListPojo> recipeListPojos) {
                mediatorLiveData.setValue(recipeListPojos);
            }
        });
    return mediatorLiveData;
}

有关 MediatorLiveData

的更多详细信息,请参见 here

Transformations.switchMap 可以帮助:https://developer.android.com/reference/android/arch/lifecycle/Transformations#switchmap

class SearchViewModel() : ViewModel(){

val teamId = MutableLiveData<Int>()

var teamsList: LiveData<PagedList<Team>>=
    Transformations.switchMap(teamId) { id ->
        //just example
        if (id <= 0) {
            //1
            searchDbManager.searchWithoutId()
        } else {
            //2
            anotherSearchDbManager.searchWithId(id)
        }.setBoundaryCallback(SearchResultBoundaryCallback()).build()
    }
}

fun changeTeamId(id : Int){
   teamId.postValue(id)
}

如果您想将搜索过程更改为使用团队 ID 进行搜索(或切换到其他数据源),只需从 Fragment 中调用:

viewModel.changeTeamId(2)