何时可以在 LazyList 或列的范围内使用可组合项?

发布于 2025-01-16 09:51:33 字数 515 浏览 0 评论 0原文

我使用 Jetpack Compose 构建了许多项目和组件。我已阅读 StackOverFlow 上的文档和其他教程、网站和帖子。

我不清楚何时允许在另一个可组合项中使用可组合项和可组合函数,特别是使用 LazyColumn

我有一些组件,在 LazyColumn 内部使用 RowColumn。其他时候,我尝试创建一个 itemsIndexed 列表,该列表创建一系列 RowCard ,但我收到一条错误 @可组合调用只能在 @Composable 函数的上下文中发生

LazyColumn 不被视为 @Composable 函数吗?整个 LazyColumn 位于 @Composable 函数本身内。

我对上下文从可组合环境到不可组合环境的变化感到困惑。

谁能解释一下吗?我在困惑什么?

I have built a number of projects and components with Jetpack Compose. I've read the docs and other tutorials, sites, and posts on StackOverFlow.

I am unclear about when I am allowed to use composables and composable functions inside of another composable, particularly with a LazyColumn.

I have components where I use a Row or a Column inside of a LazyColumn. Other times I try to create an itemsIndexed list that creates a series of Rows or Cards and I get an error that @Composable invocations can only happen from the context of a @Composable function.

Isn't the LazyColumn considered a @Composable function? The entire LazyColumn is within a @Composable function itself.

I'm confused about where the context changes from a composable environment to a non-composable environment.

Can anyone explain? What am I confusing?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

冷情 2025-01-23 09:51:33
@Composable invocations can only happen from the context of a @Composable function

如上所述,您需要从用 @Composable 注解的函数调用可组合项,

如果您检查 LazyColumn 函数签名,

@Composable
fun LazyColumn(
    // rest of the params
    content: LazyListScope.() -> Unit
) {

}

您将看到内容不是可组合项。另一方面,items 函数使用 itemContent 作为可组合函数,

inline fun <T> LazyListScope.items(
    items: List<T>,
    noinline key: ((item: T) -> Any)? = null,
    noinline contentType: (item: T) -> Any? = { null },
    crossinline itemContent: @Composable LazyItemScope.(item: T) -> Unit
) = items(
    count = items.size,
    key = if (key != null) { index: Int -> key(items[index]) } else null,
    contentType = { index: Int -> contentType(items[index]) }
) {
    itemContent(items[it])
}

因此您可以调用可组合函数,例如 Column inside item 函数。

items(myItems) { myItem: MyItem ->
    Column{

    }
}

ColumnRowBox 等函数的 XScope 函数标记为
@Composable

@Composable
inline fun Column(
    modifier: Modifier = Modifier,
    verticalArrangement: Arrangement.Vertical = Arrangement.Top,
    horizontalAlignment: Alignment.Horizontal = Alignment.Start,
    content: @Composable ColumnScope.() -> Unit
) {
    val measurePolicy = columnMeasurePolicy(verticalArrangement, horizontalAlignment)
    Layout(
        content = { ColumnScopeInstance.content() },
        measurePolicy = measurePolicy,
        modifier = modifier
    )
}

因此,您可以在 ColumnRowBox 内调用另一个 Composable

@Composable invocations can only happen from the context of a @Composable function

As this says you need to call a Composable from a function that is annotated with @Composable

If you check LazyColumn function signature

@Composable
fun LazyColumn(
    // rest of the params
    content: LazyListScope.() -> Unit
) {

}

You will see that content is not a Composable. On the other hand items function use itemContent as Composable

inline fun <T> LazyListScope.items(
    items: List<T>,
    noinline key: ((item: T) -> Any)? = null,
    noinline contentType: (item: T) -> Any? = { null },
    crossinline itemContent: @Composable LazyItemScope.(item: T) -> Unit
) = items(
    count = items.size,
    key = if (key != null) { index: Int -> key(items[index]) } else null,
    contentType = { index: Int -> contentType(items[index]) }
) {
    itemContent(items[it])
}

Because of this you can call Composable functions like Column inside item function.

items(myItems) { myItem: MyItem ->
    Column{

    }
}

Functions like Column, Row or Box have their XScope functions marked with
@Composable

@Composable
inline fun Column(
    modifier: Modifier = Modifier,
    verticalArrangement: Arrangement.Vertical = Arrangement.Top,
    horizontalAlignment: Alignment.Horizontal = Alignment.Start,
    content: @Composable ColumnScope.() -> Unit
) {
    val measurePolicy = columnMeasurePolicy(verticalArrangement, horizontalAlignment)
    Layout(
        content = { ColumnScopeInstance.content() },
        measurePolicy = measurePolicy,
        modifier = modifier
    )
}

And because of this you can call another Composable inside a Column, Row or Box.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文