菜单在很多系统中都是有的,通过菜单我们可以做很多额外的操作,大部分时候菜单作用是为了界面美观,将控件收录到一个地方。Android中Menu在手机应用程序中出现较少了,当我们创建Android项目后MainActivity除了自动创建一个TextView还默认显示应用程序的菜单,点击后还能弹出一个选项,而且自动重写了onCreateOptionsMenu方法和onOptionsItemSelected方法,这两个方法分别是用来创建菜单和为菜单项设定监听的方法。
Android中有三种菜单:选项菜单、上下文菜单、弹出式菜单
默认显示在标题栏的菜单就是选项菜单,上下文菜单和弹出式菜单都需要绑定控件。
1)选项菜单:
通过点击标题栏的菜单按钮或者手机的MENU物理按键启动。重写onCreateOptionsMenu方法,通过其中传入的Menu调用add()方法添加普通菜单选项,通过addSubMenu方法添加子菜单选项。也可以通过getMenuInflater().inflate(R.menu.main,menu)方法直接导入菜单,R.menu.main即为菜单添加好了菜单选项,该文件位于res/menu,通过编辑该文件中的<item>可以为菜单添加选项,主要属性有
android:id为菜单项指定一个唯一标识
android:title菜单项的标题
android:icon菜单项的图标(默认不显示)
android:checkable 菜单项是否可选
android:checked 菜单项是否已被选
android:visible 菜单项是否可见
android:enable 菜单项是否可用
android:numericShortcut 菜单项数字快捷健
android:alphabeticShortcut菜单项字符快捷健(对于这两个属性,只能手机都没有键盘没有必要设置)
为选项设置监听,重写onOptionsItemSelected方法,通过item.getItemId()方法辨别不同选项为它们设置事件。
2)上下文菜单
需要绑定控件,通过长按控件弹出到屏幕中间,操作基本与选项菜单相似,重写onCreateContextMenu方法,亦可通过两种方法设置菜单选项,重写onContextItemSelected方法为菜单选项设定监听。绑定控件方法为registerForContextMenu(view);
3)弹出式菜单
需要绑定控件,通过控件的监听事件弹出到控件下方,如果下方控件不足就弹到上方。在控件监听事件中获取PopupMenu类,然后获取Activity的Menu类,接着就可以通过两中方法添加菜单选项,通过setOnMenuItemClickListener方法对菜单选项设定监听事件。
以下做一个简单的测试,布局文件如下
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.briup.mune.MainActivity" >
<TextView
android:id="@+id/menu_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world"
android:textSize="30sp" />
</RelativeLayout>
menu.xml文件如下
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
tools:context="com.briup.mune.MainActivity" >
<!-- 普通菜单项 -->
<item
android:id="@+id/set1"
android:icon="@drawable/ic_launcher"
android:title="设置区域"/>
<item
android:id="@+id/set2"
android:title="搜索区域"/>
<!-- 子菜单项 -->
<item android:title="字体颜色">
<menu>
<item
android:id="@+id/red"
android:title="RED"/>
<item
android:id="@+id/green"
android:title="GREEN"/>
<item
android:id="@+id/blue"
android:title="BLUE"/>
</menu>
</item>
</menu>
Activity类文件如下
import android.app.Activity;
import android.graphics.Color;
import android.os.Bundle;
import android.view.ContextMenu;
import android.view.Menu;
import android.view.MenuItem;
import android.view.SubMenu;
import android.view.View;
import android.view.ContextMenu.ContextMenuInfo;
import android.view.View.OnClickListener;
import android.widget.PopupMenu;
import android.widget.PopupMenu.OnMenuItemClickListener;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends Activity {
private TextView tv;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tv = (TextView) findViewById(R.id.menu_tv);
//为控件注册上下文菜单
registerForContextMenu(tv);
tv.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
//弹出式菜单
PopupMenu popupMenu = new PopupMenu(MainActivity.this, v);//API11以后才能用
Menu menu = popupMenu.getMenu();
getMenuInflater().inflate(R.menu.main, menu);
popupMenu.setOnMenuItemClickListener(new OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.set1:
case R.id.set2:
Toast.makeText(MainActivity.this, item.getTitle().toString(), Toast.LENGTH_SHORT).show();
break;
case R.id.red:
tv.setTextColor(Color.RED);
break;
case R.id.green:
tv.setTextColor(Color.GREEN);
break;
case R.id.blue:
tv.setTextColor(Color.BLUE);
break;
}
return true;
}
});
popupMenu.show();
}
});
}
//选项菜单
@Override
public boolean onCreateOptionsMenu(Menu menu) {
//getMenuInflater().inflate(R.menu.main, menu);//菜单项导入
//普通菜单项
menu.add(0, 1, 2, "设置区域");//(组ID:一般同一个菜单定位相同,ItemId:菜单项的ID,菜单项的顺序)
menu.add(0, 2, 3, "搜索位置");
//子菜单项
SubMenu subMenu = menu.addSubMenu(0, 3, 1, "字体颜色");
subMenu.add(0, 4, 0, "红色");
subMenu.add(0, 5, 0, "绿色");
subMenu.add(0, 6, 0, "蓝色");
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
switch (id) {
case R.id.set1:
case R.id.set2:
case 1:
case 2:
Toast.makeText(this, item.getTitle().toString(), Toast.LENGTH_SHORT).show();
break;
case 4:
case R.id.red:
tv.setTextColor(Color.RED);
break;
case 5:
case R.id.green:
tv.setTextColor(Color.GREEN);
break;
case 6:
case R.id.blue:
tv.setTextColor(Color.BLUE);
break;
}
return true;
}
//上下文菜单
@Override
public void onCreateContextMenu(ContextMenu menu, View v,
ContextMenuInfo menuInfo) {
getMenuInflater().inflate(R.menu.main, menu);
super.onCreateContextMenu(menu, v, menuInfo);
}
@Override
public boolean onContextItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.set1:
case R.id.set2:
Toast.makeText(this, item.getTitle().toString(), Toast.LENGTH_SHORT).show();
break;
case R.id.red:
tv.setTextColor(Color.RED);
break;
case R.id.green:
tv.setTextColor(Color.GREEN);
break;
case R.id.blue:
tv.setTextColor(Color.BLUE);
break;
}
return true;
}
}
效果如下