在视图模型中更新另一个LiveData时,触发LiveData成员的更新 [英] Trigger update for a LiveData member when another LiveData is updated in the view model

查看:414
本文介绍了在视图模型中更新另一个LiveData时,触发LiveData成员的更新的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在文字游戏应用中,我在活动和片段之间共享一个模型:

In a word game app I share a model between an activity and a fragment:

public class MainViewModel extends AndroidViewModel {
    private LiveData<List<Game>> mGames;
    private final MutableLiveData<Game> mDisplayedGame = new MutableLiveData<>();

(请原谅屏幕截图中非英语的文字)

(please excuse the non-english text in the screenshot)

活动观察到用户当前正在播放mGames并更新导航抽屉菜单(请参见上面的屏幕截图的左侧).

The activity observes mGames being currently played by the user and updates the navigational drawer menu (see the left side of the above screenshot).

该片段会观察mDisplayedGame并将其显示在自定义视图中(请参见上面的屏幕截图的右侧).

The fragment observes mDisplayedGame and displays it in a custom view (see the right side of the above screenshot).

我的问题是,当在服务器上更新游戏列表时(活动通过Websocket接收了新的游戏列表并将其存储在会议室中),我需要发布更新片段:嘿,您要显示的游戏已更新,请重新绘制!"

My problem is that when the list of the games is updated at the server (and the activity receives new list of games via Websocket and stores it in the Room), I need to post an update to the fragment: "Hey, the game you are displaying was updated, redraw it!"

是否可以从共享视图模型中做到这一点?

Is it possible to do that from within the shared view model?

我知道我也可以在片段中观察mGames并在其中添加代码以对其进行迭代,然后找出显示的游戏是否在服务器上进行了更新.

I know that I could observe mGames in the fragment too and add a code there iterating through them and then finding out if the displayed game was updated at the server.

但是我更喜欢在MainViewModel中执行此操作,因为我感觉该片段应该只观察它正在显示的一个游戏,就是这样.

But I would prefer to do it in the MainViewModel because I have a feeling that the fragment should only observe the one game it is displaying and that's it.

TL; DR

每当通过Room在视图模型中更新mGames时,我也需要通知mDisplayedGame观察者!

Whenever mGames is updated in the view model via Room, I need to notify the mDisplayedGame observers too!

推荐答案

您应该为此使用MediatorLiveData.

You should use a MediatorLiveData for this.

它的工作方式是

public class MainViewModel extends AndroidViewModel {
    private final LiveData<List<Game>> mGames;
    private final MutableLiveData<Game> mSelectedGame = new MutableLiveData<>();

    private final MediatorLiveData<Game> mDisplayedGame = new MediatorLiveData<>();

    {
        mDisplayedGame.addSource(mGames, (data) -> {
            // find the new value of the selected game in the list
            mSelectedGame.setValue(newSelectedGame);
        });

        mDisplayedGame.addSource(mSelectedGame, (data) -> {
            mDisplayedGame.setValue(data);
        });
    }

然后将mDisplayedGame公开为LiveData<Game>,它应该可以正常工作.

And then you expose mDisplayedGame as a LiveData<Game> and it should just work.

这篇关于在视图模型中更新另一个LiveData时,触发LiveData成员的更新的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆