Android-Compose 列表组件详解

目录

一,前言

二,LazyColumn和LazyRow的使用

[2.1 coil](#2.1 coil)

[2.2 viewmodel](#2.2 viewmodel)

[2.3 LazyColumn使用](#2.3 LazyColumn使用)

[2.4 LazyRow使用](#2.4 LazyRow使用)

[2.5 LazyVerticalGrid使用](#2.5 LazyVerticalGrid使用)

[2.6 LazyHorizontalGrid](#2.6 LazyHorizontalGrid)

三,添加外边距

四,添加间隙

五,自定义宽度span

六,粘性标题


一,前言

在传统android中我们使用的列表组件是RecyclerView,但是在Compose中是没有RecyclerView组件的,它把列表组件分为了四个:LazyColumn,LazyRow,LazyVerticalGrid,LazyHorizontalGrid。从名称可以看出,LazyColumnLazyRow 之间的区别就在于它们的列表项布局和滚动方向不同。LazyColumn 生成的是垂直滚动列表,而 LazyRow 生成的是水平滚动列表。LazyVerticalGridLazyHorizontalGrid 可组合项为在网格中显示列表项提供支持。延迟垂直网格会在可垂直滚动容器中跨多个列显示其列表项,而延迟水平网格则会在水平轴上有相同的行为。

二,LazyColumn和LazyRow的使用

2.1 coil

在compose中加载图片一般使用的是coil,下面我们介绍下coil是如何使用的:

首先在app的build.gradle中添加依赖:

bash 复制代码
implementation 'io.coil-kt:coil-compose:2.0.0-rc03'

在activity中加载网络图片:

Kotlin 复制代码
class MainActivityNew : ComponentActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            AsyncImage(model = "https://img2.baidu.com/it/u=1025320646,221016220&fm=253&app=138&f=JPEG?w=800&h=1421",
                "", 
                contentScale = ContentScale.Fit)

        }
    }
}

运行效果图:

2.2 viewmodel

viewmodel在compose中的使用与kotlin中有所不同,下面讲一下使用:

首先添加依赖:

bash 复制代码
implementation "androidx.lifecycle:lifecycle-viewmodel-compose:2.4.0"

然后创建viewmodel:

Kotlin 复制代码
class MyViewModel :ViewModel() {

    var chats by mutableStateOf(
        listOf(
            Student("伽罗","20","https://img2.baidu.com/it/u=1025320646,221016220&fm=253&app=138&f=JPEG?w=800&h=1421"),
            Student("妲己","22","https://pic.rmb.bdstatic.com/bjh/240119/081fe6fa14028b1831aa89f81a8b81191308.jpeg"),
            Student("李白","25","https://img1.baidu.com/it/u=986348615,2122549478&fm=253&app=138&f=JPEG?w=800&h=1423")
        )
    )

在activity中使用:

Kotlin 复制代码
class MainActivity : ComponentActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            MyComposeTheme {
               Column (){

                   var viewModel : MyViewModel =viewModel()
                   AsyncImage(model = viewModel.chats.get(1).image, contentDescription = "")
                 
               }
                
            }
        }
    }
}

运行效果:

2.3 LazyColumn使用

1.创建viewmodel:

Kotlin 复制代码
class ListViewModel :ViewModel() {

    var student by mutableStateOf(
        listOf(
            Student("伽罗","20","https://img2.baidu.com/it/u=1025320646,221016220&fm=253&app=138&f=JPEG?w=800&h=1421"),
            Student("妲己","22","https://pic.rmb.bdstatic.com/bjh/240119/081fe6fa14028b1831aa89f81a8b81191308.jpeg"),
            Student("李白","25","https://img1.baidu.com/it/u=986348615,2122549478&fm=253&app=138&f=JPEG?w=800&h=1423")
        )
    )
}
Kotlin 复制代码
data class Student(var name:String,var age:String,var image:String)

2.使用:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyColumn(){
              items(viewModel.student){
                  Column {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

3.运行如下:

2.4 LazyRow使用

在activity中使用:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyRow(){
              items(viewModel.student){
                  Column {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

运行效果如下:

2.5 LazyVerticalGrid使用

在activity中使用:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
           
            LazyVerticalGrid(columns = GridCells.Fixed(2), //固定两列
                content = {
                    items(viewModel.student){
                        Column {
                            Text(text = it.name)
                            Text(text = it.age)
                            AsyncImage(model = it.image,"", modifier = Modifier
                                .width(100.dp)
                                .height(300.dp), contentScale = ContentScale.Fit)
                        }
                    }
                }
            )
        }
    }
}

自适应大小宽度:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyVerticalGrid(columns = GridCells.Adaptive(100.dp),//自适应宽度
                         ){
              items(viewModel.student){
                  Column(Modifier.background(it.color)) {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

2.6 LazyHorizontalGrid

在activity中使用:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
           
            LazyHorizontalGrid(rows = GridCells.Fixed(2), //固定两行
                content = {
                    items(viewModel.student){
                        Column {
                            Text(text = it.name)
                            Text(text = it.age)
                            AsyncImage(model = it.image,"", modifier = Modifier
                                .width(100.dp)
                                .height(300.dp), contentScale = ContentScale.Fit)
                        }
                    }
                }
            )
        }
    }
}

三,添加外边距

可以使用**contentPadding = PaddingValues(horizontal = 16.dp, vertical = 8.dp)**给组件整体设置外边距:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyVerticalGrid(contentPadding = PaddingValues(horizontal = 16.dp, vertical = 8.dp), columns = GridCells.Fixed(2)){
              items(viewModel.student){
                  Column(Modifier.background(it.color)) {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

效果如下:

四,添加间隙

要为子元素之间添加空隙也很简单,指定一下arrangemntspacedBy即可

Kotlin 复制代码
horizontalArrangement = Arrangement.spacedBy(12.dp),
verticalArrangement = Arrangement.spacedBy(8.dp)
Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyVerticalGrid(columns = GridCells.Fixed(2),//固定两列
                             verticalArrangement = Arrangement.spacedBy(10.dp),//垂直间隙
                             horizontalArrangement = Arrangement.spacedBy(10.dp) //水平间隙
                         ){
              items(viewModel.student){
                  Column(Modifier.background(it.color)) {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

显示效果如下:

五,自定义宽度span

如果想让某一元素占满一行,可以使用span来实现,代码如下:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()
            LazyVerticalGrid(columns = GridCells.Adaptive(100.dp),//自适应宽度
                             verticalArrangement = Arrangement.spacedBy(10.dp),//垂直间隙
                             horizontalArrangement = Arrangement.spacedBy(10.dp) //水平间隙
                         ){
                item(span = {
                    // 占据最大宽度
                    GridItemSpan(maxLineSpan)
                }){
                    Column(Modifier.background(viewModel.one.color)) {
                        Text(text = viewModel.one.name)
                        Text(text = viewModel.one.age)
                        AsyncImage(model = viewModel.one.image,"", modifier = Modifier
                            .width(100.dp)
                            .height(300.dp), contentScale = ContentScale.Fit)
                    }
                }
              items(viewModel.student){
                  Column(Modifier.background(it.color)) {
                      Text(text = it.name)
                      Text(text = it.age)
                      AsyncImage(model = it.image,"", modifier = Modifier
                          .width(100.dp)
                          .height(300.dp), contentScale = ContentScale.Fit)
                  }
              }
            }
        }
    }
}

效果如下:

六,粘性标题

使用stickyHeader可以实现粘性标题,实现代码如下:

Kotlin 复制代码
class ListDemoActivity: ComponentActivity()  {


    @OptIn(ExperimentalFoundationApi::class)
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {

            var viewModel : ListViewModel = viewModel()

            LazyColumn(){
                stickyHeader {
                    Row(Modifier.background(Color.Gray).width(100.dp).height(50.dp)){
                        Text(text = "标题1")
                    }
                }
                items(viewModel.student){
                    Column {
                        Text(text = it.name)
                        Text(text = it.age)
                        AsyncImage(model = it.image,"", modifier = Modifier
                            .width(100.dp)
                            .height(300.dp), contentScale = ContentScale.Fit)
                    }
                }
                stickyHeader {
                    Row(Modifier.background(Color.Gray).width(100.dp).height(50.dp)){
                        Text(text = "标题2")
                    }
                }
                items(viewModel.student){
                    Column {
                        Text(text = it.name)
                        Text(text = it.age)
                        AsyncImage(model = it.image,"", modifier = Modifier
                            .width(100.dp)
                            .height(300.dp), contentScale = ContentScale.Fit)
                    }
                }
            }
        }
    }
}

运行效果如下:

相关推荐
LSL666_16 小时前
5 Repository 层接口
android·运维·elasticsearch·jenkins·repository
alexhilton20 小时前
在Jetpack Compose中创建CRT屏幕效果
android·kotlin·android jetpack
2501_940094021 天前
emu系列模拟器最新汉化版 安卓版 怀旧游戏模拟器全集附可运行游戏ROM
android·游戏·安卓·模拟器
下位子1 天前
『OpenGL学习滤镜相机』- Day9: CameraX 基础集成
android·opengl
参宿四南河三1 天前
Android Compose SideEffect(副作用)实例加倍详解
android·app
火柴就是我1 天前
mmkv的 mmap 的理解
android
没有了遇见1 天前
Android之直播宽高比和相机宽高比不支持后动态获取所支持的宽高比
android
shenshizhong1 天前
揭开 kotlin 中协程的神秘面纱
android·kotlin
vivo高启强1 天前
如何简单 hack agp 执行过程中的某个类
android
沐怡旸1 天前
【底层机制】 Android ION内存分配器深度解析
android·面试