【问题标题】:How do I refresh a RecyclerView + PagedListAdapter and scroll to top?如何刷新 RecyclerView + PagedListAdapter 并滚动到顶部?
【发布时间】:2019-05-02 23:54:01
【问题描述】:

我有一个RecyclerView,它正在使用PagedListAdapter。我想刷新列表(即从我的DataSource 获取数据)并自动滚动到顶部。

这是我的 RecyclerView:

    <android.support.v7.widget.RecyclerView
        android:id="@+id/recyclerView"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
    val adapter by lazy {
        DiscoveryListAdapter(activity)
    }
        recyclerView.let {
            it.adapter = adapter
            it.layoutManager = LinearLayoutManager(activity)
        }

这是我的适配器:

class DiscoveryListAdapter() : PagedListAdapter<Discovery, DiscoveryListItemViewHolder>(DiscoveryDiffCallback()) {

    @SuppressLint("CheckResult")
    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): DiscoveryListItemViewHolder {
        //Extension function
        val view = parent.inflate(R.layout.discovery_detail_list_item)
        return DiscoveryListItemViewHolder(view)
    }

    override fun onBindViewHolder(viewHolder: DiscoveryListItemViewHolder, position: Int) {
        getItem(position)?.let {
            viewHolder.populateFrom(it)
        }
    }

    class DiscoveryDiffCallback : DiffUtil.ItemCallback<Discovery>() {
        override fun areItemsTheSame(one: Discovery, two: Discovery) =
                one == two

        override fun areContentsTheSame(one: Discovery, two: Discovery) =
                one == two
    }
}

我正在像这样构建 PagedList,订阅返回的 LiveData 对象并在适配器上调用 submitList

    fun buildLivePagedList(): LiveData<PagedList<Discovery>> {
        val config = PagedList.Config.Builder()
                .setPageSize(PAGE_SIZE)
                .setEnablePlaceholders(false)
                .setPrefetchDistance(PAGE_SIZE * 2)
                .build()
        val factory = DiscoveryListDataSourceFactory()
        return LivePagedListBuilder(factory, config).build()
    }

我正在使用这一行来刷新列表:

adapter.currentList?.dataSource?.invalidate()

这似乎正确刷新,但它使列表向下滚动一半。从那里我不知道如何让 recyclerview 返回到列表的顶部。我试过recyclerView.scrollToPosition(0),但没有骰子。无论如何,列表都会刷新但不会滚动到顶部。我该怎么做?

【问题讨论】:

  • 原来这是分页库中的一个错误:issuetracker.google.com/issues/123834703
  • 具有讽刺意味的是,我遇到了相反的问题。我想在保持滚动位置的同时刷新列表中的数据。知道您是如何实现这种行为的吗?

标签: android android-recyclerview android-paging


【解决方案1】:

尝试使用以下代码滚动到顶部:

pagedListAdapter.registerAdapterDataObserver(object : RecyclerView.AdapterDataObserver() {
    override fun onItemRangeInserted(positionStart: Int, itemCount: Int) {
        if (positionStart == 0) {
            manager.scrollToPosition(0)
        }
    }
})

【讨论】:

  • 这种方式太棒了!你节省了我几个小时,谢谢
【解决方案2】:
class DiscoveryDiffCallback : DiffUtil.ItemCallback<Discovery>() {
    override fun areItemsTheSame(one: Discovery, two: Discovery) = false

    override fun areContentsTheSame(one: Discovery, two: Discovery) = false
}

让你的 ItemCallback 返回 false。希望有帮助!

【讨论】:

    【解决方案3】:
        recyclerViewAdapter.currentList?.dataSource?.invalidate()
    
        recyclerView.postDelayed({
            recyclerView.layoutManager?.scrollToPosition(0)
        }, 400)
    

    【讨论】:

    【解决方案4】:

    试试adapter.refresh()

     val movieListAdapter : PagingDataAdapter
        swiperefresh.setOnRefreshListener {
                    movieListAdapter.refresh()
                    swiperefresh.isRefreshing = false
        }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-04-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多