Jetpack Compose
是用于构建原生界面的新款
Android
工具包。它可简化并加快
Android
的
UI
开发工作。使用更少的代码、强大的工具和直观的
Kotlin API
,快速构建
App
的
UI
。
目前
Jetpack Compose
为
Alpha
版。所以需要在
Android Studio
的
Canary
版本才能体验。
1. 创建
Jetpack Compose
项目
在
Android Studio Canary
版本中已经提供了
Compose
的模板,在创建项目时选择
Empty Compose Activity
模板即可。
img
至此,就完成一个
Compose
项目的创建。除此之外,我们也可以选择导入
Jetpack Compose
示例应用。
2. Compose 函数使用
Compose
是一种以函数为依托的声明式
UI
构建方式。比如在
MainActivity.kt
中显示一个文本。
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
Text("Hello Compose!")
}
}
}
hello_compose
这个与使用
XML
布局的方式差别很大,
setContent
块定义了
Activity
的布局。我们不使用
XML
文件来定义布局内容,而是调用一个
Compose
函数,比如上面的
Text
函数。然后
Jetpack Compose
使用自定义
Kotlin
编译器插件将这些
Compose
函数转换为应用的界面元素。
2.1
Compose
函数
Jetpack Compose
是围绕
Compose
函数构建的,在开发时只需描述应用界面的样式布局和数据依赖关系,而不必关注界面的构建过程。给一个函数添加
@Composable
注解即创建了一个 Compose 函数。
注意,
Compose
函数只能在其他
Compose
函数的范围内调用
。下面我们将上面示例中的
Text
移动到自定义的
Compose
函数中。
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
HelloCompose()
}
}
@Composable
fun HelloCompose() {
Text("Hello Compose!")
}
}
2.3 设置点击监听
除了使用
Text
函数,还有其它的基础函数供我们使用,比如
Button
、
Image
等。那么如何给
UI
控件设置点击监听呢?在
Compose
框架中提供了两种方式:
-
对于类似
Button
函数的这种,提供了
onClick
函数式接口供外部设置点击监听;
-
对于类似
Text
函数这种,没有提供显式接口设置的,通过
Modifier
类设置点击监听;
Button
函数设置点击事件
@Composable
fun TextButton() {
Button(
onClick = {
Log.d("Andoter", this.javaClass.name)
Toast.makeText(this@MainActivity, "Button 点击", Toast.LENGTH_SHORT).show()
}
) {
Text(text = "Hello Compose!", color = Color.Red)
}
}
通过设置
onClick
函数即可实现点击实现,注意
Button
函数本身没有设置文本内容,需要通过
Text
函数设置显示文本内容。
Text
函数设置点击事件
@Composable
fun ClickedText() {
val modifier = Modifier.clickable(onClick = {
Log.d("Andoter", this.javaClass.name)
Toast.makeText(this@MainActivity, "Button 点击", Toast.LENGTH_SHORT).show()
})
Text(text = "Hello Compose!",modifier = modifier.padding(10.dp))
}
通过
Modifier.clickable
的方式实现设置点击事件。
Modifier
类不仅能够设置点击事件,还能够设置控件的布局属性。
-
-
-
fillMaxWidth()
:使可组合项填充其父项给它的最大宽度
-
preferredSize()
:指定元素的首选宽度和高度
2.4 预览
在
Compose
框架中为
Compose
函数提供预览能力,通过给
Compose
函数添加
@Preview
注解即可进行预览。在实际的开发中,预览函数不要发布到线上,所以最佳做法是单独创建不会被应用调用的预览函数用于查看实际效果,专门的预览函数可以提高性能,并且有利于以后更轻松地设置多个预览。
(动图图片过大,无法上传,截图处理)
3. 布局
在
Jetpack Compose
中一切的元素都是围绕
Compose
函数展开,所以布局也是通过对应的内置
Compose
函数实现。
3.1
Column
和
Row
二者的特点:
这里我们以
Column
函数作为示例。
@Preview
@Composable
fun MultiText() {
Text(text = "Hello Compose!")
Text("Ant 学习 Compose!")
}
@Preview
@Composable
fun ColumnText() {
Column {
Text(text = "Hello Compose!")
Text("Ant 学习 Compose!")
}
}
通过
Column
可将组件按照竖直方向排列,预览效果对比:
column
3.2
ScrollableRow
和
ScrollableColumn
使用
ScrollableRow
或
ScrollableColumn
可使
Row
或
Column
内的元素滚动。
@Composable
fun ProductList() {
ScrollableColumn(Modifier.fillMaxSize()) {
listOf("Ant", "Andoter", "小伟").forEach { value ->
ProductDetailView(value)
}
}
}
@Composable
fun ProductDetailView(text: String) {
val image = imageResource(id = R.drawable.header)
Column(modifier = Modifier.padding(16.dp)) {
val imageModifier = Modifier
.preferredHeight(180.dp)
.clip(shape = RoundedCornerShape(5.dp))
.fillMaxWidth()
.clickable(onClick = {
Log.d("Ant", "click");
})
Image(image, modifier = imageModifier, contentScale = ContentScale.Crop)
Spacer(modifier = Modifier.preferredHeight(16.dp))
Text("Hello Compose!")
}
}
scroll_column
4.
Compose
界面结构
通过上面的介绍,对
Compose
有了一个初步的认识,那么
Compose
函数如何绘制在屏幕上的呢?以什么样的形式展示的呢?我们使用
Layout Inspector
工具查看一个
Compose
页面。
layer
通过左侧的布局结构可以发现,
Compose
框架中已经废弃原有的
View
体系中的控件(
TextView
、
Button
、
ImageView
等),而是使用
AndroidComposeView
(继承
ViewGroup
)、
ViewLayerContainer
(继承
ViewGroup
)和
ViewLayer
(继承
View
) 控件实现,其中
ViewLayer
代表每个
View
控件视图。
查看
ViewLayer
的调用关系,可以得到视图的生成关系:
LayerWrapper
→
AndroidComposeView
->
ViewLayer
。
5.
Compose
对业务的影响
Jetpack Compose
是一个适用于
Android
的新式声明性界面工具包,同时点击监听的设置方式也发生较大变化,那么对于我来说,最直观的业务影响是无法继续使用原有的插码技术进行点击事件的采集。这块需要进行调研适配。
上面提到设置点击的两种方式,本质上都是通过
Modifier
进行实现,来看下面的一个例子。
@Composable
fun ClickedText() {
val modifier = Modifier.clickable(onClick = {
Log.d("Andoter", this.javaClass.name)
Toast.makeText(this@MainActivity, "Button 点击", Toast.LENGTH_SHORT).show()
})
Text(text = "Hello Compose!", modifier = modifier.padding(10.dp))
}
通过
Modifier
给一个
Text
设置点击监听,在点击的时候弹出一个
Toast
。反编译看看最后的实现。
/* access modifiers changed from: package-private */
@Metadata(mo23161bv = {1, 0, 3}, mo23164k = 3, mo23165mv = {1, 4, 0})