Working with RecyclerView and multiple view types

Paul Núñez
3 min readMay 13, 2017

--

Applications that contains different views in the same list are really common (i.e: Twitter, Goodreads, New York Times…) and we should know how to create them with ease.

In this post is assumed that you understand the basics of creating a list using RecyclerViews. You should also read, if you haven’t, a great post by Jon F Hancock, “Your ViewHolders are Dumb. Make ’em Not Dumb” a good practice implemented in this post.

The code examples are written in Kotlin to keep it short, but as this language is really readable, this shouldn’t be an issue for the reader.

First things first: The model

We have to define our model classes, for this example, we are going to have a list that contains multiple updates feeds from our friends, each one with a different view. And for this we need a base Update class from which all the others update types are going to inherit and an User class from the user performing the update.

The User class (and yes, that’s all you need for defining a class in Kotlin):

data class User(
var id: String,
var name: String,
var imageUrl: String,
var profileUrl: String)

The Update classes:

abstract class Update(
val updateType: String,
val updateUser: User,
val updateTime: String) {

class TYPE {
companion object {
val NEW_FRIEND = "friend"
val COMMENT = "comment"
val READ_STATUS = "readstatus"
val USER_STATUS = "userstatus"
val REVIEW = "review"
}
}
}
data class ReviewUpdate(
val user: User,
val updatedAt: String,
val rating: String,
val book: Book
) : Update(Update.TYPE.REVIEW, user, updatedAt)
data class NewFriendUpdate(
val user: User,
val updatedAt: String,
val newFriendImageUrl: String,
val newFriendName: String
) : Update(Update.TYPE.NEW_FRIEND, user, updatedAt)

In our abstract Update class we have an inner TYPE class with various constants, this will let us know what kind of update we are receiving at the moment. That string constant is passed with the corresponding type to the Update super constructor each time we extended it:

: Update(Update.TYPE.NEW_FRIEND, user, updatedAt)

Creating our Updates Adapter

Normally when we create our custom adapter we specify to the parent adapter a custom view holder that it has to use, like this:

RecyclerView.Adapter<MyCustomViewHolder>

Our custom view holder will always extend RecyclerView.ViewHolder. But as we will be working with multiple view holder classes we have to use the parent class abstraction.

RecyclerView.Adapter<RecyclerView.ViewHolder>

I will show you the final implementation and explain each step below.

  • The companion object: is the way that we create constants in Kotlin. These two constants are types of views the adapter is going to handle. These are used to know which layout are we going to inflate and which view holder is going to be returned in the onCreateViewHolder.
  • getItembyType: this returns the view type of the update item at a position. Here we use a when (Kotlin’s switch with super powers) to check the Update type and return the corresponding type constant.
  • onCreateViewHolder: as you know this is were we inflate our views and return our ViewHolder so the RecyclerView can later put it on screen. In this case, we only need to check which view type we are receiving and return the correct custom ViewHolder.
  • onBindViewHolder: here we just send the update item from the updateList to the view holder. Using a bindView method implemented on each ViewHolder, more on this in the next section.

Creating our custom ViewHolders

To be able to keep things easy and clean, we are going to create a UpdateViewHolder interface that all our custom ViewHolders must implement. This way we can guarantee the same behavior between different ViewHolder classes.

As said before, in the onBindViewHolder method, we are calling bindView in the ViewHolders after being cast to UpdateViewHolder, because we should always depend on abstraction and not concrete implementations ;). In this

This provides an easy way to handle multiple view types with RecyclerViews. There are many ways to tackle this, one really cool one is explained by Juan Ignacio Saravia using Delegate Adapters, you should also check that out!

Conclusion

RecyclerView is a very powerful widget, and understanding how we can use it can save us a lot of time. I know that getting your hands on new things can be challenging for someone new, and that’s why I wanted to talk about this.

Hope you enjoyed this post, you can follow me on twitter @paulnunezm and let me know what you think there.

--

--

Paul Núñez

Trying to ship better code a Bit at a time @Pinger. Mostly write about Android development. Dominican 🇩🇴🌴.