Lists and grids in JetPack Compose

ListView In Jetpack Compose

  • Similar to ListView it will create all view objects at once irrespective of whether the user is viewing that particular view or not.
  • We can add a vertical scroll to items in the column. It will not be enabled by default.
  • We need to use the function rememberScrollState() to remember the scroll position of column items

ListView using Column (Screenshot)

ListView using Column (Code)

fun ScrollableColumn() {
val scrollState = rememberScrollState()
modifier = Modifier.verticalScroll(scrollState)
) {
for(i in 1..100) {
Text(text = "This is person $i", style = MaterialTheme.typography.h3,
modifier = Modifier.padding(10.dp)
Divider(color = Color.Black, thickness = 5.dp)
  • We are displaying 100 person names using a for loop
  • We are adding vertical scroll manually using verticalScroll() method. It is not enabled by default.
  • Similarly, we are using the rememberScrollState() method to remember the scroll position of column items

RecyclerView in Jetpack Compose

  • Similar to the recycler view, the lazy column recycles view objects that are not visible to the user to display new data.
  • You will see a much smoother transition in the lazy column compared to column items as it creates views on demand.
  • For the recycler view, we need to create a layout file to hold the recycler view, then we need to create another layout file for its items. Then we need to create an adapter class to populate the recycler view.
  • In Jetpack Compose we need not create these many files, We need only one function lazy column to create a recycler view and populate it with data.

RecyclerView using LazyColumn (Screenshot)

RecyclerView using LazyColumn (Code)

fun LazyColumnDemo(selectedItem: (String)->Unit) {
LazyColumn(verticalArrangement = Arrangement.spacedBy(4.dp)) {
items(100) {
Text(text = "This is person $it", style = MaterialTheme.typography.h3,
modifier = Modifier
.clickable { selectedItem("selected $it person") }
Divider(color = Color.Black, thickness = 5.dp)
  • Here we are using the LazyColumn method to display 100 persons' names.
  • We have also added a click function to each item using the clickable method.
  • When a user clicks on any item it will display a toast message with the person's name.
  • We are using Arrangement.spacedBy() to add 4.dp of vertical space between each item. Grids support both horizontal and vertical spacing.

Lazy grids in Jetpack Compose

  • Using lazy vertical grid items are scrollable and span across multiple columns.
  • Lazy horizontal grid will have the same features in the horizontal axis.

Grids using Lazy grids (Screenshot)

Grids using Lazy grids (Code)

fun LazyVerticalGridDemo() {

LazyVerticalGrid(columns = GridCells.Adaptive(minSize = 128.dp),
contentPadding = PaddingValues(
start = 12.dp,
top = 16.dp,
end = 12.dp,
bottom = 16.dp
content = {
items(100) {
backgroundColor = Color.Red,
modifier = Modifier
elevation = 8.dp,
) {
text = "$it",
fontWeight = FontWeight.Bold,
fontSize = 30.sp,
color = Color(0xFFFFFFFF),
textAlign = TextAlign.Center,
modifier = Modifier.padding(16.dp)
  • Here we are using LazyVerticalGrid to display nos across multiple columns
  • GridCells.Adaptive(minSize = 128.dp) specifies each column should be of 128 widths. Based on this width no of columns is calculated and extra space is distributed between columns.
  • We can use GridCells.Fixed(2) to display fixed 2 columns in 1 row.
  • Lazy components provide contentPadding which is used to add padding to the edges of the content. So these padding values will not be between each item but the content as a whole.

Item keys

  • So when an item is added dynamically, the item position changes due to which its remembered state is lost.
  • As a result, the user will lose its scroll positions for the item in a column or row whichever item is changed.
  • To combat these you can use a key parameter for each item and provide a key with a value unique to the item.
  • This way even if a new item is added or the old item is removed, the item state will remain intact and there will be no errors with a smooth user experience.

Sticky headers (experimental)

  • It will add a header at the top of each group.
  • Ex — For the contacts application you can group your contacts according to their initials like — “a”,”b”,”c” etc, and have a header “a”..”b”..”c” for each group.
  • You can implement this using stickyHeader() function.



Android Developer Infosys | ex-Deloitte

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store