赞
踩
Jetpack Compose是Google I/O 2019 发布的Andorid UI框架,它不同于Andorid常见的Xml+命令式Coding的UI开发范式,而是基于Kotlin的DSL实现了一套类似React的声明式UI框架。Jetpack Compose目前仍然处于pre-alpha版本,目标是2020年能够发布稳定的Beta版本。伴随React Native、Flutter等大前端框架的兴起以及Jetpack Compose、SwiftUI等native框架的出现,声明式UI正逐渐成为客户端UI开发的新趋势。我们通过一个小sample来学习和体验一下Jetpack Compose带来的新的开发方式
由于Jetpack Compose还未正式发布,需要使用Preview版的AndroidStudio进行体验:
新建Project,选择 Empty Compose Activity
Compose的API非常友好,通过为函数添加@Composable注解,将其声明为一个可以在DSL中使用的UI组件。之后在Activity中可以通过setContent{...}方法使用DSL声明UI布局:
- //MainActivity.kt
- class MainActivity : AppCompatActivity() {
-
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
- setContent {
- Greeting(name = "Android")
- }
- }
- }
-
- @Composable
- fun Greeting(name: String) {
- Text (text = "Hello $name!")
- }
从Android Studio4.0 Canary1起,可以在IDE中对@Comopse组件进行预览。在@Compose函数上添加@Preview即可进行预览。需要注意的是用Compose的代码发生变更后经过build才能在预览中反映出来,不像xml的预览那么实时,这是因为compose的代码需要经过编译生成新的class后才能再次运行从而生效,而xml的变动是无需经过编译的。
另外需注意的是@Preview的组件不能有参数,所以Greeting组件需要向下面这样进行预览
- @Composable
- fun Greeting(name: String) {
- Text (text = "Hello $name!")
- }
-
- @Preview
- @Composable
- fun PreviewGreeting() {
- Greeting("Android")
- }
在IDE中就可以预览的效果如下:
了解了基本使用之后,我们实现一个简单的Sample,用来显示文章列表:
首先,定义sample中需要使用的data class
- //Article.kt
- data class Article(
- val id: String,
- val title: String,
- val url: String,
- val user: User
- )
- //User.kt
- data class User(
- val id: String,
- val name: String,
- val profileImageUrl: String
- )
接下来实现文章列表Item的UI,由于用到了DrawImage组件,先在build.gradle中添加以下依赖
- dependencies{
- implementation 'androidx.ui:ui-foundation:0.1.0-dev03'
- }
相比传统的通过Class定义自定义控件的方式,定义Compose组件只需要定义一个function:
- @Composable
- fun ArticleItem(article: Article) {
- val image = +imageResource(R.drawable.ic_header)
- val typography = +MaterialTheme.typography()
-
- Row(modifier = Spacing(16.dp)) {
- Container(modifier = Size(60.dp, 60.dp)) {
- DrawImage(image = image)
- }
- Column(modifier = ExpandedWidth wraps Spacing(right = 16.dp, left = 16.dp)) {
- Text(article.title, style = typography.h6)
- Text(article.user.name, modifier = Spacing(top = 4.dp), style = typography.subtitle2)
- }
- }
- }
function内部可以调用其他的@Compose的function,从而实现有层级的UI。上面代码中使用到下列Compose组件:
可见,用Andorid传统的布局方式不同,ComposeI采用类似H5或Flutter中广泛使用的Flexbox布局方式。
由Item构成文章列表
- //ArticleList.kt
- @Composable
- fun ArticleList(articles: List<Article>) {
- VerticalScroller {
- Column {
- articles.forEach { article ->
- Card(
- modifier = Spacing(4.dp) wraps Expanded,
- shape = RoundedCornerShape(8.dp)
- ) {
- ArticleItem(article = article)
- }
- }
- }
- }
- }

在MainAcitity中显示文章列表:
- //MainActivity.kt
- class MainActivity : AppCompatActivity() {
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
-
- val articles = mutableListOf<Article>()
- repeat(11) {
- articles.add(
- Article(
- id = "$it",
- title = "Kotlin入门",
- url = "http://www.exsample.com/articles/$it",
- user = User(id = "123", name = "第${it}讲...", profileImageUrl = "")
- )
- )
- }
-
- setContent {
- MaterialTheme {
- ArticleList(articles = articles)
- }
- }
- }
- }

文章列表显示如下:
最后我们可以在顶部增加Toolbar,让显示效果更完善。可以通过Column将Toolbar放置在顶部:
- class MainActivity : AppCompatActivity() {
- override fun onCreate(savedInstanceState: Bundle?) {
- super.onCreate(savedInstanceState)
-
- setContent {
- MaterialTheme {
- Column {
- TopAppBar(title = {
- Text("Kotlin入门")
- })
- ArticleList(articles = articles)
- }
- }
- }
- }
- }

通过上面的sample我们了解了如何使用Jetpack Compose进行一个简单的UI布局。但Compose绝不仅仅是用来布局的工具,否则和Anko有什么区别呢?它真正强大的是包晗状态管理在内的一整套声明式UI的编程范式,关于这些的学习我们后面再另开文章介绍。Jetpack Compose吸收了很多前端框架的设计思想,例如用function替代class明显是来自React的函数式组件的灵感,这些变化会让习惯与写OOP程序的同学们有一种耳目一新的感觉,但是不可否认的是现阶段无论功能和性能上,Jetpack Compose距离”可用”还有很大一段距离,相信不久的未来Beta版的推出会给我们带来更多惊喜。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。