Jetpack Compose 架构层
基本架构层
Jetpack Compose 不是一个单体式项目,而是由多层模块组合而成的完整堆栈。了解这些层次结构可以帮助你:
- 使用适当的抽象级别构建应用
- 了解何时可以"降级"到较低级别获取更多控制权
- 最小化依赖项
Compose 的主要架构层(从下到上):
1. 运行时(Runtime)
提供 Compose 的基本组件,如 remember、mutableStateOf、@Composable 注解和 SideEffect。如果你只需要 Compose 的树管理功能而不需要界面,可以直接基于此层构建。
2. 界面(UI)
包含多个模块(ui-text、ui-graphics 和 ui-tooling 等),实现界面工具包的基本组件,如 LayoutNode、Modifier、输入处理、自定义布局和绘图。如果只需要界面工具包的基本概念,可以基于此层构建。
3. 基础(Foundation)
为 Compose 界面提供与设计系统无关的构建块,如 Row、Column、LazyColumn 和特定手势识别。你可以基于此层构建自己的设计系统。
4. Material
提供 Material Design 系统的实现,包括主题系统、样式化组件、涟漪效果和图标。在应用中使用 Material Design 时,基于此层构建最为合适。
设计原则
1. 精细化组合
Compose 提供可组合的小块功能,而非几个单体式组件。高级组件提供更多功能但控制权较少,你可以"降级"到低级组件获取更多控制:
// 高级 API
val color = animateColorAsState(if (condition) Color.Green else Color.Red)
// 低级 API(提供更多控制)
val color = remember { Animatable(Color.Gray) }
LaunchedEffect(condition) {
color.animateTo(if (condition) Color.Green else Color.Red)
}
2. 自定义能力
通过组合小构建块,可以轻松按需自定义组件。例如,Material 的 Button 由 4 个组件组合而成:
@Composable
fun Button(
// …
content: @Composable RowScope.() -> Unit
) {
Surface(/* … */) {
CompositionLocalProvider(/* … */) { // set LocalContentAlpha
ProvideTextStyle(MaterialTheme.typography.button) {
Row(/* … */ content = content)
}
}
}
}
Button 组合了:
- Material
Surface:提供背景、形状和点击处理 CompositionLocalProvider:在启用/禁用按钮时更改内容透明度ProvideTextStyle:设置默认文本样式Row:为按钮内容提供默认布局
3. 按需自定义
当需要超出组件参数的自定义时,可以"降级"到某一层级创建自己的组件:
@Composable
fun GradientButton(
// …
background: List<Color>,
modifier: Modifier = Modifier,
content: @Composable RowScope.() -> Unit
) {
Row(
// …
modifier = modifier
.clickable(onClick = {})
.background(Brush.horizontalGradient(background))
) {
CompositionLocalProvider(/* … */) { // set material LocalContentAlpha
ProvideTextStyle(MaterialTheme.typography.button) {
content()
}
}
}
}
如果不想使用 Material 概念,可以进一步"降级"只使用基础层组件:
@Composable
fun BespokeButton(
// …
backgroundColor: Color,
modifier: Modifier = Modifier,
content: @Composable RowScope.() -> Unit
) {
Row(
// …
modifier = modifier
.clickable(onClick = {})
.background(backgroundColor)
) {
// No Material components used
content()
}
}
选择合适的抽象级别
Compose 以构建可重复使用的分层组件为理念,不应总是以构建低级构建块为目标。高级组件通常融入了最佳实践(如无障碍功能支持)。
例如,为自定义组件添加手势支持时,应考虑使用合适的抽象级别:
- 低级:
Modifier.pointerInput(从头开始构建) - 中级:
Modifier.draggable、Modifier.scrollable - 高级:
Modifier.swipeable
最佳实践:基于能提供所需功能的最高级别组件构建,以受益于其包含的最佳实践。
提示:如需构建自定义设计系统的示例,可参考 Jetsnack 示例。