今天就来了解下ActionBar相关的知识,这里十分感谢郭神的博客
关于ActionBar大致的简单使用为:
- Action Bar 的添加和移除
- Action Bar 一些简单操作,如修改文字,图标等,
- 添加Action按钮,注意menu文件中各个按钮的摆放,如always,never,ifRoom
- 响应添加的Action按钮事件
- 添加Action View
- Action Bar 的导航
- 特殊:overflow不显示的情况,overflow列表中显示图片的情况
1、ActionBar的添加
非常简单,只需要在AndroidManifest.xml中指定Application或Activity的theme是Theme.Holo或其子类就可以了。
2、Action Bar的隐藏
在Activity中获取Actionbar然后通过hide方法来隐藏。
ActionBar actionBar =getActionBar();
actionBar.hide();
3、修改Action Bar相关的标题和图标
只需在清单文件中修改icon、lable属性即可。
android:icon="@drawable/f1"
4、添加Action按钮
我们知道当Activity启动的时候,系统会调用Activity的onCreateOptionsMenu()方法来取出所有的Action按钮,我们只需要在这个方法中去加载一个menu资源,并把所有的Action按钮都定义在资源文件里面就可以了。
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
修改我们的menu文件,添加了两个action 控件,指定showAsAction属性分别为never、ifRoom、always。
never:表示永远显示咋overflow中
always:表示总是显示在action bar中,当屏幕空间不够用时,不显示
ifRoom:屏幕空间够用时显示在action bar中,不够用时显示在overflow中。
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
tools:context="com.example.useactionbar.MainActivity" >
<item
android:id="@+id/action_settings"
android:orderInCategory="100"
android:showAsAction="never"
android:title="@string/action_settings"/>
<item
android:id="@+id/item_1"
android:showAsAction="ifRoom"
android:title="one"
android:icon="@drawable/f1"/>
<item
android:id="@+id/item_2"
android:showAsAction="ifRoom"
android:title="two"
android:icon="@drawable/f1"/>
</menu>
效果如下:
5、响应Action 按钮事件
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.action_settings) {
return true;
}
return super.onOptionsItemSelected(item);
}
6、添加Action View
ActionView是一种可以在ActionBar中替换Action按钮的控件,它可以允许用户在不切换界面的情况下通过ActionBar完成一些较为丰富的操作。
为了声明一个ActionView,我们可以在menu资源中通过actionViewClass属性来指定一个控件。
showAsAction属性中我们还声明了一个collapseActionView,这个值表示该控件可以被合并成一个Action按钮。
<item
android:id="@+id/item_1"
android:showAsAction="ifRoom|collapseActionView"
android:actionViewClass="android.widget.SearchView"
android:title="one"
android:icon="@drawable/f1"/>
如果你还希望在代码中对SearchView的属性进行配置(比如添加监听事件等),完全没有问题,只需要在onCreateOptionsMenu()方法中获取该ActionView的实例就可以了。
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
//得到SearchView实例
MenuItem item = menu.findItem(R.id.item_1);
SearchView view = (SearchView) item.getActionView();
//得到实例后就可以对该实例进行相关操作了
......
......
return true;
}
7、Action Bar 导航
在Activity中通过调用setDisplayHomeAsUpEnabled此方法来设置导航
ActionBar actionBar =getActionBar();
actionBar.setDisplayHomeAsUpEnabled(true);
设置之后需要在监听事件中调用finish()方法即可。
从效果上看有点像是Activity回退栈的效果,其实却有着很大的却别。如A1跳转到A2再跳转到A3,Activity的流程为A3回退到A2,再回退到A1,但是若我们使用Action Bar来进行导航,可以指定A3的父为A1,回退则为A3->A1。
在Android 4.1版本之后,也可以直接使用android:parentActivityName这个属性来进行指定
<activity
android:name="com.example.actionbartest.MainActivity"
android:logo="@drawable/weather"
android:parentActivityName="父Activity" >
</activity>
8、特殊情况
如果手机没有物理Menu键的话,overflow按钮就可以显示,如果有物理Menu键的话,overflow按钮就不会显示出来。
@Override
protected void onCreate(Bundle savedInstanceState) {
......
setOverflowShowingAlways();
}
private void setOverflowShowingAlways() {
try {
ViewConfiguration config = ViewConfiguration.get(this);
Field menuKeyField = ViewConfiguration.class.getDeclaredField("sHasPermanentMenuKey");
menuKeyField.setAccessible(true);
menuKeyField.setBoolean(config, false);
} catch (Exception e) {
e.printStackTrace();
}
}
overflow中的Action按钮应不应该显示图标,是由MenuBuilder这个类的setOptionalIconsVisible方法来决定的,如果我们在overflow被展开的时候给这个方法传入true,那么里面的每一个Action按钮对应的图标就都会显示出来了
@Override
public boolean onMenuOpened(int featureId, Menu menu) {
if (featureId == Window.FEATURE_ACTION_BAR && menu != null) {
if (menu.getClass().getSimpleName().equals("MenuBuilder")) {
try {
Method m = menu.getClass().getDeclaredMethod("setOptionalIconsVisible", Boolean.TYPE);
m.setAccessible(true);
m.invoke(menu, true);
} catch (Exception e) {
}
}
}
return super.onMenuOpened(featureId, menu);
}
8、添加Action Provider
和Action View有点类似,Action Provider也可以将一个Action按钮替换成一个自定义的布局。但不同的是,Action Provider能够完全控制事件的所有行为,并且还可以在点击的时候显示子菜单。
<item
android:id="@+id/item_1"
android:showAsAction="ifRoom"
android:actionProviderClass="android.widget.ShareActionProvider"
android:title="one"
android:icon="@drawable/f1"/>
可以看到Action Provider与Action View的使用是一样的。
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
MenuItem item = menu.findItem(R.id.item_1);
ShareActionProvider shareActionProvider = (ShareActionProvider) item.getActionProvider();
shareActionProvider.setShareIntent(getDefaultIntent());
return true;
}
private Intent getDefaultIntent() {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("image/*");
return intent;
}
可以看到,这里的shareActionProvider的效果有点像overflow的效果,当然我们也可以自定义ActionProvider
public class MyProvider extends ActionProvider {
public MyProvider(Context context) {
super(context);
}
@Override
public View onCreateActionView() {
return null;
}
@Override
public boolean hasSubMenu() {
return true;
}
@Override
public void onPrepareSubMenu(SubMenu subMenu) {
subMenu.clear();
subMenu.add("one");
subMenu.add("two");
}
}