Android Quick Tips #8 — How to Dynamically Tint Actionbar Menu Icons

We're continuing our Android Quick Tips series with a practical topic. In this short blog post we'll show you how to dynamically tint your action bar menu item icons.

If you're interested in our previous Android Quick Tips, take a look:

Android Quick Tips #1 Series Overview

Dynamically Tinting Menu Items

If you're developing an Android app, you most likely are using menu items in the actionbar, similar to this:

Actionbar Item

As you know, you would need a XML resource describing your menu. For the screenshot and the following examples, we created the following simple menu:

<menu xmlns:android="http://schemas.android.com/apk/res/android"  
      xmlns:app="http://schemas.android.com/apk/res-auto"
      xmlns:tools="http://schemas.android.com/tools"
      tools:context=".MainActivity">

    <item
        android:id="@+id/action_delete"
        android:icon="@android:drawable/ic_delete"
        android:title="Delete"
        app:showAsAction="ifRoom"/>

</menu>  

Next, we'll need to create the menu in the activity. That is also standard Android code:

public class MainActivity extends AppCompatActivity {

    ...

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.menu_main, menu);

        return true;
    }

    ...
}

Alright, that's the basics of adding a menu item to your actionbar. In our case, we're using a standard drawable as the icon. Unfortunately, this comes only in a red color. If you need any other color, you'll have to send it off to your designer to get it redesigned in the new color you need.

But no anymore! This tiny snippet of the tintMenuIcon() method will take the icon of an actionbar menu item and apply a new color to it:

public static void tintMenuIcon(Context context, MenuItem item, @ColorRes int color) {  
    Drawable normalDrawable = item.getIcon();
    Drawable wrapDrawable = DrawableCompat.wrap(normalDrawable);
    DrawableCompat.setTint(wrapDrawable, context.getResources().getColor(color));

    item.setIcon(wrapDrawable);
}

We've made the function static, so you can move it into a utils class and call it from any place in your app. We'll also pass the menu item and our wished color. Of course, you can pass any color to it. You can make the decision at runtime!

The missing last piece is when to call the tintMenuIcon() function. We recommend doing it in the onCreateOptionsMenu() function:

@Override
public boolean onCreateOptionsMenu(Menu menu) {  
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.menu_main, menu);

    MenuItem menuItem = menu.findItem(R.id.action_delete);

    if (menuItem != null) {
        tintMenuIcon(MainActivity.this, menuItem, android.R.color.holo_purple);
    }

    return true;
}

The menu.findItem() will get the specific menu item you need. Then, if Android found it, it'll pass the item along with the wished color to our tintMenuIcon() function.

Colored Actionbar Item

Of course, you can color multiple menu items using the same technique:

@Override
public boolean onCreateOptionsMenu(Menu menu) {  
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.menu_main, menu);

    MenuItem menuItemDelete = menu.findItem(R.id.action_delete);
    MenuItem menuItemAdd = menu.findItem(R.id.action_add);

    if (menuItemDelete != null) {
        tintMenuIcon(MainActivity.this, menuItemDelete, android.R.color.holo_purple);
    }

    if (menuItemAdd != null) {
        tintMenuIcon(MainActivity.this, menuItemAdd, android.R.color.holo_green_dark);
    }

    return true;
}

We hope this snippet is helpful to you. Our designer has less time-consuming tasks of providing the same drawable in multiple colors and we don't have to wait for drawables anymore! Awesome :)

If this snippet was helpful to you and you'd like more of these Quick Tips, let us know in the comments!

Explore the Library

Find interesting tutorials and solutions for your problems.