如何使用Jetpack Compose创建GridView

时间:2019-10-28 18:32:52

标签: android android-jetpack-compose

如何在不使用回收器视图或android.widget.gridview的情况下在Jetpack compose中创建Gridview?

6 个答案:

答案 0 :(得分:7)

另一个基于LazyColumnFor(Jetpack Compose版本1.0.0-alpha04)的解决方案

@Composable
fun <T> LazyGridFor(
    items: List<T>,
    rowSize: Int = 1,
    itemContent: @Composable BoxScope.(T) -> Unit,
) {
    val rows = items.chunked(rowSize)
    LazyColumnFor(rows) { row ->
        Row(Modifier.fillParentMaxWidth()) {
            for ((index, item) in row.withIndex()) {
                Box(Modifier.fillMaxWidth(1f / (rowSize - index))) {
                    itemContent(item)
                }
            }
        }
    }
}
    
@Preview("LazyGridFor: example")
@Composable()
fun LazyGridForPreview() {
    val data = (1..100).map(Integer::toString)
    LazyGridFor(data, 3) { item ->
        Text(item)
    }
}

答案 1 :(得分:5)

正如@Pavel Marchenko 提到的,LazyVerticalGrid 是从版本 1.0.0-alpha09 中添加的

这是一个简单的例子:

    LazyVerticalGrid(
        cells = GridCells.Adaptive(96.dp),
        contentPadding = PaddingValues(16.dp),
    ) {
        items(bookList) { book ->
            Image(book.cover, modifier = Modifier.padding(8.dp))
        }
    }

答案 2 :(得分:3)

您可以使用Table版式,将其子级排列成行和列

类似的东西:

@Composable
fun table(){

    Padding(2.dp) {
        Table(columns = 8) {

            for (i in 0 until 8) {
                tableRow {
                    for (j in 0 until 8) {
                        Padding(2.dp) {
                            //Cell
                            Text("TX")
                        }
                    }
                }
            }
        }
    }
}

enter image description here

答案 3 :(得分:1)

我创建了一个自适应网格布局:

预览

Jetpack compose adaptative grid layout landscape|tablette

Jetpack compose adaptative grid layout

代码

await data.forEachAsync((key, value) async {
    ...
});

完整代码为here

我决定实现我自己的自适应网格布局,因为现有的 LazyVerticalGrid 是实验性的,将来可以删除,要使用它,您必须递归地注释使用它的可堆肥与 @ExperimentalFoundationApi :

LazyColumn(modifier = modifier) {
            ...
            val numberOfItemsByRow = LocalConfiguration.current.screenWidthDp / 200 // you can replace 200 by the minimum size you want your cells to have.

            items(items = trendingGameList.chunked(numberOfItemsByRow)) { rowItems ->
                Row(
                    horizontalArrangement = Arrangement.spacedBy(14.dp),
                    modifier = Modifier.padding(horizontal = 16.dp),
                ) {
                    for (game in rowItems) {
                        GameCard(game = game, onClick = { }, modifier = Modifier.weight(1F))
                    }
                }
                Spacer(Modifier.height(14.dp))
            }
            ...
        }

OR 使用需要 @ExperimentalFoundationApi @Composable fun A { LazyVerticalGrid { ... } } @ExperimentalFoundationApi @Composable fun B { A {..} } @ExperimentalFoundationApi @Composable fun C { B {..} } ... 编译器参数的 @OptIn(ExperimentalFoundationApi::class)

答案 4 :(得分:0)

我创建了一个自定义gridview以使用android jetpack compose,直到他们不支持Compose中Gridlayout的官方recycleview。

@Composable
fun <T> GridView(
cols: Int = 0,
list: List<T>,
child: @Composable() (dataModal: T) -> Unit
) {

val rows = (list.size / cols) + (if (list.size % cols > 0) 1 else 0)
VerticalScroller(modifier = 
Modifier.fillMaxHeight().fillMaxHeight().drawBackground(color = colorResource(
    id = R.color.color_bg_application
))) {
    Table(columns = cols) {
        for (r in 0 until rows) {
            tableRow {
                for (c in 0 until cols) {
                    //Cell
                    val i = (r * cols) + c
                    if (i < list.size) {
                        child(list[i])
                    } else {
                        break
                    }
                }
            }
        }

    }
}
}

使用

 GridView(cols = 4, list = model.list,child = { Item( it) })

项目声明

@Composable
fun Item(t: T) {
....
}

答案 5 :(得分:0)

对@Madhav的答案进行了几处更改(使用compose v1.0.0-alpha01):

@Composable
fun <T> GridView(
        cols: Int = 1,
        list: List<T>,
        rowModifier: Modifier = Modifier,
        colModifier: Modifier = Modifier,
        child: @Composable (dataModal: T) -> Unit
) {

    val rows = (list.size / cols) + (if (list.size % cols > 0) 1 else 0)
    
    ScrollableColumn(modifier = colModifier) {
        
        for (r in 0 until rows) {
            Row(modifier = rowModifier, horizontalArrangement = Arrangement.SpaceAround) {
                for (cell in 0 until cols) {
                    val i = (r * cols) + cell
                    if (i < list.size) { child(list[i]) } else { break }
                }
            }
        }
    }

}

用法

GridView(cols = 2, list = listOf("1", "2", "3", "4",)) {
     Text(text = it)
}