Waf*_*_ck 2 android kotlin android-jetpack android-jetpack-compose
为什么我的应用程序在运行此代码时崩溃:
val scrollState = rememberLazyListState(0)
var isLastItemVisible by remember { mutableStateOf(false) }
LaunchedEffect(scrollState) {
while (!isLastItemVisible) {
val lastVisibleItemIndex = scrollState.layoutInfo.visibleItemsInfo.lastOrNull()?.index
val totalItemsCount = scrollState.layoutInfo.totalItemsCount
isLastItemVisible = lastVisibleItemIndex != null && lastVisibleItemIndex == totalItemsCount - 1
}
onLastItemSeen()
}
Run Code Online (Sandbox Code Playgroud)
当我在循环的最后一行添加任何延迟时,一切都正确。我在 LazyRow 中显示项目。
它不会让 ANR 崩溃,因为你处于无限循环中,无法滚动。
您可以使用衍生状态来检查最后一项是否可见
val isLastItemVisible by remember {
derivedStateOf {
val lastVisibleItemIndex = scrollState.layoutInfo.visibleItemsInfo.lastOrNull()?.index
val totalItemsCount = scrollState.layoutInfo.totalItemsCount
lastVisibleItemIndex != null && lastVisibleItemIndex == totalItemsCount - 1
}
}
LaunchedEffect(isLastItemVisible){
if (isLastItemVisible){
// Send event here
}
}
Run Code Online (Sandbox Code Playgroud)
或 LaunchedEffect 内的 snapshotFlow 仅发送一次事件
// Sends event only once
LaunchedEffect(scrollState) {
snapshotFlow {
scrollState.layoutInfo
}
.map {
val lastVisibleItemIndex = it.visibleItemsInfo.lastOrNull()?.index
val totalItemsCount = it.totalItemsCount
lastVisibleItemIndex != null && lastVisibleItemIndex == totalItemsCount - 1
}
// If it's a one time event filtering it
.filter { it }
.distinctUntilChanged()
.collect {
println("New Event sent...")
}
}
Run Code Online (Sandbox Code Playgroud)
或者每次最后一项可见时发送事件
// Sends event every time last item is seen
LaunchedEffect(scrollState) {
snapshotFlow {
scrollState.layoutInfo
}
.map {
val lastVisibleItemIndex = it.visibleItemsInfo.lastOrNull()?.index
val totalItemsCount = it.totalItemsCount
lastVisibleItemIndex != null && lastVisibleItemIndex == totalItemsCount - 1
}
.distinctUntilChanged()
.collect {visible->
println("Scroll visible: $visible")
if (visible){
println("New Event sent...")
}
}
}
Run Code Online (Sandbox Code Playgroud)
另外,我添加了一个示例,当最后一个项目可见时,可以在底端显示按钮,例如
@Preview
@Composable
private fun ListSample() {
val scrollState = rememberLazyListState(0)
val isLastItemVisible by remember {
derivedStateOf {
val lastVisibleItemIndex = scrollState.layoutInfo.visibleItemsInfo.lastOrNull()?.index
val totalItemsCount = scrollState.layoutInfo.totalItemsCount
lastVisibleItemIndex != null && lastVisibleItemIndex == totalItemsCount - 1
}
}
Box {
LazyColumn(
state = scrollState
) {
items(20) {
Text(
text = "Row $it",
modifier = Modifier.fillMaxWidth().padding(8.dp),
fontSize = 20.sp
)
}
}
if (isLastItemVisible) {
FloatingActionButton(
modifier = Modifier.align(Alignment.BottomEnd).padding(8.dp),
onClick = {
},
content = {
Icon(imageVector = Icons.Default.ArrowUpward, contentDescription = null)
}
)
}
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
273 次 |
| 最近记录: |