0

Compose with で作成された検索ページに取り組んでいます。データが変更されたときに最初の項目に戻るという望ましいLazyColumn動作を除いて、すべて正常に動作します。LazyColumn

これは、遅延列の実際の実装です。

@Composable
fun <DataType : Any> GenericListView(
    itemsList: SnapshotStateList<DataType>, // this list comes from the search page viewmodel
    modifier: Modifier = Modifier.fillMaxSize(),
    spacing: Dp = 24.dp,
    padding: PaddingValues = PaddingValues(0.dp),
    item: @Composable (DataType) -> Unit
) {

    val listState: LazyListState = rememberLazyListState()
    val coroutineScope = rememberCoroutineScope()

    LazyColumn(
        verticalArrangement = Arrangement.spacedBy(spacing),
        state = listState,
        modifier = modifier.padding(padding)
    ) {
        items(itemsList) {
            item(it)
        }
    }

    SideEffect {
        Log.i("->->->->->->->", "side effect launched")
        coroutineScope.launch {
            listState.scrollToItem(0)
        }
    }
}

docs が言うようにSideEffect、関数が再構成されるたびに呼び出される必要がありますが、ブレークポイントを使用してデバッグ モードでのみ動作しているように見えますSideEffect。それ以外の場合は、ページ全体が最初に作成されたときにのみ動作します。

LaunchedEffectの代わりにasSideEffectを使用して既に試しましたが、何も起こりませんでした。itemsListkey

コードがデバッグ モードでしか機能しないのはなぜですか? または、新しいデータが設定されたときに位置をリセットするための既に作成された実用的なソリューションですか?

4

1 に答える 1

0

SideEffectSnapshotStateListが変更されたときに Compose が実際にビュー全体を再構成していないため、機能しませんLazyColumn。この状態値のみを使用しているため、この関数のみを再構成する必要があることがわかります。

それを機能させるには、次のように変更itemsListList<DataType>てプレーンリストを渡すことができitemsList = mutableStateList.toList()ます-ビュー全体の再構成を強制します。


LaunchedEffectwith passedSnapshotStateListは同じ理由で機能しません: 変更されていない状態コンテナーのアドレスを比較します。アイテム自体を比較するには、再び単純なリストに変換できます。この場合、アイテム ハッシュによって比較されます。

LaunchedEffect(itemsList.toList()) {
}
于 2021-12-18T01:43:56.400 に答える