← Back to list

LazyColumn & LazyRow in Jetpack Compose: Bye Bye RecyclerView 👋

In Part 1, we covered the basics of Jetpack Compose — Composables, State, and Modifiers. If you haven’t read that yet, go check it out…

Shalu Gupta · 2026-06-17 20:06 · 0 claps · 4.2 min read paywalled
#jetpack-compose #android #kotlin #androiddev #techdroidverse
Open on Medium ↗
Wiki topics: 📱 · Mobile Development

LazyColumn & LazyRow in Jetpack Compose: Bye Bye RecyclerView 👋

In Part 1, we covered the basics of Jetpack Compose — Composables, State, and Modifiers. If you haven’t read that yet, go check it out first!

In this article, we’re tackling one of the most common things every Android app needs:

Displaying a list of items efficiently.

In the old world, this meant RecyclerView + Adapter + ViewHolder + DiffUtil + XML layouts. That's a LOT of boilerplate just to show a list.

In Compose? Two words: LazyColumn and LazyRow.

What’s Wrong with a Regular Column?

You might be thinking — “We already have Column in Compose. Why do we need something else?"

Great question! Here’s the problem:

// ❌ Don’t do this for long lists! Column { items.forEach { item -> Text(text = item) } }

A regular Column renders ALL items at once — even the ones off screen. If you have 1000 items, it creates 1000 Text composables in memory immediately.

This is slow. It will lag. Your users will notice.

LazyColumn solves this by only rendering items that are currently visible on screen — just like RecyclerView did, but with far less code.

Meet LazyColumn

LazyColumn renders a vertical scrollable list and only composes items as they appear on screen. Items that scroll off are automatically disposed.

Here’s the simplest example:

**@Composable fun FruitList() { val fruits = listOf(“🍎 Apple”, “🍌 Banana”, “🍊 Orange”, “🍇 Grapes”, “🍓 Strawberry”)**

LazyColumn { items(fruits) { fruit -> Text( text = fruit, modifier = Modifier .fillMaxWidth() .padding(16.dp), fontSize = 18.sp ) } } }

That’s it. No Adapter. No ViewHolder. No XML layout file. Just a function.

Meet LazyRow

LazyRow does the exact same thing — but horizontally. Perfect for carousels, category chips, or image sliders.

**@Composable fun CategoryChips() { val categories = listOf(“Android”, “Kotlin”, “Compose”, “Java”, “DSA”, “Go”)**

LazyRow( contentPadding = PaddingValues(horizontal = 16.dp), horizontalArrangement = Arrangement.spacedBy(8.dp) ) { items(categories) { category -> Surface( shape = RoundedCornerShape(50), color = MaterialTheme.colorScheme.primaryContainer ) { Text( text = category, modifier = Modifier.padding(horizontal = 16.dp, vertical = 8.dp) ) } } } }

The items() Block — Your Best Friend

Inside LazyColumn and LazyRow, you use special DSL functions to add content:

Function What it does

items(list)Renders each item in a list

item { }Renders a single item (e.g. a header)

items(count)Renders N items by index

itemsIndexed(list)Renders items with their index

Example: Header + List with itemsIndexed

@Composable fun NumberedList() { val languages = listOf(“Kotlin”, “Java”, “Go”, “Python”, “Swift”)

LazyColumn { item { Text( text = “Programming Languages”, style = MaterialTheme.typography.headlineMedium, modifier = Modifier.padding(16.dp) ) }

itemsIndexed(languages) { index, language -> Text( text = “${index + 1}. $language”, modifier = Modifier .fillMaxWidth() .padding(horizontal = 16.dp, vertical = 8.dp) ) } } }

Building a Real-World Card List

Let’s build something closer to a real app — a list of user profile cards:

data class User(val name: String, val role: String, val emoji: String)

**@Composable fun UserList() { val users = listOf( User(“Rahul Sharma”, “Android Developer”, “👨‍💻”), User(“Priya Singh”, “UI/UX Designer”, “🎨”), User(“Amit Patel”, “Backend Engineer”, “⚙️”), User(“Sneha Gupta”, “Product Manager”, “📋”), User(“Vikram Nair”, “DevOps Engineer”, “🚀”) )**

LazyColumn( contentPadding = PaddingValues(16.dp), verticalArrangement = Arrangement.spacedBy(12.dp) ) { items(users) { user -> UserCard(user) } } }

**@Composable fun UserCard(user: User) { Card( modifier = Modifier.fillMaxWidth(), elevation = CardDefaults.cardElevation(defaultElevation = 4.dp) ) { Row( modifier = Modifier.padding(16.dp), verticalAlignment = Alignment.CenterVertically ) { Text(text = user.emoji, fontSize = 40.sp) Spacer(modifier = Modifier.width(16.dp)) Column { Text(text = user.name, style = MaterialTheme.typography.titleMedium) Text(text = user.role, style = MaterialTheme.typography.bodySmall) } } } }**

Clean, readable, and efficient — no matter how many users are in the list.

Key Parameters You Should Know

contentPadding

Adds padding around the entire list (not individual items):

LazyColumn( contentPadding = PaddingValues(horizontal = 16.dp, vertical = 8.dp) ) { … }

verticalArrangement / horizontalArrangement

Adds spacing between items automatically:

LazyColumn( verticalArrangement = Arrangement.spacedBy(8.dp) ) { … }

reverseLayout

Starts the list from the bottom — useful for chat apps:

LazyColumn(reverseLayout = true) { … }

RecyclerView is powerful, but LazyColumn gives you 90% of the capability with 20% of the effort.

Common Beginner Mistakes

❌ Using a regular Column for long lists Always use LazyColumn when your list has more than ~20 items or unknown length.

❌ Forgetting the key parameter For better performance and correct animations, provide a unique key for each item:

items(users, key = { user -> user.name }) { user -> UserCard(user) }

Without key, Compose can't track which item changed and may redraw more than necessary.

❌ Nesting a LazyColumn inside a scrollable Column This causes a conflict — two scrollable containers fighting each other. Keep it to one.

What’s Next in This Series?

Now that you can render lists like a pro, here’s what’s coming up:

  1. Jetpack Compose BasicsPublished
  2. LazyColumn & LazyRowYou are here
  3. 🔜 Navigation Compose — Moving between screens
  4. 🔜 ViewModel + StateFlow — Managing state properly at scale
  5. 🔜 Material 3 — Google’s design system in Compose
  6. 🔜 AnimationsAnimatedVisibility, animateColorAsState, and more

Final Thoughts

LazyColumn and LazyRow are the workhorses of any real Android app. Once you get comfortable with them, you'll be amazed at how much faster you can build compared to the old RecyclerView approach.

The key takeaway? Lazy = efficient. Only render what the user can see.

Try building a simple contacts list or a news feed today — you’ll have it running in under 30 minutes. 🚀

🎥 Want to Go Deeper? Subscribe to TechDroidVerse!

If this article helped you, you’re going to love the TechDroidVerse YouTube channel.

I cover everything a modern developer needs to know — including:

  • Java — from the basics all the way to advanced concepts
  • 🧠 DSA (Data Structures & Algorithms) — explained simply, so interviews don’t scare you
  • 🐹 Go (Golang) — the fast, clean language taking the backend world by storm

Whether you’re just starting out or leveling up your skills, there’s something for you.

👉 **Subscribe to TechDroidVerse on YouTube** — it’s free, and it might just be the best thing you do for your dev career today.

If this helped you, consider following for more beginner-friendly Android development content. Drop a comment with what you’re building — I’d love to hear!


메타데이터
post_id
b6bbba292402
slug
lazycolumn-lazyrow-in-jetpack-compose-bye-bye-recyclerview-b6bbba292402
url
https://medium.com/@info.shaludroid/lazycolumn-lazyrow-in-jetpack-compose-bye-bye-recyclerview-b6bbba292402
canonical_url
https://medium.com/@info.shaludroid/lazycolumn-lazyrow-in-jetpack-compose-bye-bye-recyclerview-b6bbba292402
author_url
https://medium.com/@info.shaludroid
status
ok
fetched_at
2026-06-20 20:29:01