0

我试图在填充我的 ListAdapter 时从 LiveData 切换到 StateFlow。

我目前有一个MutableLiveData<List<CustomClass>>我正在观察更新列表适配器的:

  viewModel.mutableLiveDataList.observe(viewLifecycleOwner, Observer {
         networkIngredientAdapter.submitList(it)
}

这工作正常。现在我将viewModel 中的 替换为MutableLiveData<List<CustomClass>?>MutableStateFlow<List<CustomClass>?>

 private val _networkResultStateFlow = MutableStateFlow<List<IngredientDataClass>?>(null)
    val networkResultStateFlow : StateFlow<List<IngredientDataClass>?>
    get() = _networkResultStateFlow

 fun loadCustomClassListByNetwork() {
            viewModelScope.launch {
//a network request using Retrofit
 val result = myApi.myService.getItems()
 _networkResultStateFlow.value = result
}
}

我正在这样的片段中收集新列表:


 lifecycleScope.launchWhenStarted {
 viewModel.networkResultStateFlow.collect(){
                list -> networkIngredientAdapter.submitList(list)}
}

但是,当我调用 loadCustomClassListByNetwork() 时,列表适配器不会更新。为什么我无法收集价值

4

2 回答 2

1

尝试用以下代码替换片段中的代码:

lifecycleScope.launch {
viewModel.networkResultStateFlow.flowWithLifecycle(lifecycle)
         .collect { }
}
于 2021-12-28T06:15:32.860 回答
0

我在原始问题中没有提到,但是在创建的协程范围内进行了两个收集调用,如下所示:

lifecycleScope.launchWhenStarted {

       viewModel.networkResultStateFlow.collect(){
                list -> networkIngredientAdapter.submitList(list)}

       viewModel.listOfSavedIngredients.collectLatest(){
                  list -> localIngredientAdapter.submitList(list)}
}

以前只有第一个对方付费电话有效,因此只有一个列表在更新。所以我刚刚创建了两个单独的协程范围,现在它可以工作了:

lifecycleScope.launchWhenStarted {

       viewModel.networkResultStateFlow.collect(){
                list -> networkIngredientAdapter.submitList(list)}
}

lifecycleScope.launchWhenStarted {

       viewModel.listOfSavedIngredients.collectLatest(){
                  list -> localIngredientAdapter.submitList(list)}
}

注意:使用launch,launchWhenStartedlaunchWhenCreated产生相同的结果。

一旦我弄清楚每个收集电话需要单独范围的原因,我将编辑我的回复。

编辑:所以只有一个 listAdapter 更新的原因是因为我的每个 StateFlow 都需要一个单独的 CoroutineScope,因为根据定义,Flows 在协程上运行。每个流程都使用其各自的协程范围来收集自己的值,因此您不能让流程共享相同的协程范围 b/c,然后它们将冗余地收集相同的值。@ruby6221 提供的答案也创建了一个新的协程范围,因此很可能有效,但由于升级我的 SDK 版本的不相关问题,我无法对其进行测试,否则我会将其设置为正确答案。

于 2021-12-31T02:15:45.050 回答