我正在使用Jetpack Compose编写Android应用程序。我有一个名为MultiSelectGroup
的Composable,每当单击FilterChip
时,它需要修改并返回一个选择列表。代码如下:
@OptIn(ExperimentalLayoutApi::class, ExperimentalMaterial3Api::class)
@Composable
fun MultiSelectGroup(
items: List<String>,
currentSelections: List<String>,
onSelectionsChanged: (List<String>) -> Unit,
) {
FlowRow {
items.forEach { item ->
FilterChip(
label = { Text(item) },
selected = currentSelections.contains(item),
onClick = {
val newSelectedChips = currentSelections.toMutableList().apply {
if (contains(item)) {
remove(item)
} else {
add(item)
}
}
onSelectionsChanged(newSelectedChips)
},
)
}
}
}
字符串
当前使用以下代码调用此组件:
val allItems = remember { (1..6).map {"$it"} }
val selectedItems = remember {
mutableStateOf(emptyList<String>())
}
MultiSelectGroup(
items = allItems,
currentSelections = selectedItems,
onSelectionsChanged = { selectedItems.value = it },
)
型
问题是,这种方法在重组方面似乎相当低效;每次单击FilterChip
时,所有FilterChip
都将重新组合,无论它们是否在视觉上发生变化。我目前的理解是,这是因为列表正在重新设置,并且List
是一种更不稳定的数据类型,Compose决定重新呈现依赖于List
的所有组件,而不仅仅是List
中的元素发生了变化。
我已经考虑过将每个FilterChip
的onClick
中的“更新列表”逻辑从组件中提升出来--然而,这个组件执行这个逻辑似乎是明智的,因为这个行为总是相同的,并且只会在每次使用MultiSelectGroup
时重复。我也尝试过使用mutableStateList
、key
和derivedStatedOf
的组合,但我还没有找到一个有效的解决方案。
像这样的组件注定要重新组合它的每个子组件吗?或者有没有一种方法可以优化这种视图的重组?提前感谢!
2条答案
按热度按时间y0u0uwnf1#
您当前的函数是不稳定的,因为你提到的参数
字符串
您可以创建一个包含文本和项选择状态的类,而不是两个列表。
型
您可以将
List
替换为稳定的SnapshotStateList
型
并将其用作
型
会的
型
实际上,您可以发送一个列表而不是SnapshotList,但随后FlowRow范围将被重新组合。使用SnapshotStateList,两个作用域都是不可跳过的。
你也可以不使用回调函数,因为你可以在
MultiSelectGroup
中更新SnapshotStateList
,但我不想在函数中更新输入的属性。h5qlskok2#
Google已经给出了一套最佳实践,你可以遵循,以避免不必要的重组。
https://developer.android.com/jetpack/compose/performance/bestpractices