I’ve been talking a lot about

Kotlin for Android Developers



Show me the tricks!

I’ve been talking a lot about Kotlin before in this blog, but this is a compilation of things that Kotlin can do for you to simplify Android code. This will be a set of independent examples in no particular order.

Click listeners are clean and fun to write

The lack of lambdas in Java 7 is the reason why listeners and callbacks are so awful to write. Kotlin has beautiful lambdas and a nice compatibility with Java libraries. So it’s able to map interfaces with one method into a lambda. You can just do:

myButton.setOnClickListener { navigateToDetail() }

And that’s all.

Why are layouts so difficult to inflate? Not anymore!

When you are in a adapter for instance, and you need to inflate a layout, this is the code you will have to write:

LayoutInflater.from(parent.getContext()).inflate(R.id.my_layout, parent, false);

Why parent can’t just inflate its own layouts? Well, with Kotlin you can. You can create an extension function that will do it for you:

fun ViewGroup.inflate(@LayoutRes layoutRes: Int, attachToRoot: Boolean = false): View {
    return LayoutInflater.from(context).inflate(layoutRes, this, attachToRoot)

ViewGroup now has a new inflate function that will receive a layout resource and an optional attachToRoot. With default values you can create several versions of the same function without the need of overloading the function. You can now do:

parent.inflate(R.layout.my_layout, true)

ImageView, load your image!

ImageView can’t directly load images from network. We have some libraries that create custom views, such as NetworkImageView, but this forces you to use inheritance, which can lead you to problems at some point. Now that we know we can add functions to any class, why not doing it that way?

fun ImageView.loadUrl(url: String) {

You can use the library you want inside this function. But magic is in the function itself. You now have a super-powered ImageView:



Menu switches are so ugly… Not anymore!

When overriding onOptionsItemSelected, we’ll usually create a switch with a good set of branches that always have to return true, but the last one that calls super. If there are drawer options among these actions, its even worse, because you also have to close the drawer. An alternative (just to show you what you can do, not saying it’s the best solution) could be to create extension functions that do those things for you.

First, we can create a consume function, which means that it’s consuming the event (returning true), and receives a lambda that will do the work we want to do for that branch. The same can be done for the drawer. If it consumes the event, it means that we are closing the drawer after the action is clicked:

override fun onOptionsItemSelected(item: MenuItem) = when (item.itemId) {
    R.id.action_settings -> consume { navigateToSettings() }
    R.id.nav_camera -> drawer.consume { navigateToCamera() }
    R.id.nav_gallery -> drawer.consume { loadGallery() }
    R.id.nav_slideshow -> drawer.consume { loadSlideshow() }
    else -> super.onOptionsItemSelected(item)

How these functions look?

inline fun consume(f: () -> Unit): Boolean {
    return true

And very similar for the drawer:

inline fun DrawerLayout.consume(f: () -> Unit): Boolean {
    return true

The good thing is that these functions are inline, which means that the function is substituted by the code of the function in compilation time, so it’s as efficient as writing the code directly into the place of the call.

Snacks are like toasts… but uglier

The code to show a snack from the design support library is even uglier than toasts. But we can do it better in Kotlin. We can achieve something like this:

view.snack("This is my snack")
view.snack("This snack is short", Snackbar.LENGTH_SHORT) 

And what if we have an action? No worries, Kotlin to the rescue:

view.snack("Snack message") {
    action("Action") { toast("Action clicked") }

We can create small DSLs for anything that bothers us. What we need?

inline fun View.snack(message: String, length: Int = Snackbar.LENGTH_LONG, f: Snackbar.() -> Unit) {
    val snack = Snackbar.make(this, message, length)

This first function creates the snackbar, makes the snackbar execute the extension function we are providing, and then shows itself.

That function will create the Snackbar action. This is how the action function looks:

fun Snackbar.action(action: String, color: Int? = null, listener: (View) -> Unit) {
    setAction(action, listener)
    color?.let { setActionTextColor(color) }

You can even specify a color for the text of the action. If you don’t, the default value is null, and the last line decides what to do. Don’t you love this last line?

color?.let { setActionTextColor(color) }

The code inside let will only be executed if color is not null.

I don’t have the context right now… but who cares?

In Java, when we are for instance finding a view, we have to wait until the layout of the activity is inflated until you can assign a value to a field.

And the same happens to the context. If an object is depending on the context, you need to declare the field at the beginning of the class, and then assign a value during onCreate.

With Kotlin delegation, you can just delegate the value to the lazy delegate, and the code won’t be executed until the property is first used:

override val toolbar by lazy { find<Toolbar>(R.id.toolbar) }
override val dataBase by lazy { DataBase(this) }

override fun onCreate(savedInstanceState: Bundle?) {

The find function belongs to Anko library. But you can do something similar quite easy:

inline fun <reified T : View> Activity.find(id: Int): T = findViewById(id) as T
Kotlin for Android Developers

More lambdas, more beautiness

In Java we need to create objets for everything. A good example is postDelayed, where you need to create a complete Runnable. Kotlin interoperability just requires a lambda, and it’s much nicer and readable:

view.postDelayed({ doWhatever() }, 200)

And what if you want to create a thread that runs something?

Thread().run { 
    // Running in a thread    

“I hate AsyncTasks!!”. Well, then don’t use them

Thanks to Anko library, we also have a small DSL to deal with background tasks.

async() {
    // Do something in a secondary thread
    uiThread {
        // Back to the main thread

It is also context aware, so if it’s called inside an activity, the uiThread part won’t be called if the activity is finishing.

Why is dealing with collections so difficult? Not anymore

The short answer is the lack of lambdas and functional operations. But Kotlin can work with them, so sorting, transforming, mapping or filtering are just a function call away.

return parsedContacts.filter { it.name != null && it.image != null }
        .sortedBy { it.name }
        .map { Contact(it.id, it.name!!, it.image!!) }

You can check a complete list of operations for collections

Operator overloading: let your imagination fly

Who said you can’t access to the views in a ViewGroup as if it was an array? Wouldn’t it be nice? But it must be difficult… of course not. You just need to create an extension function that acts as an operator.

operator fun ViewGroup.get(pos: Int): View = getChildAt(pos)

You can now do:

val view = viewGroup[2]

You could even create an extension property that returns a list of the views:

val ViewGroup.views: List<View>
    get() = (0 until childCount).map { getChildAt(it) }

Now you have a direct access to the views:

    val views = viewGroup.views

Fed up with so many getters, setters, toString(), equals()…?

Data classes in Kotlin give all this for you.

data class Person(val name: String, val surname: String, val age: Int) 

We’re done here.

Starting activities the easy way

Anko also provides some nice functions to navigate to other activity without the need of creating an intent, adding the extras, calling the function… Everything can be done in a single line:

startActivity<DetailActivity>("id" to 2, "name" to "Kotlin")

This will create a set of extras for the intent with the values specified by the list of pairs the function is receiving as a parameter.

Android Extensions, or how to forget about findViewById

With Kotlin Android Extension, just by adding a specific import, the plugin will be able to create a set of properties for an activity, a fragment, or even a view, so that you don’t have to worry about declaring or finding those views. The name of the properties will be the ones defined in the XML you are importing. So for instance, in a RecyclerView adapter, you could do this in the ViewHolder:

import kotlinx.android.synthetic.main.item_contact.view.*


fun bindContact(contact: Contact) {
    itemView.name.text = contact.name
    itemView.setOnClickListener { listener(contact) }

But this can be cleaner. If you’re using the same variable several times, you can use some functions from the standard library, such as apply:

fun bindContact(contact: Contact) = itemView.apply {
    name.text = contact.name
    setOnClickListener { listener(contact) }

Shut up and take my money!

This is a sneak peek of what Kotlin can do for you. Many of these things are just a syntactic sugar that improves readiness, helps write cleaner code, avoids boilerplate and, the most important thing, makes you feel like a ninja.

Kotlin has many other awesome features you’d love to learn. The language is really fun and creative, it’s pragmatic (just a small set of incredible features) and it’s totally integrated with Android development.

So I recommend you to take a look at the book and get it now.

Kotlin for Android Developers

Author: Antonio Leiva

I’m in love with Kotlin. I’ve been learning about it for a couple of years, applying it to Android and digesting all this knowledge so that you can learn it with no effort.

%d bloggers like this: