标签: android-paging-3

Android Jetpack Paging 3:带 Room 的 PagingSource

我正在使用最新的 Jetpack 库。
Pagination3 版本:3.0.0-alpha05
房间版本:2.3.0-alpha02

我的实体有 Long asPrimaryKey和 Room 可以PagingSource为其他Int类型生成。

error: For now, Room only supports PagingSource with Key of type Int.
    public abstract androidx.paging.PagingSource<java.lang.Long, com.example.myEntity>` getPagingSource();
Run Code Online (Sandbox Code Playgroud)

因此,我尝试实现我的 custom PagingSource,就像文档建议的那样。

问题是Data Refresh,因为 Room 生成的代码处理数据刷新,而我的代码无法处理这种情况。

任何建议如何实现自定义PagingSourceRoom,也负责处理Data Refresh

android android-room android-paging android-paging-library android-paging-3

8
推荐指数
1
解决办法
1689
查看次数

如何在 Android 中使用 Paging 3 库显示空视图

我想在 paging3 加载空列表时显示空视图。

它似乎适用于以下代码。这是处理分页 3 库的正确方法吗?:

        adapter?.addLoadStateListener { loadState ->
            adapter?.apply {
                if (itemCount <= 0 && !loadState.source.refresh.endOfPaginationReached) {
                    Timber.d("==> to show empty view")
                    tvEmptyView.isGone = false
                } else {
                    Timber.d("==> to hide empty view")
                    tvEmptyView.isGone = true
                }
            }
        } 
Run Code Online (Sandbox Code Playgroud)

android android-layout android-paging-3

8
推荐指数
2
解决办法
990
查看次数

恢复分页库 3 中的滚动位置

我将 Paging Library 3 与 RemoteMediator 一起使用,其中包括从网络和本地 Room 数据库加载数据。每次我滚动到 RecyclerView 中的某个位置,导航到另一个片段,然后导航回带有列表的片段时,滚动状态不会保留,并且 RecyclerView 显示从第一个项目开始的列表而不是位置在我离开之前我就已经到了。

我尝试使用 StateRestorationPolicy 但没有成功,并且似乎无法找到一种方法来获取 PagingDataAdapter 的滚动位置并在导航回 Fragment 时将其恢复到相同的精确位置。

在我的 ViewModel 中,我有一个从 RemoteMediator 收集数据的 Flow:

val flow = Pager(config = PagingConfig(5), remoteMediator = remoteMediator) {
    dao?.getListAsPagingSource()!!
}.flow.cachedIn(viewModelScope)
Run Code Online (Sandbox Code Playgroud)

我正在将该数据提交给我的片段中的适配器:

viewLifecycleOwner.lifecycleScope.launch {
    viewModel.flow.collectLatest { pagingData ->
        adapter?.submitData(pagingData)
    }
}
Run Code Online (Sandbox Code Playgroud)

在片段的顶部,我的适配器列出为:

class MyFragment : Fragment() {

    ...

    private var adapter: FeedAdapter? = null

    ...

    override onViewCreated(...) {

        if (adapter == null) {
            adapter = FeedAdapter(...)
        }

        recyclerView.adapter = adapter

        viewLifecycleOwner.lifecycleScope.launch {
            viewModel.flow.collectLatest …
Run Code Online (Sandbox Code Playgroud)

paging android android-paging android-paging-library android-paging-3

8
推荐指数
1
解决办法
3888
查看次数

当一项状态发生更改时刷新 LazyPagingItems

基本上我有一个在可组合函数中收集的分页数据流:

val list = state.listFlow.collectAsLazyPagingItems()
Run Code Online (Sandbox Code Playgroud)

列表中的每个项目都有一个号召性用语按钮,该按钮将启用/禁用视图并更新相应项目的 UI。

我的问题是,我们如何更新项目的视觉状态,而不需要在 PagingData 上调用刷新,从而重新查询 API/数据库以获取更新的数据?

此外,如果用户滚动浏览了 5 个或更多页面,我不想重新加载整个内容,更改可以是本地的。

有关如何实现这一目标的任何线索?

android android-paging android-jetpack-compose android-paging-3

8
推荐指数
1
解决办法
3143
查看次数

干净的架构:无法将 PagingSource&lt;Int, Entities&gt; 映射到 PagingSource&lt;RepositoryModel&gt;

我的要求是使用干净的架构和离线支持在页面中显示注释。我正在使用 Paging 库进行分页。下面是用于获取笔记的简洁架构图。

在此输入图像描述

注意:请在新选项卡中打开上图并缩放以清晰查看。

我有四层UIUseCaseRepositoryDatasource。我打算抽象数据源的内部实现。为此,我需要NotesEntities在跨越边界之前映射到另一个模型。

class TimelineDao{
    @Transaction
    @Query("SELECT * FROM NotesEntities ORDER BY timeStamp DESC")
    abstract fun getPagingSourceForNotes(): PagingSource<Int, NotesEntities>
}
Run Code Online (Sandbox Code Playgroud)

目前的实施:

internal class NotesLocalDataSourceImpl @Inject constructor(
    private val notesDao: NotesDao
) : NotesLocalDataSource {
    override suspend fun insertNotes(notes: NotesEntities) {
        notesDao.insert(NotesEntities)
    }

    override fun getNotesPagingSource(): PagingSource<Int, NotesEntities> {
        return notesDao.getPagingSourceForNotes()
    }
}
Run Code Online (Sandbox Code Playgroud)

预期实施:

internal class NotesLocalDataSourceImpl @Inject constructor(
    private val notesDao: NotesDao
) : NotesLocalDataSource {
    override suspend …
Run Code Online (Sandbox Code Playgroud)

paging clean-architecture android-room android-paging android-paging-3

8
推荐指数
1
解决办法
673
查看次数

Android Paging(三)一次性加载所有页面

我在项目中使用 Android Paging 3 库来逐页加载数据。在这个项目中,我没有使用数据库,这意味着我正在使用network only requests. 问题在于,它不是根据用户滚动加载页面,而是首先加载所有页面。这是我用于项目分页部分的代码:

我的 RxPagingSource 类:

class ReviewPagingSource constructor(
    private val network: Network,
    private val filter: ReviewFilter,
    private val config: Config,
    private val cacheFirstResponse: Boolean
) : RxPagingSource<Int, Review>() {

    override fun loadSingle(params: LoadParams<Int>): Single<LoadResult<Int, Review>> {
        return network.getReviews(
            filter.copy(page = (params.key ?: 0) , pageSize = params.loadSize),
            config,
            cacheFirstResponse
        )
            .subscribeOn(Schedulers.io())
            .map { toLoadResultPage(it, params) }
            .onErrorResumeNext {
                when (it) {
                    is TimeoutException,
                    is NoInternetException, is NetworkException, is UnexpectedResponseException -> Single.just(
                        LoadResult.Error(it) …
Run Code Online (Sandbox Code Playgroud)

android kotlin android-architecture-components android-paging-3

7
推荐指数
1
解决办法
5237
查看次数

如何处理 Kotlin Jetpack Paging 3 异常?

我是 kotlin 和 jetpack 的新手,我被要求处理来自 PagingData 的错误(异常),我不允许使用 Flow,我只允许使用 LiveData。

这是存储库:

class GitRepoRepository(private val service: GitRepoApi) {

    fun getListData(): LiveData<PagingData<GitRepo>> {
        return Pager(
            // Configuring how data is loaded by adding additional properties to PagingConfig
            config = PagingConfig(
                pageSize = 20,
                enablePlaceholders = false
            ),
            pagingSourceFactory = {
                // Here we are calling the load function of the paging source which is returning a LoadResult
                GitRepoPagingSource(service)
            }
        ).liveData
    }
}
Run Code Online (Sandbox Code Playgroud)

这是视图模型:

class GitRepoViewModel(private val repository: GitRepoRepository) : ViewModel() {

    private val …
Run Code Online (Sandbox Code Playgroud)

kotlin android-livedata android-jetpack kotlin-coroutines android-paging-3

7
推荐指数
1
解决办法
5345
查看次数

Paging 3 库在首次使用后不再请求我的 API

我正在尝试使用 paging 3 库对我的 REST API 进行分页,特别是使用该类RemoteMediator
我想要实现的是,我的本地数据库用于 UI 的初始呈现,如果显示的数据有任何更改,它会通过休息调用进行反应式更新。

我现在的奇怪行为是,分页仅在第一次时按预期工作:当用户滚动 RecyclerView 时,页面会增量加载(意味着触发 REST 调用)。

在我的本地数据库中有数据后,在开始时只有一个休息调用(具有初始加载大小),在结束时会连续触发大约 4 个请求。因此,它不会像第一次那样增量请求我的 API,它只是在最后触发所有请求。

这种行为正常吗?或者这是一个错误?

我的远程中介代码:

@ExperimentalPagingApi
class PageableRemoteMediator<T : Any>(
    private val pageKeyId: String,
    private val apiRequestFun: suspend (PageKey?, Int) -> ApiResult<Page<T>>,
    private val entityPersisterFun: suspend (Page<T>) -> Unit,
    application: Application
) : RemoteMediator<Int, T>() {
    private val db = DatabaseProvider.getDatabase(application)
    private val pageKeyDao = db.pageKeyDao()

    override suspend fun initialize(): InitializeAction {
        return InitializeAction.LAUNCH_INITIAL_REFRESH
    }

    override suspend fun load(loadType: LoadType, state: PagingState<Int, …
Run Code Online (Sandbox Code Playgroud)

android android-paging android-paging-3

7
推荐指数
1
解决办法
1161
查看次数

如何使用 Paging 3 库传递元数据和分页列表

我正在使用 Android Paging 3 beta 库在回收器视图中加载分页列表并使用 MVVM 架构。

我需要将其他元数据(例如有关页面的常见信息)传递给视图,但PagingSource.LoadResult.Page 的设计方式是仅将项目列表返回到视图。

以下是我想到的几个选项:

  • 使用实时数据独立传递元数据
  • 直接从数据库或内存缓存中读取元数据

最好的方法是什么?还有其他更好的建议吗?

android android-paging-3

6
推荐指数
0
解决办法
269
查看次数

如何实现基于游标的分页的 PagingSource.getRefreshKey - Android Jetpack Paging 3

我正在尝试使用Android Paging Library 3实现基于游标的分页(基于GraphQL Relay 规范),但我不知道如何实现。getRefreshKey

这是我尝试过的:

data class PagingKey(
    val before: String? = null,
    val after: String? = null,
)

class MoviePagingSource() : PagingSource<PagingKey, Movie>() {
    override suspend fun load(params: LoadParams<PagingKey>): LoadResult<PagingKey, Movie> {
        return try {
            val response = fetchMovies(
                before = params.key?.before,
                after = params.key?.after,
                pageSize = params.loadSize,
            )

            LoadResult.Page(
                data = response.edges.map { mapEdgeToMovie(it) },
                prevKey = if (response.pageInfo.hasPreviousPage) PagingKey(
                    before = response.pageInfo.startCursor
                ) else null,
                nextKey = if (response.pageInfo.hasNextPage) PagingKey(
                    after …
Run Code Online (Sandbox Code Playgroud)

android kotlin android-jetpack android-paging android-paging-3

6
推荐指数
1
解决办法
2401
查看次数