Jetpack Compose布局组件&列表组件

Jetpack Compose布局组件&列表组件

1. 线性布局

概述

Compose 中的线性布局对应的是Android传统视图中的LinearLayout,不一样的地方是,Compose根据Orientation的不同又将布局分为Column和Row, Column对应传统视图LinearLayout中orientation = “vertical”的情况,Row对应传统视图LinearLayout中orientation = “horizontal”的情况.由于两者内部元素在父容器中的布局和对其方式不同,分成两个组件有助于提供类型安全的Modifier修饰符。

Column = 垂直

Row = 横向

1.1 Column
@Composable
inline fun Column(
    modifier: Modifier = Modifier,  // 修饰符
    verticalArrangement: Arrangement.Vertical = Arrangement.Top, //verticalArrangement 参数来定位子项在 Column 中的垂直位置。
    horizontalAlignment: Alignment.Horizontal = Alignment.Start, // horizontalAlignment 参数来定位子项在 Column 中的水平位置
    content: @Composable ColumnScope.() -> Unit
) {

Arrangement有如下枚举值:

Arrangement.Start // 子view排列在头部
Arrangement.End // 子view排列在尾部
Arrangement.Center // 子view排列在中间
Arrangement.SpaceBetween // 首尾没有空隙,且子view之间均匀分散
Arrangement.SpaceAround // 首尾空隙是每个子view之间空隙的一半
Arrangement.SpaceEvenly // 让每个子view之间的空隙均匀分散,包括首尾
垂直排列 Column
    ComposeDemoTheme {
        Column(
            modifier = Modifier
                .border(1.dp, color = Color.Red)
                .size(150.dp),
            verticalArrangement = Arrangement.Center
        ) {
            Text(
                text = "Hello World",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Column 是垂直",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Column 是垂直",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
        }
    }

在这里插入图片描述

垂直排列 Column 改变子的垂直方向和水平方向的位置
    ComposeDemoTheme {
        Column(
            modifier = Modifier
                .border(1.dp, color = Color.Red)
                .size(150.dp),
            verticalArrangement = Arrangement.Top,  // 改变子的垂直位置为顶部
            horizontalAlignment = Alignment.End // 改变子的水平位置为后
        ) {
            Text(
                text = "Hello World",
                style = MaterialTheme.typography.bodyLarge,
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Column 是垂直",
                style = MaterialTheme.typography.bodyLarge,
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Column 是垂直",
                style = MaterialTheme.typography.bodyLarge,
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
        }
    }

在这里插入图片描述

1.1 Row
@Composable
inline fun Row(
    modifier: Modifier = Modifier,//修饰符
    horizontalArrangement: Arrangement.Horizontal = Arrangement.Start,//水平对齐方式
    verticalAlignment: Alignment.Vertical = Alignment.Top,//垂直对齐方式
    content: @Composable RowScope.() -> Unit
){
}
水平排列 Row
    ComposeDemoTheme {
        Row(
            modifier = Modifier
                .border(5.dp, color = Color.Red)
                .size(350.dp),

        ) {
            Text(
                text = "Hello World",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.absolutePadding(10.dp,10.dp,0.dp,0.dp)
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Row是水平",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.absolutePadding(10.dp,10.dp,0.dp,0.dp)
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
            Text(
                text = "Row是水平",
                style = MaterialTheme.typography.bodyLarge,
                modifier = Modifier.absolutePadding(10.dp,10.dp,0.dp,0.dp)
//                modifier = Modifier.align(Alignment.CenterHorizontally)
            )
        }
    }

在这里插入图片描述

使用 horizontalArrangement 和 verticalAlignment 让内容居中

在这里插入图片描述

给子内容添加间距使用 Arrangement.spacedBy

在这里插入图片描述

2.Box布局

inline fun Box(
    modifier: Modifier = Modifier, // 修饰符
    contentAlignment: Alignment = Alignment.TopStart, // 内容对齐方式(水平和垂直),默认是左上角(LTR情况下)
    propagateMinConstraints: Boolean = false, // 是否将最小约束传给内部View,如果设置为true,则内容会填满Box本身
    content: @Composable BoxScope.() -> Unit // 内部布局
)
box 代码示例
fun BoxDemo() {
    ComposeDemoTheme {
        Box(
            modifier = Modifier
                .size(300.dp)
                .background(Color.Blue),
            contentAlignment = Alignment.Center,
        ) {
            Text(
                text = "1", fontSize = 20.sp, textAlign = TextAlign.Center, modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
                    .align(Alignment.Center)
            )

            Text(
                text = "2", fontSize = 20.sp, textAlign = TextAlign.Center, modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
                    .align(Alignment.BottomEnd)
            )

            Text(
                text = "3", fontSize = 20.sp, textAlign = TextAlign.Center, modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
                    .align(Alignment.BottomStart)
            )

            Text(
                text = "4", fontSize = 20.sp, textAlign = TextAlign.Center, modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
                    .align(Alignment.TopStart)
            )

            Text(
                text = "5", fontSize = 20.sp, textAlign = TextAlign.Center, modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
                    .align(Alignment.TopEnd)
            )
        }

    }
}

在这里插入图片描述

Box 添加 propagateMinConstraints = true 子会填充满Box
在这里插入图片描述

3.约束布局

Compose ConstraintLayout约束布局主要应用在构建复杂布局,避免使用ColumnRowBox多层嵌套,同时也能提高开发效率。

开始使用之前需要添加对ConstraintLayout的依赖:

    implementation "androidx.constraintlayout:constraintlayout-compose:1.0.1"
@Composable
inline fun ConstraintLayout(
    modifier: Modifier = Modifier,
    optimizationLevel: Int = Optimizer.OPTIMIZATION_STANDARD,
    crossinline content: @Composable ConstraintLayoutScope.() -> Unit
)
fun ConstraintLayoutDemo() {
    ConstraintLayout(modifier = Modifier.size(500.dp)) {
        //为每个子元素创建引用
        val (buttonRef, textRef) = createRefs()
        Button(
            onClick = { /* Do something */ },
            //将组合函数和引用关联
            modifier = Modifier.constrainAs(buttonRef) {
                //指定约束条件,现有引用parent是指ConstraintLayout
                top.linkTo(parent.top, margin = 16.dp)
            }
        ) {
            Text("Button")
        }
        Text(
            text = "Text",
            Modifier.constrainAs(textRef) {
                top.linkTo(buttonRef.bottom, margin = 16.dp)
//                centerAround(buttonRef.end)    //自己中间对齐谁的哪边
                centerHorizontallyTo(parent)    //水平居中
            }
        )
    }
}

通过linkTo函数将view与其他view或者parent约束。这里的parent指的就是ConstraintLayout本身。

constrainAs函数中的starttopendbottom分别代表view的左、上、右、下四条边,linkTo表示相互作用。

在这里插入图片描述

供居中对齐,centerTocenterHorizontallyTocenterVerticallyTo

fun ConstraintLayoutDemo2() {
    ConstraintLayout(modifier = Modifier.size(400.dp, 100.dp)) {
        val (imgRef, text1Ref, text2Ref, text3Ref) = createRefs()
        Image(
            painter = painterResource(id = R.drawable.ic_launcher_background),
            contentDescription = "image",
            modifier = Modifier
                .size(80.dp)
                .constrainAs(imgRef) {
                    top.linkTo(parent.top, margin = 10.dp)
                    start.linkTo(parent.start, margin = 10.dp)
                },
            contentScale = ContentScale.Crop
        )

        Text(
            text = "约束布局标题",
            color = Color.Blue,
            fontSize = 20.sp,
            textDecoration = TextDecoration.Underline,
            modifier = Modifier
                .constrainAs(text1Ref) {
                    start.linkTo(imgRef.end, margin = 10.dp)
                    top.linkTo(imgRef.top)
                }
        )

        Text(
            text = "约束布局副标题",
            color = Color.Blue,
            fontSize = 15.sp,
            textDecoration = TextDecoration.Underline,
            modifier = Modifier
                .constrainAs(text2Ref) {
                    start.linkTo(text1Ref.start)
                    top.linkTo(text1Ref.bottom, margin = 20.dp)
                }
        )

        Text(
            text = "垂直居中",
            color = Color.Blue,
            fontSize = 15.sp,
            textDecoration = TextDecoration.Underline,
            modifier = Modifier
                .constrainAs(text3Ref) {
                    end.linkTo(parent.end, margin = 20.dp)
                    centerVerticallyTo(parent)
                }
        )
    }
}

在这里插入图片描述

4.lazycolumn 纵向列表

fun lazyColumnDemo() {
    val list = mutableStateListOf<String>()
    repeat(20) {
        list.add(it.toString())
    }
    LazyColumn(
        modifier = Modifier.fillMaxSize(),
        verticalArrangement = Arrangement.spacedBy(24.dp),//item 间距
        contentPadding = PaddingValues(start = 5.dp, end = 5.dp),
    ) {
        item {
            Text(
                text = "列表头布局",
                fontSize = 20.sp,
                textAlign = TextAlign.Center,
                modifier = Modifier
                    .size(400.dp, 100.dp)
                    .background(Color.Yellow)
            )
        }
        items(list) {
            ConstraintLayoutDemo3(it)
        }

    }
}

在这里插入图片描述

修改 reverseLayout = true 将列表顺序反转

fun lazyColumnDemo() {
    //可触发重组的List
    val list = mutableStateListOf<String>()

    repeat(20) {
        list.add(it.toString())
    }
    LazyColumn(
        modifier = Modifier.fillMaxSize(),
        verticalArrangement = Arrangement.spacedBy(24.dp),//item 间距
        contentPadding = PaddingValues(start = 5.dp, end = 5.dp),
        reverseLayout = true
    ) {
        item {
            Text(
                text = "列表头布局",
                fontSize = 20.sp,
                textAlign = TextAlign.Center,
                modifier = Modifier
                    .size(400.dp, 100.dp)
                    .background(Color.Yellow)
            )
        }
        items(list) {
            ConstraintLayoutDemo3(it)
        }

    }
}

在这里插入图片描述

5.LazyRow 横向列表

用法与LazyColumn 一样

fun lazyRowDemo() {
    val list = mutableStateListOf<String>()
    repeat(20) {
        list.add(it.toString())
    }
    LazyRow(
        modifier = Modifier.fillMaxSize(),
        horizontalArrangement = Arrangement.spacedBy(24.dp),//item 间距
        contentPadding = PaddingValues(top = 20.dp),
    ) {
        item {
            Text(
                text = "头",
                fontSize = 15.sp,
                textAlign = TextAlign.Center,
                modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Yellow)
            )
        }
        items(list) {
            Text(
                text = it,
                fontSize = 20.sp,
                textAlign = TextAlign.Center,
                modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
            )
        }

    }
}

在这里插入图片描述

6.LazyVerticalGrid

fun LazyVerticalGridDemo() {
    val list = mutableStateListOf<String>()
    repeat(20) {
        list.add(it.toString())
    }
    LazyVerticalGrid(
        columns = GridCells.Fixed(3),
        horizontalArrangement = Arrangement.spacedBy(10.dp),//item 间距
        verticalArrangement = Arrangement.spacedBy(10.dp),
        contentPadding = PaddingValues(10.dp)
    ) {

        item {
            Column {
                Button(modifier = Modifier.fillMaxWidth(), onClick = { list.add("21") }) {
                    Text(text = "新增数据")
                }
            }
        }

        items(list) {
            Text(
                text = it,
                fontSize = 20.sp,
                textAlign = TextAlign.Center,
                modifier = Modifier
                    .size(50.dp, 50.dp)
                    .background(Color.Gray)
            )
        }
    }

}

在这里插入图片描述

  • 7
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值