【问题标题】:getViewLifeCycleOwner() vs 'this' vs this.getActivity() in Androidx FragmentsAndroidx Fragments 中的 getViewLifeCycleOwner() vs 'this' vs this.getActivity()
【发布时间】:2020-03-13 13:01:25
【问题描述】:

我们在片段中大量使用了 LiveData 的 observe 方法。最近发布的 androidx 片段 sdk 导致 Android Studio 将 liveDataObject.observe(this) 的实例标记为不正确,以支持 liveDataObject.observe(getViewLifecycleOwner())

添加了一个新的 Lint 检查,确保您在从 onCreateView()、onViewCreated() 或 onActivityCreated() 观察 LiveData 时使用 getViewLifecycleOwner()。 (b/137122478) https://developer.android.com/jetpack/androidx/releases/fragment

我们担心实施此更改,因为我们不了解getViewLifecycleOwner() 的功能与使用this 的功能相比如何,以及它是否会导致与thisthis.getActivity() 的使用发生冲突时在片段中设置 ViewModel。

另外,我们使用 Android Navigation 组件,注意到当用户导航到同一个 Activity 中的不同 Fragment 时,会调用每个 Fragment 的 onDestroyView() 方法,而不是 onDestroy()

这是我们在onViewCreated()中的代码示例

 vm.getStemLengths().observe(this, stemLengths -> {
        this.stemLengths = new ArrayList<>(Stream.of(stemLengths).map(stemLength ->
                new SearchModel(Integer.toString(stemLength.getValue()))).toList());
  });

稍后,在onDestroyView()

 vm.getStemLengths().removeObservers(this);

同时,根据片段,容纳 LiveData 的 ViewModel 设置为以下之一:

 vm = new ViewModelProvider(this.getActivity()).get(PrepareVM.class);

在 Activity 中跨片段保持视图模型。

或者:

vm = new ViewModelProvider(this).get(AprobacionVM.class);

如果VM不需要在当前fragment之外持久化

总而言之,在观察片段onCreateView() 中的 LiveData 对象时,将 this 更改为 getViewLifeCycleOwner() 是否会与 ViewModel 模式/导航组件冲突?是否存在例如 livedata 更改最终触发来自用户导航离开的同一活动中的前一个片段的观察者的实例?

从 getViewLifeCycleOwner 的文档看来,进行此更改可能允许我们删除每个片段的 onDestroyView() 中的 removeObservers() 调用。这是正确的理解吗?

【问题讨论】:

    标签: android android-fragments android-lifecycle


    【解决方案1】:

    Fragment 实现了LifecycleOwner,它将其创建和销毁事件分别映射到片段的onCreateonDestroy

    Fragment.getViewLifecycleOwner() 将其创建和销毁事件分别映射到片段的onViewCreatedonDestroyView。精确的序列描述在here

    如果您在观察者中使用视图,您将需要视图生命周期。否则,当视图层次结构无效时,您可能会得到更新,这可能会导致崩溃。

    从 getViewLifeCycleOwner 的文档看来,进行此更改可能允许我们删除每个片段的 onDestroyView() 中的 removeObservers() 调用。

    正确。

    【讨论】:

    • 感谢您的回复!一方面 onDestroyView() 中的 removeObservers() 调用不再需要,但另一方面 getViewLifecycleOwner() 使用片段的 onDestroy() 方法。所以如果 onDestroy() 方法没有被调用(就像我们的例子一样,当用户离开时只有 onDestroyView() 被调用),实时数据观察者将不会被删除,对吗?
    • onDestroyView,我的错字非常糟糕,抱歉。视图生命周期确实以 onDestroyView 结束。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-02-22
    • 2012-10-18
    • 1970-01-01
    • 2013-10-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多