1.Menu概述
3.0以前
3.0以前的Menu,当用户点击菜单按钮时,选项菜单的内容会出现在屏幕底部,可包含多达6个菜单项,超出部分以更多来显示。
3.0以后
选项菜单中的项目将出现在操作栏里面,用户可以使用操作栏右侧的图标或者按设备的菜单键显示操作溢出菜单。
2.Menu创建方式
2.1XML方式定义Menu
清晰的菜单结构,将菜单内容与应用的逻辑代码分离,资源适配更容易。
<?xml version="1.0" encoding="utf-8"?> <menu xmlns:android="http://schemas.android.com/apk/res/android"> <!-- 设置ID --> <item android:id="@+id/save_item" android:icon="@mipmap/ic_launcher" android:title="Add"/> <item android:id="@+id/remove_item" android:title="Remove"/> </menu>
2.2Java代码方式定义Menu
//创建OptionMenu @Override public boolean onCreateOptionsMenu(Menu menu) { /** //加载菜单资源 getMenuInflater().inflate(R.menu.optionmenu,menu); **/ //Java方式设计菜单 //添加不包含子菜单的菜单项:参数1:组ID(表示那个组),参数2:菜单项的id, // 参数3:排序的序号,参数4:文本内容 menu.add(1,1,1,"保存"); menu.add(1,2,2,"设置"); //添加包含子菜单的菜单项 SubMenu subMenu = menu.addSubMenu(1,3,3,"更多"); //添加子菜单 subMenu.add(2,4,1,"添加"); subMenu.add(2,5,2,"退出"); return true; } }
2.3加载菜单资源
加载菜单资源实例如下:
@Override public boolean onCreateOptionsMenu(Menu menu) { getMenuInflater().inflate(R.menu.optionmenu,menu); return true; }
说明:
getMenuInflater() 得到MenuInflater对象 inflater(参数1,参数2) 给当前活动创建菜单
参数1:用于指定通过那个资源文件来创建菜单
参数2:用于指定将菜单项添加到哪一个Menu对象当做去。
onCreateXXXMenu(Menu menu) 为指定菜单类型传入menu参数,然后给这个方法返回true,
表示允许创建的菜单显示出来;如果返回了false,则创建的菜单将无法显示、
2.4定义菜单响应事件
重写其响应事件方法,实例如下:
//OptionMenu菜单项被选中时的方法 @Override public boolean onOptionsItemSelected(MenuItem item) { switch (item.getItemId()){ case R.id.save_item: Toast.makeText(this, "点击了添加选项", Toast.LENGTH_SHORT).show(); case R.id.remove_item: Toast.makeText(this, "点击了移除选项", Toast.LENGTH_SHORT).show(); default: } return true; }
注意:一定要返回true。
3.选项菜单(OptionMenu)
是一个应用的主菜单项,用于放置对应用产生全局影响的操作。
点击菜单选项,弹出菜单栏。一个Activity只能有一个OptionMenu
点击res右键,new->Android Resource Directory,选择Resource类型为Menu,创建一个Menu,再在Menu里面新建一个Menu Resource file.
如下:optionmenu.xml
<?xml version="1.0" encoding="utf-8"?> <menu xmlns:tools="http://schemas.android.com/tools" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:android="http://schemas.android.com/apk/res/android"> <!-- 设置ID --> <item android:title="保存" android:id="@+id/save" android:icon="@mipmap/ic_launcher" app:showAsAction="always|withText"/> <item android:title="设置" android:id="@+id/setting"/> <item android:title="更多操作" android:id="@+id/more"> <!-- 子菜单 --> <menu > <item android:title="子菜单1" /> <item android:title="子菜单2" /> <item android:title="退出" android:id="@+id/exit"/> </menu> </item> </menu>
item里面的重要属性:
app:showAsAction=""(控制显示特性) always:直接将某个菜单选项显示在标题栏上面
never:不在标题栏里面直接显示出来
ifRoom:有空间的话就显示
withTest:控制图标和文本一起显示
collapseActionView:折叠
可以使用“ | ”进行多选
android:icon="" 显示图标 如何使用:在MainActivity.java中
//创建OptionMenu @Override public boolean onCreateOptionsMenu(Menu menu) { //加载菜单资源 getMenuInflater().inflate(R.menu.optionmenu,menu); return true; } //OptionMenu菜单项被选中时的方法 @Override public boolean onOptionsItemSelected(MenuItem item) { switch (item.getItemId()){ case R.id.save: Toast.makeText(this, "保存", Toast.LENGTH_SHORT).show(); case R.id.setting: Toast.makeText(this, "设置", Toast.LENGTH_SHORT).show(); case R.id.more: Toast.makeText(this, "更多", Toast.LENGTH_SHORT).show(); case R.id.exit: Toast.makeText(this, "退出", Toast.LENGTH_SHORT).show(); } return super.onOptionsItemSelected(item); }
4.上下文菜单(ContextMenu)
普通上下文菜单方式:
长按某个View不放,就会在屏幕中间弹出ContextMenu。
一个Activity可能有多个View,从而有多个ContextMenu。
如下:contextmenu.xml
<?xml version="1.0" encoding="utf-8"?> <menu xmlns:android="http://schemas.android.com/apk/res/android"> <item android:id="@+id/sure" android:title="确定" /> <item android:id="@+id/cancel" android:title="取消" /> </menu>
如何使用:在MainActivity.xml中
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //演示ContextMenu //1.注册,两个都会注册同一个菜单 registerForContextMenu(findViewById(R.id.ctx_btn)); registerForContextMenu(findViewById(R.id.pop_btn)); //2.创建,覆盖onCreateContextMenu //3.菜单项的操作 } //创建ContextMenu @Override public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { getMenuInflater().inflate(R.menu.contextmenu,menu); } //ContextMenu菜单项被选中时的操作方法 @Override public boolean onContextItemSelected(MenuItem item) { switch (item.getItemId()){ case R.id.sure: Toast.makeText(this, "确定", Toast.LENGTH_SHORT).show(); case R.id.cancel: Toast.makeText(this, "取消", Toast.LENGTH_SHORT).show(); } return super.onContextItemSelected(item); }
为View设置特殊上下文操作模式
即长按某个View后,菜单项将会显示在标题栏上面。
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //4.为按钮设置上下文操作模式 //4.1实现ActionMode CallBack //4.2在View的长按事件中去启动上下文操作模式 findViewById(R.id.ctx_btn).setOnLongClickListener(new View.OnLongClickListener(){ @Override public boolean onLongClick(View view) { startActionMode(callback); return false; } }); } //设置上下文操作模式 ActionMode.Callback callback = new ActionMode.Callback() { //创建,在启动上下文操作模式时(startActionMode(Callback)调用 @Override public boolean onCreateActionMode(ActionMode actionMode, Menu menu) { getMenuInflater().inflate(R.menu.contextmenu,menu); return true; } //在创建方法后进行调用 @Override public boolean onPrepareActionMode(ActionMode actionMode, Menu menu) { return false; } //点击时 @Override public boolean onActionItemClicked(ActionMode actionMode, MenuItem menuItem) { switch (menuItem.getItemId()){ case R.id.sure: Toast.makeText(MainActivity.this, "确定", Toast.LENGTH_SHORT).show(); case R.id.cancel: Toast.makeText(MainActivity.this, "取消", Toast.LENGTH_SHORT).show(); } return true; } //上下文操作模式结束时调用 @Override public void onDestroyActionMode(ActionMode actionMode) { Log.e("TAG","======== 结束 ========"); } };
5.弹出菜单(PopupMenu)
一个以模态形式展示的弹出风格的菜单,绑定在View上,一般出现在被绑定的View的下方(如果没有空间,则会显示在上方)。
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //popupMenu弹出式菜单的演示 final Button popBtn = findViewById(R.id.pop_btn); findViewById(R.id.pop_btn).setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { //实例化PopupMenu对象 PopupMenu popupMenu = new PopupMenu(MainActivity.this,popBtn); //加载菜单资源:利用MenuInflater popupMenu.getMenuInflater().inflate(R.menu.contextmenu,popupMenu.getMenu()); //为PopupMenu设置监听器 popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() { @Override public boolean onMenuItemClick(MenuItem menuItem) { switch (menuItem.getItemId()){ case R.id.sure: Toast.makeText(MainActivity.this, "确定", Toast.LENGTH_SHORT).show(); case R.id.cancel: Toast.makeText(MainActivity.this, "取消", Toast.LENGTH_SHORT).show(); } return false; } }); //别忘记这一步 popupMenu.show(); } }); }