Paging 3 は、以前のバージョンのページング ライブラリとは大きく異なります。
このバージョンでは拡張機能が提供されており、Kotlin のコルーチンと Flow の最高級のサポート、Jetpack Compose とのシームレスな統合が実現しています。
Paging 3 に移行するメリット
Paging 3 では、旧バージョンのライブラリにはない以下の機能を利用できます。
- Kotlin のコルーチンと
Flowの最高級のサポート。 - レスポンシブ UI 設計のための組み込みの読み込み状態およびエラー信号(再試行および更新機能を含む)。
- リポジトリ レイヤの改善。キャンセルのサポートやシンプルなデータソース インターフェースなど。
- プレゼンテーション層、リスト セパレータ、カスタムページ変換、ヘッダーとフッター、Lazy リストの読み込み状態アイテムの改善。
アプリを Paging 3 に移行する
Paging 3 に完全に移行するには、Paging 2 から次の主要コンポーネントを移行する必要があります。
DataSourceクラスPagedList- プレゼンテーション層(
LazyPagingItems)
ただし、Paging 3 コンポーネントの中には、以前のバージョンの Paging と下位互換性があるものもあります。特に、Pager API では、古い
DataSource オブジェクトを asPagingSourceFactory メソッドで使用できます。そのため、以下のような移行が可能です。
DataSourceをPagingSourceに移行して、残りの Paging の実装を変更しない。- Paging の実装全体を移行して、アプリを Paging 3 に完全に移行する。
このページのセクションでは、アプリの各レイヤで Paging コンポーネントを移行する方法について説明します。
DataSource クラス
このセクションでは、古い Paging の実装を移行して PagingSource を使用するために必要なすべての変更について説明します。
Paging 2 の PageKeyedDataSource、PositionalDataSource、ItemKeyedDataSource はすべて、Paging 3 の PagingSource API に統合されています。すべての古い API クラスの読み込みメソッドは、PagingSource 内の単一の load メソッドに統合されています。これにより、コードの重複が減少します。これは、古い API クラスの実装における読み込みメソッド全体のロジックの多くが同一であることがよくあるためです。
すべての読み込みメソッドのパラメータは、Paging 3 で LoadParams シールクラスに置き換えられます。このクラスには、各読み込み型のサブクラスが含まれます。`load` メソッド内の読み込み型を区別する必要がある場合は、LoadParams のどのサブクラス(LoadParams.Refresh、LoadParams.Prepend、LoadParams.Append)が渡されたかを確認します。
PagingSource の実装について詳しくは、データソースを定義するをご覧ください。
キーを更新する
PagingSource の実装では、読み込まれたページング データの途中の状態から更新を再開する方法を定義する必要があります。そのためには、
getRefreshKey
を実装し、最近アクセスしたインデックスとしてstate.anchorPositionを使用して、正しい初期キーをマッピングします。
// Replaces ItemKeyedDataSource.
override fun getRefreshKey(state: PagingState<String, User>): String? {
return state.anchorPosition?.let { anchorPosition ->
state.getClosestItemToPosition(anchorPosition)?.id
}
}
// Replacing PositionalDataSource.
override fun getRefreshKey(state: PagingState<Int, User>): Int? {
return state.anchorPosition
}
変換を一覧表示する
ページング ライブラリの旧バージョンでは、ページング データの変換は次のメソッドに依存しています。
DataSource.mapDataSource.mapByPageDataSource.Factory.mapDataSource.Factory.mapByPage
Paging 3 では、すべての変換は PagingData に対する演算子として適用されます。上記リストのいずれかのメソッドを使用してページング リストを変換している場合は、新しい PagingSource を使用して Pager を作成するときに、変換ロジックを DataSource から PagingData に移動する必要があります。
Paging 3 でページング データに変換を適用する方法については、 データ ストリームを変換するをご覧ください。
PagedList
このセクションでは、古い Paging の実装を移行して Paging 3 で Pager と PagingData を使用するために必要なすべての変更について説明します。
PagedListBuilder クラス
PagingData は、Paging 2 の既存の PagedList に代わるものです。PagingData に移行するには、以下を更新する必要があります。
- Paging の設定が
PagedList.ConfigからPagingConfigに移動されました。 - 古いビルダー クラスが単一の
Pagerクラスに統合されました。 Pagerは、.flowプロパティを含むオブザーバブルなFlow<PagingData>を公開します。
val flow = Pager(
// Configure how data is loaded by passing additional properties to
// PagingConfig, such as prefetchDistance.
PagingConfig(pageSize = 20)
) {
ExamplePagingSource(backend, query)
}.flow
.cachedIn(viewModelScope)
Paging 3 で PagingData オブジェクトのリアクティブ ストリームを設定する方法について詳しくは、PagingData のストリームを設定するをご覧ください。
階層化されたソース用の BoundaryCallback
Paging 3 では、ネットワークおよびデータベースからのページングのハンドラとして、PagedList.BoundaryCallback が RemoteMediator に置き換わります。
RemoteMediator を使用して
Paging 3 のネットワークとデータベースからページングする方法については、Android ページングの Codelab をご覧ください。
LazyPagingItems
このセクションでは、古い Paging の実装を移行して Paging 3 の LazyPagingItems を使用するために必要なすべての変更について説明します。
Paging 3 には、新しい PagingData フローを処理する collectAsLazyPagingItems が用意されています。プレゼンテーション層を移行するには、paging-compose アーティファクトと collectAsLazyPagingItems を使用して PagingData アイテムを収集し、@Composable 関数で表示します。
LazyPagingItems の詳細については、ページング データを読み込む、表示するをご覧ください。
リストの差分と更新
現在カスタムのリスト差分ロジックを使用している場合は、Paging 3 で提供される LazyPagingItems を使用するように実装を移行します。差分が正しく行われるようにするには、Lazy リストにアイテムキーを指定します。
@Composable
fun UserScreen(viewModel: UserViewModel) {
// Collects the Flow into a LazyPagingItems object
val lazyPagingItems = viewModel.pager.flow.collectAsLazyPagingItems()
UserList(lazyPagingItems)
}
@Composable
fun UserScreen(viewModel: UserViewModel) {
val lazyPagingItems = viewModel.pager.flow.collectAsLazyPagingItems()
UserList(lazyPagingItems)
}
@Composable
fun UserList(lazyPagingItems: LazyPagingItems<User>) {
LazyColumn {
items(
count = lazyPagingItems.itemCount,
// Provide a stable key for each item, similar to DiffUtil in Views
key = lazyPagingItems.itemKey { user -> user.id }
) { index ->
val user = lazyPagingItems[index]
if (user != null) {
UserRow(user = user)
}
}
}
}
アイテムキーの詳細については、アイテムキーをご覧ください。
読み込み状態
Paging 3 では、読み込み状態のヘッダーまたはフッターを表示するために別のアダプターは必要ありません。LazyPagingItems オブジェクトは、LazyColumn 内で直接確認できる loadState プロパティを公開します。
LazyColumn {
// ... items(lazyPagingItems) go here ...
// Show loading spinner at bottom of list when appending data
if (lazyPagingItems.loadState.append is LoadState.Loading) {
item {
CircularProgressIndicator(modifier = Modifier.fillMaxWidth())
}
}
}
参考情報
ページング ライブラリについて詳しくは、以下の参考情報をご覧ください。
ドキュメント
Views のコンテンツ
あなたへのおすすめ
- 注: JavaScript がオフになっている場合はリンクテキストが表示されます
- ページング データを読み込む、表示する
- ページング データを収集する
- ネットワークとデータベースからページングする