First off a couple of links that I have found to be useful. In no particular order:
- http://www.vogella.com/articles/AndroidActionBar/article.html
- http://wptrafficanalyzer.in/blog/adding-custom-action-view-to-action-bar-in-android/
- http://wptrafficanalyzer.in/blog/creating-custom-action-provider-in-action-bar/
- http://actionbarsherlock.com/
As background the ActionBar is a consisten title bar that can be added to an android application. The most common and basic form is to simply have an icon and a title to be used to brand your application. Recently I have had a need to do a little more than basic branding so I have had to do a lot of research.
One thing I should note is that the ActionBar is only available in Android 3.0 (sdk 11 I think) and above. Below that and you will have to either make everything custom yourself (been there, done that, did not like it) or you can use the ActionBarSherlock library which gives you all the ActionBar functionality all the way back to sdk 7.
As my application requires compatibility all the way back to at least Gingerbread (I am aiming for Froyo) I have implemented it with the sherlock library. The only different in the following code is that instead of calling getSupportActionBar() you would call getActionBar(). At least thats the only difference I have found so far.
So the google blog entry here gives a decent tutorial on how to customize the look for the action bar but for my purposes I wanted to be able to deal with things a little more dynamically. I really wanted to be able to add custom icons, buttons, and text which would change based on what the user was currently looking at. For example I have an initial landing page where I may want to have the users name displayed to let them know who is logged in. I may also want to have a button that would open a new fragment to compose an email at which point I would like the text to change to say "Compose".
So for starters, getting access to the ActionBar is a simple call:
ActionBar actionBar = this.getSupportActionBar();
or
ActionBar actionBar = this.getActionBar(); // iof you arent using Sherlock
So in order to change the text of the actin bar I can simply call
actionBar.setTitle("TITLE"); // replace the default applicaiton name with this text
The action bar also supports a subtitle which is nice although I probably wont use it much.
actionBar.setSubtitle("subtitle");// the subtitle sits below the title and is smaller font
By default the ActionBar will use your applicaiton icon in the top left corner of the action bar, but for my purposes I wanted to use that space for a different button. Specifically I wanted to use it as a menu button that would slide open a menu ont he left side of the screen similar to the way that facebook does it. Sliding the menu in is a blog entry to itself but to change the image is fairly simple. All you have to do is pass in a drawable or resource integer to the setLogo function. This can be easily achieved using styles as in the google blog but I wanted to be able to change the icon based on what the user was doing. Perhaps on the main page I would like my app icon but on the compose page I want it to switch to be a mail icon.
actionBar.setLogo(R.drawable.ic_action_menu_dark);// set the drawable
actionBar.setDisplayUseLogoEnabled(true);// this toggles between displaying app icon and custom logo
Now while changing the icon is great I also want to be able to click on it to perform actions. Android does suppor a "home as up" functionality in which the logo can be clicked on to perform an action but the drawback is that it adds a back arrow < icon beside your icon when you do this. I have yet to figure out how to get rid of that :(
// to make the "home" button clickable I have to set it as home up enables. unfortunately this adds an < indicating that you can go back which I
// dont want.
actionBar.setDisplayHomeAsUpEnabled(true);
Now the background of the ActionBar is pretty borring by default so of course you will want to set the background which is easy :)
Drawable d = getResources().getDrawable(R.drawable.ic_launcher);
actionBar.setBackgroundDrawable(d);
The drawable passed in will be stretched over the full action bar so you want to make sure your drawable is the correct size for the given screen.
The final and probably the most important feature that I figured out was the addition of a custom view to the action bar. This custom view replaces the title but leaves the logo and any added menu items.
actionBar.setCustomView(R.layout.actionbar_view);
EditText search = (EditText) actionBar.getCustomView().findViewById(R.id.searchfield);
search.setOnEditorActionListener(new OnEditorActionListener()
{
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event)
{
Toast.makeText(MainActivity.this, "Search triggered", Toast.LENGTH_LONG).show();
return false;
}
});
actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM | ActionBar.DISPLAY_SHOW_HOME);
One thing that I should add when it comes to menu items added is that most of the tutorials that I read simply assumed your phone didn't have a hardware menu button in which case your menu xml files will be added to the action bar. If you are on a device that does have a menu hardware key the menu items aren't added to the action bar. To ensure that it is added you have to add a few lines
MenuInflater inflater = getSupportMenuInflater();
inflater.inflate(R.menu.actionbar, menu);
Again I am using the sherlock support library but it should work if you just called getMenuInflator() instead
~(' ')~
Some screenshot will b more helpful..
ReplyDelete