使用MVVM架构进行活动共享元素转换

时间:2018-08-06 14:33:04

标签: android android-transitions shared-element-transition android-mvvm

我正在学习MVVM模式,现在遇到问题。我有一个带有imageview的活动A,一个带有相同imageview但在另一个地方更大的活动B。在活动A中,我单击imageview,我想开始活动B,并且应该共享imageview以便通过漂亮的动画实现我想要的功能。

使用数据绑定,我可以在视图模型中单击imageview:

<de.hdodenhof.circleimageview.CircleImageView
                    android:layout_width="60dp"
                    android:layout_height="60dp"
                    android:onClick="@{(v) -> user.onAvatarClick(v)}"
                    android:scaleType="centerCrop"
                    android:src="@{user.photoUrl}"
                    android:transitionName="@string/avatar_transition" />

在我的视图模型中,我应该这样写:

public void onAvatarClick(View view) {
    Intent intent = new Intent(context, AvatarActivity.class);
    ActivityOptionsCompat options = ActivityOptionsCompat.makeSceneTransitionAnimation(activity, view, view.getTransitionName());
    context.startActivity(intent, options.toBundle());
}

但是,问题是我的视图模型对活动一无所知。而且我不知道该怎么做。

一种可能的解决方案是使用诸如startActivityB(View view)之类的方法创建接口,并在活动中实施该接口,并将其设置为例如viewModelListener的字段。然后我可以写类似的东西:

public void onAvatarClick(View view) {
    viewModelListener.startActivityB(view);
}

但是在这种情况下,我的视图模型将具有对视图的引用,这破坏了MVVM的主要思想,对吗?

那么,使用MVVM体系结构以共享元素开始新活动的正确方法是什么?

1 个答案:

答案 0 :(得分:0)

这可以通过Android中的实时数据来完成。您可以观察实时数据的变化,并相应地导航到其他活动。

此处的示例

在您单击按钮的xml文件中

android:onClick="@{()->homeActivityViewModel.openNewActivity()}"

在您的viewModel类中

private final MutableLiveData<Boolean> openNewScreen = new MutableLiveData<>();

 //function that is binded to xml
public void openNewActivity() {
    openNewScreen.setValue(true);
}

public MutableLiveData<Boolean> getNewScreen() {
    return openNewScreen;
}

您的活动

 homeActivityViewModel.getNewScreen().observe(this,
            start -> {
                if (start) {
                    Intent intent = new Intent(this, NewActivity.class);
                    startActivity(intent);
                } });