Android Anko Commons

Filed Under: Android

In this tutorial, we’ll be discussing the Anko library. We’ll be diving deep into the Anko Commons Module today.

Android Anko

Anko is an open source library that was developed by JetBrains for revolutionalizing the Android Development using Kotlin. It makes your code super small and with the improved readability, it gets closer to English poetry.

Anko was developed with the goal to extract the full benefits out of the Kotlin Syntax and make the Android Development faster and easier.

The Anko DSL library consists of the following components at the time of writing:

  • Anko Commons – This library consists of common tasks in android development. It provides helpers for intents, logging, alert dialogs, async, toasts etc.
  • Anko Layouts – Lets you quickly create layouts programmatically in a faster and easier way.
  • Anko SQLite – This provides helper functions for Android SQLite
  • Anko Coroutine – It supplies utilities based on the kotlinx.coroutines library.

We’ll be concentrating on Anko Commons in this tutorial. Let’s see what it has in store for us.

Anko Commons

To get started with using Anko Commons in your new Android Studio Project, add the following dependency in your app’s build.gradle.


implementation 'org.jetbrains.anko:anko-commons:0.10.2'

To use the Appcompat Styles, add the following dependency as well:


implementation 'org.jetbrains.anko:anko-appcompat-v7-commons:0.10.2'

Once you’ve synced your build.gradle, it is time to code!
We’ll be implementing the following things in our Android Application using Anko Commons:

  • Toasts
  • Alert Dialogs

  • Selectors
  • Intents
  • Logging
  • Miscelleaneous Helper Functions

Implementation

Let’s look at each of the utility helper functions one at a time.

Android Anko Toasts



val number = 1

toast("Hello Anko Commons")
toast(R.string.app_name)
longToast("Long Toast $number")

The above code creates helper functions for normal toast and long toast with respective time as Toast.LENGTH_SHORT and Toast.LENGTH_LONG.

Their equivalent non-anko code is:


Toast.makeText(applicationContext, "string", Toast.LENGTH_SHORT).show()
Toast.makeText(applicationContext, "string", Toast.LENGTH_LONG).show()

The codes speak for themselves on how short and easy the Anko version is.
For more details on the non-Anko Android Toasts, refer this tutorial.

Android Anko Alert Dialogs

The Anko Commons utility function for displaying an alert dialog is:


alert("You have a message!", "Android Anko Alert") {
                yesButton { toast("Yes") }
                noButton {}
                neutralPressed("Maybe") {}
            }.show()

Inside the alert block we can add the following properties too:

  • message
  • title
  • icon
  • positiveButton
  • negativeButton
  • okButton
  • cancelButton
  • onCancelled{ }
  • customTitle{ } – Here we can add an Anko Layout for the title layout. We’ll look into this in the next tutorial.
  • customView { } – Here we can set a custom view using Anko Layouts. More on this in the next tutorial.

The non-Anko code for Alert Dialogs is:


val builder = AlertDialog.Builder(this)
        
        with(builder)
        {
            setTitle("Androidly Alert")
            setMessage("We have a message")
            setPositiveButton("OK"){}
            setNegativeButton(android.R.string.no){}
            setNeutralButton("Maybe"){}
            show()    
        }

Anko Commons Selectors

To add a list of items inside the Alert Dialog we use the selector syntax as shown below:


val languages = listOf("Java", "Python", "Kotlin", "Swift")
            selector("Your favourite programming language?", languages, { dialogInterface, i ->
                toast("You're favourite language is ${languages[i]}, right?")
            })

Needless to say, the Anko Commons Alert Dialogs codes are much concise then the non-Anko ones discussed here.

The equivalent non-Anko code is:


val items = arrayOf("Red", "Orange", "Yellow", "Blue")
        val builder = AlertDialog.Builder(this)
        with(builder)
        {
            setTitle("List of Items")
            setItems(items) { dialog, which ->
                Toast.makeText(applicationContext, items[which] + " is clicked", Toast.LENGTH_SHORT).show()
            }

            setPositiveButton("OK", positiveButtonClick)
            show()
        }

Running a Task in background thread

We can use the doAsync utility function to run a task in background thread easily and switch back to the main thread, the UI thread to update the UI.



doAsync{
 //implement background task here
   uiThread{
   //this thread is the main thread. update the UI here.
   }
}

Android Anko Intents

We can shorten our Intents code to start activities using Anko commons.

The following is non-Anko code for Intents in Android.



val intent = Intent(this, SecondActivity::class.java)
startActivity(intent)

Anko version:


startActivity<SecondActivity>()

Setting Flags and passing values

Non-Anko Code:


val intent = Intent(this, SecondActivity::class.java)
intent.putExtra("value", 3)
intent.putExtra("name", "Androidly")
intent.setFlag(Intent.FLAG_ACTIVITY_SINGLE_TOP)
startActivity(intent)

Anko Code:


startActivity(intentFor<SecondActivity>("value" to 3, "name" to "Androidly").singleTop())

In order to pass flags, you use intentFor.

Intent Helper Functions

  • makeCall(number) – Must ask for runtime permissions. We’ll cover this later.
  • sendSMS(number, ) – Must add runtime permissions. We’ll cover this later.
  • browse(url: String) – Must set Internet Permission
  • share(text, [subject])
  • email(email, [subject], )

We’ll implement many of these in our Android Studio Project later in this tutorial.

Logging

Anko commons provides shorthand forms for various types of Logging Statements.

The non-Anko version for debug log is:

Log.d("TAG","debug")

In order to use the Anko version you must implement the interface AnkoLogger in your Activity.

And then:


info("Info log")
debug(5) //converts to string.
debug { "Each log can be written in either of these forms" }
warn(null) //shows null
verbose { "Verbose" }
wtf("Kotlin Androidly Tutorial")

Notice that there are two styles of the above functions. () and {}

Miscellaneous Functions

Following are some of the Anko Common helper functions that are commonly used for dimension conversions:

  • dip() – Converts the Int or float passed into dip
  • sp() – Converts the Int or float passed into sp value
  • px2dip() – Converts px to dip
  • px2sp() – Converts px to sp.

Let’s implement the above functions we’ve discussed in our Android Studio Project.

Project Structure

android anko commons project structure

Our Android Application will consist of two activities.

Code

The code for the layouts is given below:

activity_main.xml


<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:gravity="center"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Button
        android:id="@+id/btnShortToast"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Short Toast" />


    <Button
        android:id="@+id/btnLongToast"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Long Toast" />


    <Button
        android:id="@+id/btnSimpleAlertDialog"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Simple Alert Dialog" />


    <Button
        android:id="@+id/btnAdvAlertDialog"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Advanced Alert Dialog" />


    <Button
        android:id="@+id/btnAlertDialogWithList"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Alert Dialog With List" />


    <Button
        android:id="@+id/btnDoAsync"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="DO ASYNC" />


    <Button
        android:id="@+id/btnIntent"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Goto Next Activity" />


</LinearLayout>

activity_second.xml


<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:gravity="center"
    android:orientation="vertical"
    tools:context=".SecondActivity">

    <Button
        android:id="@+id/btnBrowseUrl"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Browse Url" />


    <Button
        android:id="@+id/btnSendEmail"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Send Email" />


    <Button
        android:id="@+id/btnShare"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Share" />


</LinearLayout>

The code for the MainActivity.kt is given below:


package net.androidly.androidlyankocommons

import android.support.v7.app.AppCompatActivity
import android.os.Bundle
import android.support.v4.content.ContextCompat
import android.support.v7.app.AlertDialog
import kotlinx.android.synthetic.main.activity_main.*
import org.jetbrains.anko.*
import org.jetbrains.anko.appcompat.v7.Appcompat

class MainActivity : AppCompatActivity(), AnkoLogger {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)


        info("Info log")
        debug(5)
        debug { "Each log can be written in either of these forms" }
        warn(null)
        verbose { "Verbose" }
        wtf("Kotlin Androidly Tutorial")

        

        btnShortToast.setOnClickListener {
            toast("Hello Anko Commons")
            toast(R.string.app_name)
        }

        btnLongToast.setOnClickListener {
            longToast("Long!")
        }

        btnSimpleAlertDialog.setOnClickListener {
            alert("You have a message!", "Android Anko Alert") {
                yesButton { toast("Yes") }
                noButton {}
                neutralPressed("Maybe") {}
            }.show()
        }

        btnAdvAlertDialog.setOnClickListener {

            alert("Anko Common Alert") {
                title = "Title"
                yesButton { toast("Yes") }
                noButton { }
                icon = ContextCompat.getDrawable(this@MainActivity, R.mipmap.ic_launcher)!!
                onCancelled {
                    val dialog = alert(Appcompat) {
                        title = "Anko Alerts"
                        message = "Don't press outside the dialog to cancel me again :)"
                        okButton { toast(android.R.string.ok) }

                    }.build()

                    with(dialog)
                    {
                        show()
                        getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(ContextCompat.getColor(ctx, R.color.colorPrimary))
                    }
                }

            }.show()
        }


        btnAlertDialogWithList.setOnClickListener {

            val languages = listOf("Java", "Python", "Kotlin", "Swift")
            selector("Your favourite programming language?", languages, { dialogInterface, i ->
                toast("Your favourite language is ${languages[i]}, right?")
            })
        }

        btnDoAsync.setOnClickListener {

            doAsync {

                Thread.sleep(2000)

                uiThread {
                    toast("This work is done after 2 seconds")
                }
            }
        }


        btnIntent.setOnClickListener {
            startActivity<SecondActivity>("name" to "Androidly", "age" to 1)
        }
    }
}

Inside the btnAdvAlertDialog we create another dialog when the dialog is canceled on touching outside.
We’ve also implemented the Alert Dialog differently wherein we get the AlertDialog instance and can do the changes on the Buttons etc.

The code for the SecondActivity.java is given below:


package net.androidly.androidlyankocommons

import android.support.v7.app.AppCompatActivity
import android.os.Bundle
import kotlinx.android.synthetic.main.activity_second.*
import org.jetbrains.anko.browse
import org.jetbrains.anko.email
import org.jetbrains.anko.share

class SecondActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_second)


        btnBrowseUrl.setOnClickListener {
            browse("https://www.androidly.net")
        }

        btnSendEmail.setOnClickListener {
            email("anupamchugh@gmail.com (mailto:anupamchugh@gmail.com)", "Test Androidly", "Message text From Androidly Application")
        }



        btnShare.setOnClickListener {

            val number = 123
            share("Hello $number", "Copy")
        }
    }
}

Do add the Internet Permission in your AndroidManifest.xml file.

The output of the above application in action is given below:

android anko commons demo

This brings an end to this tutorial. You can download the project from the link below:

Leave a Reply

Your email address will not be published. Required fields are marked *

close
Generic selectors
Exact matches only
Search in title
Search in content
Search in posts
Search in pages