从 Firestore 异步调用填充 RecyclerView

Populate RecyclerView from Firestore async call

我能够从 Firestore 检索数据(它在 populateValletList() 的 GlobalScope 中绝对可用,并且我能够从 asnyc 数据库调用或当我简单地添加一个 ValletpopulateValletList() 中手动添加到我的项目列表中,但是,当我想从 Firestore 数据填充该视图时,它不起作用。

不再调用 RecyclerAdapter 中的 onBindViewHolder

override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
    when(holder){
        is ValletViewHolder ->{
            holder.bind(items[position])
        }
    }
}

这就是我填充项目的方式 private var items : MutableList<Vallet> = ArrayList() :

fun populateValletList() {
    GlobalScope.launch {
        items = getAllValletsFromDatabase.executeUseCase()
    }
}

我在 onActivityCreated 中初始化我的 RecyclerView

private fun initRecyclerView(){
    recycler_view_vallets.apply{
        layoutManager = LinearLayoutManager(context)
        addItemDecoration(ValletRecyclerAdapter.ValletItemDecorator(30))
        valletAdapter = ValletRecyclerAdapter()
        adapter = walletAdapter
    }
    valletAdapter.populateValletList()
}

这是我第一次使用协程,我在这里忽略了什么?

好的,我认为您可以在代码中进行一些改进,但我认为没有按照您想要的方式工作的原因是因为我更新了您的项目列表,您必须调用 notifyDataSetChanged() 在你的适配器上。

理想情况下,您应该 运行 您的协程使用非全局范围,以避免泄漏,您可以为其使用视图模型,或者您可以使用 lifecycleScope.run { } 在你的片段中,为此我相信你需要添加一个依赖项。

    implementation "androidx.lifecycle:lifecycle-extensions:2.2.0"

关于更新回收器,我建议使用 ListAdapter,因此它添加了 DIFF Utils 并更容易更新值。

总结一下。

你的 Recycler Adapter 应该是这样的:

class HomePatchesAdapter : ListAdapter<Vallet, RecyclerView.ViewHolder>(REPO_COMPARATOR) {


    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
        return HomePatchesViewHolder.create(parent, viewType)
    }

    override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
        val repoItem = getItem(position)


        if (repoItem != null) {
            (holder as HomePatchesViewHolder).bind(repoItem)
        }
    }


    companion object {
        private val REPO_COMPARATOR = object : DiffUtil.ItemCallback<Vallet>() {
            override fun areItemsTheSame(oldItem: Vallet, newItem: Vallet): Boolean =
                oldItem.name == newItem.name

            override fun areContentsTheSame(oldItem: Vallet, newItem: Vallet): Boolean =
                oldItem == newItem
        }
    }


}

你的片段应该是这样的:

private fun initRecyclerView(){
    recycler_view_vallets.apply{
        layoutManager = LinearLayoutManager(context)
        addItemDecoration(ValletRecyclerAdapter.ValletItemDecorator(30))
    }

        val adapter = HomePatchesAdapter()
        recycler_view_vallets?.adapter = adapter

    lifecycleScope.run {

      adapter.submitList(getAllValletsFromDatabase.executeUseCase())

     } 

}

如果有道理请告诉我。