【发布时间】:2018-10-23 13:58:44
【问题描述】:
我说奇怪是因为我不明白有人可能会告诉我什么正在按预期工作。
我有一个带有 LiveData 成员的 AndroidViewModel,我在 MainActivity 中观察到它可以切换一些代码功能。 LiveData 对象在视图模型的构造函数中被分配了初始值。
理论上一切正常,除了观察者的行为在安装后首次启动应用程序和后续应用程序启动之间发生变化。
在安装后的第一次启动期间,观察者在我设置它们后立即被触发,而底层的 LiveData 对象没有被更改。
在应用程序的后续启动期间,观察者不会在设置后过早触发,而是仅在我更改应用程序其他地方的值时触发,这是我期望发生的。
最初我认为观察者不知何故从 LiveData 初始化中获得了延迟触发,但如果这是真的,那么无论是安装后的第一次运行还是后续启动,它都应该发生。
因此,为了让应用按预期运行,如果应用在安装后首次运行,我必须在观察者中使用哨兵,以防止它们在第一次触发期间正常运行。
有人可以解释为什么会发生这种情况,如果它是我不相信的预期功能,请指向解释此问题的文档?
我觉得我又在破解 Android。
这是人们经常要求的一些代码 sn-ps,从 LiveData 声明开始。
@NonNull
private final MutableLiveData<Boolean> consentRequired = new MutableLiveData<>();
ViewModel 构造函数初始化
setConsentRequired(false);
ViewModel 获取器/设置器
@NonNull
public LiveData<Boolean> getConsentRequired()
{
return consentRequired;
}
@NonNull
public void setConsentRequired(@NonNull Boolean consentRequired)
{
this.consentRequired.setValue(consentRequired);
}
观察者
getViewModel().getConsentRequired().observe(this, item ->
{
if (sentryAllowsObserverToRun)
{
// Do the observer stuff here
}
}
sentryAllowsObserverToRun 是我必须设置的布尔值,以表明这不是安装后首次应用启动的第一个触发器。
【问题讨论】:
-
从viewmodel setConsentRequired(false)的构造函数中移除这个调用;
-
@Vishal 谢谢,我知道是构造函数分配触发了第一次观察,但我想知道为什么这只发生在设备上安装应用程序后的第一次启动时,并且永远不会对于任何其他应用程序启动。因此,当应用程序安装并启动时,构造函数赋值会触发观察者,然后我关闭应用程序,当我再次运行应用程序时,构造函数赋值不会触发观察者。这种行为很奇怪。
-
因为 ViewModelProviders 返回 ViewModel 的单例对象,这意味着当您启动应用程序时,ViewModelProviders 会创建一个对象,并且每当您在应用程序的同一生命周期期间访问该对象时,它都会返回相同的对象。
-
@Vishal 你没抓住重点。我关闭了应用程序,所以它的生命周期不一样。让我这样说吧。我安装了应用程序,当我打开它时,观察者立即被触发。然后我关闭应用程序,关闭手机。当我重新打开手机并打开应用程序时,不会触发观察者。没有生命周期可以在冷启动设备后存活。仅当我安装后第一次运行应用程序时才会触发观察者。
标签: android android-livedata android-viewmodel