5

我正在从网络加载帖子,为此我正在使用Paging 3,但现在的问题是我的列表项包含 Like/Dislike 按钮,假设单击Like,那么如何在不重新加载整个数据集的情况下更新该项目的数据?

我已阅读此android-pagedlist-updates,但似乎这适用于较旧的 Paging 2 或 1,那么在Paging 3中实现这一目标的完美方法是什么

4

3 回答 3

0

我通过以下机制克服了这一挑战。维护内部 Hashmap 以保存键和对象,将此内部 hashmap 保存在您的 pagedlist 适配器中。随着列表的滚动,您将通过使用它的某个唯一键将远程喜欢/不喜欢作为初始状态添加到内部哈希映射中,因为该键是唯一的,您将不会复制,然后您将这个内部哈希映射用于您的更新 UI。

喜欢和不喜欢的 onClick 侦听器将更新此内部哈希图。再次内部哈希图是 UI 更新的参考。

解决方案很简单 - 在另一个内部 hashmap 上收集有用的数据以供以后操作。

于 2020-07-31T06:46:21.273 回答
0

我找到了一种解决方法,您可以使用它来实现这一目标,并提供了我正在使用的代码库的一些背景:

  • 我有一个 PagingDataAdapter(Pagination-3.0 适配器)作为回收器视图适配器。
  • 我有片段的视图模型
  • 我有一个返回 PaginationData 流的存储库
  • 并将此流作为 liveData 暴露给片段

存储库代码:

override fun getPetsList(): Flow<PagingData<Pets>> {
    return Pager(
        config = PagingConfig(
            pageSize = 15,
            enablePlaceholders = false,
            prefetchDistance = 4
        ),
        pagingSourceFactory = {
            PetDataSource(petService = petService)
        }
    ).flow
}

视图模型代码:

// create a hashmap that stores the (key, value) pair for the object that have changed like (id:3, pet: fav=true .... )

viewModelScope.launch {
            petRepository.getPetsList()
                .cachedIn(viewModelScope)
                .collect {
                    _petItems.value = it
                }
        }

现在是映射和所有魔法发生的片段代码

viewModel.petItems.observe(viewLifecycleOwner) { pagingData ->
        val updatedItemsHashMap = viewModel.updatedPetsMap
        val updatedPagingData = pagingData.map { pet ->
            if (updatedItemsHashMap.containsKey(pet.id))
                updatedItemsHashMap.getValue(pet.id)
            else
                pet
        }
        viewLifecycleOwner.lifecycleScope.launch {
            petAdapter.submitData(updatedPagingData)
        }
    }

这就是实现这一点的方法,关键是对从存储库发出的 pagingData 进行映射。

不起作用的事情:

_petItems.value = PagingData.from(yourList)

这不起作用,因为根据文档,这用于静态列表,并且您会失去分页 3.0 附带的分页功能。所以映射 pagingData 似乎是唯一的方法。

于 2021-09-01T04:26:40.747 回答
-1

在 Paging3 中,您仍然需要依赖PagingSource.invalidate来提交更新,这与其说是不变性,不如说是关于拥有单一的事实来源。

通常,执行此操作的正确方法是更新支持数据集并调用invalidate,这将触发不应导致任何 UI 更改的 REFRESH + DiffUtil,但保证如果该页面被删除并重新获取,加载的页面仍将保持最新。最简单的方法是使用已经内置自失效的 PagingSource 实现,例如 Room 提供的实现,只需更新喜欢/不喜欢按钮的相应行 onClick 即可。

有一个开放的错误跟踪工作以支持使用 Flow<> 对列表进行高度频繁、精细的更新,如果这是您的用例,您可以在此处关注:https ://issuetracker.google.com/160232968

于 2020-07-30T17:04:04.717 回答