Java 在屏幕中跨不同片段共享ViewModel的一个实例

Java 在屏幕中跨不同片段共享ViewModel的一个实例,java,android,kotlin,mvvm,Java,Android,Kotlin,Mvvm,我使用的是单活动模式,在一个特定的屏幕中,我想用两个不同的片段共享一个viewModel。经过一段时间的研究,我发现了以下解决方案: 我在创建viewModel时使用activity实例,以便我的两个片段都获得相同的实例。但是这种方法的缺点是,viewModel实例在应用程序运行之前是活动的 我可以在启动第一个片段时向其添加标记,并在第二个片段中创建viewModel时传递第一个片段的实例。通过这种方式,我将在两个片段之间共享ViewModel的单个实例。 ViewModelProviders.

我使用的是单活动模式,在一个特定的屏幕中,我想用两个不同的片段共享一个viewModel。经过一段时间的研究,我发现了以下解决方案:

  • 我在创建viewModel时使用activity实例,以便我的两个片段都获得相同的实例。但是这种方法的缺点是,viewModel实例在应用程序运行之前是活动的
  • 我可以在启动第一个片段时向其添加标记,并在第二个片段中创建viewModel时传递第一个片段的实例。通过这种方式,我将在两个片段之间共享ViewModel的单个实例。
    ViewModelProviders.of(fragmentManager?.findFragmentByTag(TAG)!!,viewModelFactory).get(CustomViewModel::class.java)

  • 我在某处又读了一个分享viewModel的方法,但我忘了,因为它对我不起作用

  • 我想知道哪种方法最适合跨片段共享viewModel。我的选择是什么?谢谢。

    根据 以下是如何使用多个片段共享同一个ViewModel

    model = activity?.run {
            ViewModelProviders.of(this)[SharedViewModel::class.java]
        } ?: throw Exception("Invalid Activity")
    
    其在文件中解释如下:

    请注意,这两个片段都检索包含它们的活动。这样,当每个片段都获得ViewModelProvider时,它们会收到相同的SharedViewModel实例,该实例的作用域是此活动

    [更新] 您可以在片段中使用kotlin属性委托

    private val model: SharedViewModel by activityViewModels()
    

    你打破了MVVM模式,它的全部要点是视图模型与其对应视图之间的1:1关系。如果你同时使用导航组件,你可以通过导航图级别来确定viemodel的范围。嘿@MarkFeldman我理解你的观点,但为两个不同的片段创建一个视图模型是合乎逻辑的,如果两者使用相同的数据。我还有另一个屏幕,在那里我使用了四个片段。在该屏幕中创建四个ViewModel似乎不是一个好主意,尤其是当所有片段使用相同的数据时。此外,根据中的viewmodel描述,单个viewmodel可用于共享数据b/w片段。嘿@AndreClassen谢谢。我目前没有在应用程序中使用导航图。在我实现了导航图之后,我肯定会尝试一下。它可能看起来合乎逻辑,但它不是MVVM。视图是GUI的声明性元素,而视图模型是该视图状态的抽象;数据绑定将它们结合在一起。如果您有必须由多个视图表示的数据,那么这些数据应该在您的模型层中,多个视图模型实例将这些数据公开给它们的关联视图。如果不将多个视图抽象到视图模型层中,就无法单元测试它们是否和平共存(比如说)。这是不推荐的吗?
    private val model: SharedViewModel by activityViewModels()