Kotlin coroutines Flow 没有被取消
Kotlin coroutines Flow is not canceled
我有一个 UseCase class 方法 returns Flow
fun startTimeTicker(startTime: Long) = flow {
val countdownStart = System.currentTimeMillis()
for (currentTime in countdownStart..startTime step ONE_SECOND_MILLIS) {
.... irrelevant ...
emit("Some String")
delay(ONE_SECOND_MILLIS)
}
}
我正在像这样在 ViewModel 中收集发射日期
private fun startCollecting(startTime: Long) = launch {
matchStartTimerUseCase.startTimeTicker(startTime).collect {
_startTimeCountdown.postValue(it)
}
}
我的片段正在观察 LiveData 并显示值。在我离开屏幕之前,它会按预期工作。由于 launch
是通过 ViewModel 的 coroutineScope 调用的,它不应该被取消并且不再发出值吗?
ViewModel 的范围在 BaseViewModel 中实现,我的 ViewModel 从中扩展如下:
抽象class BaseViewModel(
私有 val dispatcherProvider:DispatcherProvider
) : ViewModel(), CoroutineScope {
override val coroutineContext: CoroutineContext
get() = job + dispatcherProvider.provideUIContext()
private val job = SupervisorJob()
override fun onCleared() {
super.onCleared()
job.cancel()
}
}
我是否忘记添加一些自定义取消逻辑或遗漏了其他内容?
如果您的 ViewModel 的范围是 Activity 的生命周期 ViewModelProvider(requireActivity()).get(YOUR_VIEWMODEL::class.java)
,那么 onCleared
将不会被调用,除非您的 Activity 被销毁,但不会随着旋转变化而被调用.
首先,确保调用了onCleared(),如果没有调用可以调用Fragment的任何生命周期方法或Activity.
我有一个 UseCase class 方法 returns Flow
fun startTimeTicker(startTime: Long) = flow {
val countdownStart = System.currentTimeMillis()
for (currentTime in countdownStart..startTime step ONE_SECOND_MILLIS) {
.... irrelevant ...
emit("Some String")
delay(ONE_SECOND_MILLIS)
}
}
我正在像这样在 ViewModel 中收集发射日期
private fun startCollecting(startTime: Long) = launch {
matchStartTimerUseCase.startTimeTicker(startTime).collect {
_startTimeCountdown.postValue(it)
}
}
我的片段正在观察 LiveData 并显示值。在我离开屏幕之前,它会按预期工作。由于 launch
是通过 ViewModel 的 coroutineScope 调用的,它不应该被取消并且不再发出值吗?
ViewModel 的范围在 BaseViewModel 中实现,我的 ViewModel 从中扩展如下:
抽象class BaseViewModel( 私有 val dispatcherProvider:DispatcherProvider ) : ViewModel(), CoroutineScope {
override val coroutineContext: CoroutineContext
get() = job + dispatcherProvider.provideUIContext()
private val job = SupervisorJob()
override fun onCleared() {
super.onCleared()
job.cancel()
}
}
我是否忘记添加一些自定义取消逻辑或遗漏了其他内容?
如果您的 ViewModel 的范围是 Activity 的生命周期 ViewModelProvider(requireActivity()).get(YOUR_VIEWMODEL::class.java)
,那么 onCleared
将不会被调用,除非您的 Activity 被销毁,但不会随着旋转变化而被调用.
首先,确保调用了onCleared(),如果没有调用可以调用Fragment的任何生命周期方法或Activity.