くうと徒然なるままに

モバイルアプリを作りながらバックエンドも作っています。

RecyclerView.ListAdapter でアイテム挿入後に何かしたい!非同期辛い!

RecyclerView を使って何かする時に ListAdapter を使ってますか? DIFFUtil を使うときに合わせて使うことが多いかなと思います。

問題点

submitList しても非同期で挿入されるため、 SubmitList() した直後にRecyclerView(Adapter) に対してあれこれすると古いリストに対して操作してしまう。

どのようなケースで問題になるのでしょうか?
具体的には以下にsubmitList した後に処理をするケースで問題になります。

// adpater は ListAdapter の実装クラス
adapter.submitList(emptyList())
// RecyclerView に適当な処理を加える
binding.RecyclerView.scrollToPosition(100)

Why?

SubmitList は内部で DIFFUtil を使い差分を計算する処理をバックグラウンドExecuter でしているからです。

そのため、submitList が発火した後に非同期的に差分計算をし、挿入したりしてます。

必ず挿入した後のリストに対して操作しなければいけない場合は?

コールバックを設定すれば大丈夫そうです。
ただ、もっとスッキリできる方法あるかも....

        adapter.registerAdapterDataObserver(object: RecyclerView.AdapterDataObserver(){
            override fun onItemRangeChanged(positionStart: Int, itemCount: Int) {
                super.onItemRangeChanged(positionStart, itemCount)
                // 変更されたのがコールバックされる
            }
        })