Android PopupMenu
弹出菜单是停靠在一个View上的一个模式菜单。如果View对象下方有空间,那么弹出菜单将显示在停靠对象的下方,否则会显示在上方。这是非常有用的:
1. 给指定内容的操作提供一个溢出式菜单(如图4所示的Gmail的邮件头)。
图4. Gmail应用中的一个弹出菜单,停靠于右上角的溢出按钮。
注意:这是跟上下文菜单不一样,上下文菜单是对选择内容有影响的操作。针对应用选择内容的操作,请使用上下文操作模式或浮动内容菜单。
2. 提供命令语句的第二部分(如一个标记为“Add”按钮,用弹出菜单来产生不同的“Add”选项)。
3. 提供一个不保留持久选择的类似Spinner组件的下拉菜单。
注意:弹出菜单是在API 级别 11和更高版本上才有效的。
如果你在XML中定义了你的菜单,以下是如何显示弹出菜单的方法:
1. 用它的构造器实例化一个PopupMenu对象,它需要当前应用程序的Context和菜单要停靠的那个View两个对象作为参数。
2. 使用MenuInflater对象把你的菜单资源装载到由PopupMenu.getMenu()方法返回的Menu对象中。在API 级别 14以上的版本,你能够使用PopupMenu.inflate()方法来替代。
3. 调用PopupMenu.show()方法来显示弹出菜单。
例如,下列是一个带有android:onClick属性的按钮显示弹出菜单的方法:
清单文件中的定义:
<ImageButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="@drawable/ic_overflow_holo_dark"
android:contentDescription="@string/descr_overflow_button"
android:onClick="showPopup" />
Activity中的代码:
public void showPopup(View v) {
PopupMenu popup = new PopupMenu(this, v);
MenuInflater inflater = popup.getMenuInflater();
inflater.inflate(R.menu.actions, popup.getMenu());
popup.show();
}
在API 级别 14和更高的版本上,你能够用PopupMenu.inflate()方法把填充菜单的两个代码合并到一起。
当用户选择了一个菜单项或在触摸了菜单区域的外部,这个菜单就会消失。你能使用PopupMenu.OnDismissListener回调方法来监听菜单消失事件。
处理点击事件
当用户选择一个菜单项来执行一个操作时,你必须要实现PopupMenu.OnMenuItemClickListener接口并且通过调用 setOnMenuItemClickListener()方法把它注册给你的PopupMenu对象。当用户选择一个项目是,系统会调用你的接口中的 onMenuItemClick()回调方法。如:
public void showMenu(View v) {
PopupMenu popup = new PopupMenu(this, v);
// This activity implements OnMenuItemClickListener
popup.setOnMenuItemClickListener(this);
popup.inflate(R.menu.actions);
popup.show();
}
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.archive:
archive(item);
return true;
case R.id.delete:
delete(item);
return true;
default:
return false;
}
}
创建菜单组
菜单组是共享某些特性的菜单项目的集合,使用菜单组,可以做以下事情:
1. 用setGroupVisible()方法显示或隐藏组内的所有菜单项;
2. 用setGroupEnabled()方法启用或禁用组内的所有菜单项;
3. 用setGroupCheckable()方法指定所有组内项目是否可复选。
你能够通过把菜单资源中<item>元素嵌套进<group>元素中来创建分组菜单,或者使用带有分组ID的add()方法。
以下是包含了一个分组的菜单资源
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@+id/menu_save"
android:icon="@drawable/menu_save"
android:title="@string/menu_save" />
<!-- menu group -->
<group android:id="@+id/group_delete">
<item android:id="@+id/menu_archive"
android:title="@string/menu_archive" />
<item android:id="@+id/menu_delete"
android:title="@string/menu_delete" />
</group>
</menu>
这个分组菜单中的项目与第一个项目显示在同一个层次级别上---菜单中的三个项目是同级的,你能够使用上面列出的方法,通过引用组ID来修改分组菜单中两个项目的属性。系统也不会把分组的菜单项给分开。如,如果你给每个菜单项声明了android:showAsAction=”ifRoom”属性,那么它们将既可以同时显示在操作栏中,也可以同时显示在操作溢出中。
使用可复选的菜单项
菜单能够用于切换选项的界面,针对一个独立的选项使用一个可复选的Checkbox菜单,对于一组互斥的选项可使用一组带有单选按钮的菜单(如图5所示)。
图5.带有复选菜单项的子菜单截图。
注意:图标菜单(选项类型的菜单)中的菜单项不能显示一个复选框或单选按钮。如果你选择了让图标菜单中的菜单项可复选,那么就必须在每次状态改变时通过更换手动的更换图标或文本来的指明复选的状态。
你能够使用<item>元素中的android:checkable属性给单独的菜单项定义可复选的行为,或者用<group> 元素中的android:checkableBehavior属性给一组菜单项定义可复选行为。如,下例中菜单组中的每个菜单项都带有一个可复选的复选按钮:
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<group android:checkableBehavior="single">
<item android:id="@+id/red"
android:title="@string/red" />
<item android:id="@+id/blue"
android:title="@string/blue" />
</group>
</menu>
android:checkableBehavior属性可以有以下三种设置:
1. single:菜单组中仅有一个菜单能够被复选(复选按钮)
2. all:所有菜单项都能够被复选(复选框)
3. none:没有项目是可复选的
你能够在<item>元素中使用android:checked属性给一个菜单项设置默认的复选状态,并且可以用setChecked()方法在代码中改变它。
当一个可复选的菜单项被选择的时候,系统会调用对应被选择的菜单项的回调方法(如onOptionsItemSelected())。你必须在这时设置复选框的状态,因为复选框或复选按钮不会自动的改变它们的状态。你能够用isChecked()方法来查询复选菜单的当前状态(被用户选择之前的状态),然后用setChecked()方法设置复选状态。如:
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.vibrate:
case R.id.dont_vibrate:
if (item.isChecked()) item.setChecked(false);
&nbs
补充:移动开发 , Android ,