Snippet: Animated Action Bar Items

This snippet is taken from some of the code I’ve recently released in photup, and shows you how to make an Action Bar item more noticeable, allowing you to lead the user onto the correct path.

actionbar

You can see what I mean here:

So why did I add this in photup? Well, one of the problems that I had with the selection screen was that there were many many clickable items on it:

  • Each item in the Grid is clickable twice, one for selection (the tick), and the other to ‘open’ the image (clicking the image).
  • Filter spinner at the bottom
  • Navigation Tabs.
  • Action Bar items, with overflow.

For me, the Action Bar item got lost in the melee of 29 clickable items on the screen, which meant that I had to find a way ‘promoting’ the Action Bar item, making it obvious to the user what the next step is (or isn’t). I could have simplified the UI, adding more layers of interaction, but this would have resulted in the user having to click more to achieve an action. So instead, I decided on trying to make the Action Bar item stand out more more visually.

I’m not saying this technique is needed for all apps, in fact it should be needed on very few.

How to do it

The first thing you need to do is create the layout for the item. You can pretty much add anything here, but I wanted to mimic an standard Action Bar item as much as possible:

<uk.co.senab.photup.views.UploadActionBarView
    xmlns:android="http://schemas.android.com/apk/res/android"

    <!-- If you use ActionBarSherlock: -->
    style="?attr/actionButtonStyle"
    <!-- If you're only targeting ICS (possible HC) above: -->
    style="?android:attr/actionButtonStyle"

    android:layout_width="wrap_content"
    android:layout_height="match_parent">

    <View
        android:id="@+id/v_action_upload_bg"
        android:layout_width="0px"
        android:layout_height="0px"
        android:layout_alignBottom="@+id/iv_action_upload"
        android:layout_alignLeft="@+id/iv_action_upload"
        android:layout_alignRight="@+id/iv_action_upload"
        android:layout_alignTop="@+id/iv_action_upload"
        android:background="@color/pressed_photup"
        android:visibility="gone" />

    <ImageView
        android:id="@+id/iv_action_upload"
        android:layout_width="wrap_content"
        android:layout_height="match_parent"
        android:src="@drawable/ic_action_upload"
        android:paddingLeft="12dp"
        android:paddingRight="12dp" />

</uk.co.senab.photup.views.UploadActionBarView>

You can find the source for UploadActionBarView on Github. It’s a simple class that just animates the background View on demand, and exposes the functionality via two simple methods: animateBackground() and stopAnimatingBackground().

Hooking it up

Now we have the layouts, we just need to hook it up to the Action Bar. It’s as simple as adding the android:actionLayout attribute to the menu xml entry,┬áreferencing your new layout,.

<menu xmlns:android="http://schemas.android.com/apk/res/android" >

    <item
        android:id="@+id/menu_upload"
        android:actionLayout="@layout/layout_action_upload"
        android:showAsAction="ifRoom"
        android:title="@string/upload_title"/>

</menu>

Then to start the animation, you’ll need the following in your Activity:

// Keep Reference to Action Layout
private UploadActionBarView mUploadActionView;

@Override
public boolean onCreateOptionsMenu(Menu menu) {    
    getSupportMenuInflater().inflate(R.menu.your_menu_file, menu);

    // Get MenuItem, and it's Action View
    MenuItem item = menu.findItem(R.id.menu_upload);
    mUploadActionView = (UploadActionBarView) item.getActionView();

    // onOptionsItemSelected will NOT be called for a custom View,
    // so set a OnClickListener and handle it ourselves.
    mUploadActionView.setOnClickListener(this);    
}

public void onClick(View v) {
    if (v == mUploadActionView) {
        // Action Bar item has been clicked, do something...
    }
}

// When you later want to animate the background, or stop the animate, just call:
if (null != mUploadActionView) {
    // To start the animation
    mUploadActionView.animateBackground();

   // Or to stop it
   mUploadActionView.stopAnimatingBackground();
}