android - ViewModel + 数据绑定(bind)中的最佳实践和模式。 ViewModel中的ObservableField可以吗?

标签 android design-patterns android-databinding android-architecture-components android-mvvm

通过查看示例,我看到了 2 种使用 Android 架构组件的 MVVM 方法。

第一种方法:

  1. ViewModel 提供LiveData
  2. Activity 订阅LiveData
  3. 当调用 Activity 的观察者正在将数据设置到 ViewModel ObservableField 时。
  4. 整个 ViewModel 被传递给绑定(bind)。
  5. xml 中,您只需将 ObservableField 设置为值

    <ProgressBar
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        app:visibleGone="@{viewmodel.listLoading}"/>
    
    <android.support.v4.widget.SwipeRefreshLayout
        android:id="@+id/swiperefresh"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:refreshing="@{viewmodel.listRefreshing}"
        app:onRefreshListener="@{() -> viewmodel.refreshList()}"
        app:visibleGone="@{!viewmodel.listLoading}">
    

优点: 我不需要传递状态(例如“正在加载”),因为我在 中更新 listLoading ObservableField >ViewModel 如下所示:

val listLoading = ObservableBoolean(false)
/** other observable fields go here **/

val list: MutableLiveData<List<Item>> = MutableLiveData()

  fun loadList() {
        listLoading.set(true)
        repo.getList { items ->
            list.value = items
            listLoading.set(false)
        }
    }

缺点:这种方法有缺点吗?

第二种方法:

  1. ViewModel 提供LiveData
  2. Activity 订阅LiveData
  3. 当调用 Activity 的观察者被传递给绑定(bind)时
  4. 只将需要的对象(pojo)传递给绑定(bind)

优点:这种方法有什么优点吗?

缺点:状态应该从 ViewModel 返回。在这个sample from Google数据包装在 Resource 对象中。

第一种方法用于 another sample app from Google

我想从具有更多 Android 数据绑定(bind)和 Android Arch 组件使用经验的开发人员那里了解这两种模式的优缺点。

最佳答案

您应该考虑将 View 逻辑与业务逻辑分开。

由于您有一个使用数据绑定(bind)和 AAC 来处理的 ViewModel,因此您还应该将 View (布局)内的逻辑分开。

只需将两个变量传递给您的布局。一个是处理业务逻辑的 VievModel,如按下按钮和处理逻辑,第二个是 View ( fragment )。

之后就可以使用了

app:onRefreshListener="@{() -> yourViewFragment.refreshList()}"

如果当前没有订阅 View ,请避免出现“上下文泄漏”或无法正常工作的解决方案。

由于 onRefreshListener 绑定(bind)到 fragment ,因此可以将其传递到 fragment 中。

您不应在 ViewModel 中创建 LiveData 或 ObservableField 来处理此类操作,因为如果您暂停和恢复 fragment ,您将再次观察 LiveData。这也意味着您将再次获得最后传送的数据。

可以在 ViewModel 中使用的示例:

<Textview ... name="@{viewModel.dataOfYourModel}" onClick="@{viewModel.doNetworkCall}" />

黄金法则:除了 android.arch.* 组件之外,每个以 android.* 开头的包/导入都不应在 View 模型中。

关于android - ViewModel + 数据绑定(bind)中的最佳实践和模式。 ViewModel中的ObservableField可以吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46696170/

相关文章:

Android数据绑定(bind)@BindingConversion失败,用于int到字符串

android - 所有司机的虚拟现实

android - 如何从我包含在 Android 上的第三方库中删除未使用的资源?

java - 在设备上安装两个类似的 Unity 应用程序时出错

android - 无法在 Android 的 Tabbar 应用程序中添加 AlertDialog?

design-patterns - Windows 服务的六边形架构/端口和适配器架构。正确的路?

design-patterns - 如何可靠地处理队列?

android - 寻找回调以了解数据绑定(bind)何时完成

ios - 单例模式是否适合我的情况?需要在 iOS App 中全局访问大量数据

android - 如何在 Android Studio 3.0.0 中使用数据绑定(bind)和 Kotlin