解决android4.0系统中菜单(Menu)添加Icon无效问题

在Android4.0系统中,创建菜单Menu,通过setIcon方法给菜单添加图标是无效的,图标没有显出来,2.3系统中是可以显示出来的。这个问题的根本原因在于4.0系统中,涉及到菜单的源码类 MenuBuilder做了改变,该类的部分源码如下:

 1 public class MenuBuilder implements Menu {
 2 ...
 3 private boolean mOptionalIconsVisible = false;
 4 ....
 5     void setOptionalIconsVisible(boolean visible) {
 6         mOptionalIconsVisible = visible;
 7     }
 8
 9     boolean getOptionalIconsVisible() {
10         return mOptionalIconsVisible;
11     }
12 ...
13 }  

上面的代码中,mOptionalIconsVisible成员初始值默认为false,这就是为什么给菜单设置图标没有效果的原因;所以,只要我们在创建菜单时通过调用setOptionalIconsVisible方法设置mOptionalIconsVisible为true就可以了;这时候问题来了,要想调用该方法,就需要创建MenuBuilder对象,但是,我们是无法在开发的应用程序中创建MenuBuilder这个对象的(MenuBuilder为系统内部的框架类);

这时候就需要考虑用反射了,在代码运行创建菜单的时候通过反射调用setOptionalIconsVisible方法设置mOptionalIconsVisible为true,然后在给菜单添加Icon,这样就可以在菜单中显示添加的图标了;

代码实现如下:

 1 package com.stevenhu.mie;
 2
 3 import java.lang.reflect.Method;
 4
 5 import android.app.Activity;
 6 import android.os.Bundle;
 7 import android.util.Log;
 8 import android.view.Menu;
 9 import android.view.MenuItem;
10
11 public class MainActivity extends Activity
12 {
13     /** Called when the activity is first created. */
14     @Override
15     public void onCreate(Bundle savedInstanceState)
16     {
17         super.onCreate(savedInstanceState);
18         setContentView(R.layout.main);
19     }
20
21     @Override
22     public boolean onCreateOptionsMenu(Menu menu)
23     {
24         //运行时,参数Menu其实就是MenuBuilder对象
25         Log.d("MainActivity", "menu--->" + menu);
26
27         /*利用反射机制调用MenuBuilder的setOptionalIconsVisible方法设置mOptionalIconsVisible为true,
28          * 给菜单设置图标时才可见
29          */
30         setIconEnable(menu, true);
31
32         MenuItem item1 = menu.add(0, 1, 0, R.string.item1);
33         item1.setIcon(R.drawable.camera);
34
35         MenuItem item2 = menu.add(0, 1, 0, R.string.item2);
36         item2.setIcon(R.drawable.dial);
37
38         MenuItem item3 = menu.add(0, 1, 0, R.string.item3);
39         item3.setIcon(R.drawable.sms);
40
41         return super.onCreateOptionsMenu(menu);
42     }
43
44     @Override
45     public boolean onPrepareOptionsMenu(Menu menu)
46     {
47         // TODO Auto-generated method stub
48         return super.onPrepareOptionsMenu(menu);
49     }
50
51     //enable为true时,菜单添加图标有效,enable为false时无效。4.0系统默认无效
52     private void setIconEnable(Menu menu, boolean enable)
53     {
54         try
55         {
56             Class<?> clazz = Class.forName("com.android.internal.view.menu.MenuBuilder");
57             Method m = clazz.getDeclaredMethod("setOptionalIconsVisible", boolean.class);
58             m.setAccessible(true);
59
60             //MenuBuilder实现Menu接口,创建菜单时,传进来的menu其实就是MenuBuilder对象(java的多态特征)
61             m.invoke(menu, enable);
62
63         } catch (Exception e)
64         {
65             e.printStackTrace();
66         }
67     }
68 }  

通过上面的代码,就可以实现在Android4.0系统中设置菜单的Icon有效了

时间: 2024-10-12 23:34:23

解决android4.0系统中菜单(Menu)添加Icon无效问题的相关文章

关于解决android4.0系统中菜单无法添加Icon的问题

在Android4.0系统中,创建菜单Menu,然后通过setIcon方法给菜单添加图标是无效的,图标不会显出来,而之前的系统中是可以显示出来的.这个问题的根本原因在于4.0系统中,涉及到菜单的源码类 MenuBuilder做了改变,其中有private boolean mOptionalIconsVisible = false;属性使得无法显示菜单图标. 但是,我们又无法在开发的应用程序中创建MenuBuilder这个对象的(因为MenuBuilder是系统内部的框架类). 当然如果不是很需要

64位系统中为VS2012添加OpenGL工具包

之前一直都是按照网上教程进行的添加,以前使用的系统是32位的,所以一直都没有问题.最近换了64位系统,要使用到OpenGL,于是就又进行了原来的工作,但进行测试时,老是失败: 但是在目录:"C:\Windows\System32"下我已经放了这个dll,于是思考会不会是因为64位系统的问题,所以就在"glut32.dll"和"glut.dll"拷贝了一份放到了"C:\Windows\System"下,再次运行,发现已经能够正常

嵌入式系统中为什么要添加操作系统?(转)

原帖地址:http://blog.sina.com.cn/s/blog_8f396e370100vjs0.html 嵌入式系统中为什么要添加操作系统?这个问题很多人都能回答,并且也一定要很多答案.当外行问及我这个问题的时候,我说是想让程序脱离硬件,提高程序的可移植性和可读性:另外就是当系统比较复杂的情况下,操作系统可以为这个复杂的系统提供管理机制,开发人员只要完成功能函数,并且添加任务即可,不用再去管不同的任务之间通信以及各个不同功能之间如何协同工作等等的问题.但是这样说出来,似乎没法让他们感受

解决在ubuntu系统中安装Chrome失败的问题

1. 下载 Google Chrome 文件名,例如: google-chrome-stable_current_i386.deb 2. 在命令行下安装 直接用软件中心打开将会有可能因为依赖关系不完整导致失败,在命令行下进入包含安装包.deb文件的目录, 然后: $ sudo dpkg -i google-chrome-stable_current_i386.deb 如果报告依赖关系错误,例如: dpkg:依赖关系问题使得 google-chrome-stable 的配置工作不能继续: goog

系统组件:菜单Menu(1)

常用的菜单有: OptionMenu(系统菜单):当点击手机的菜单键时,出现在应用顶部下的菜单. ContextMenu(上下文菜单):当长按某一UI控件时,出现的菜单. PopupMenu(弹出菜单):当点击某一UI控件时,弹出的菜单. SubMenu(子菜单):当点击某一菜单的菜单项时,出现的下一级菜单. 下面主要总结前三种菜单的用法: 1.OptionMenu使用:重写Activity的回调方法onCreateOptionsMenu()创建选项菜单,同时一般肯定会对菜单项进行监听,所以同时

cocos2dx中菜单menu 和 menuItem

菜单Menu是专门用来承载菜单按钮的Layer图层,图层中的子节点只能够是菜单项MenuItem或其子类.通常先创建菜单项MenuItem,然后使用一个或多个菜单项生成菜单Menu,最后把Menu加入当前Layer图层. 如果直接在层中添加MenuItem也可以正常显示,但是无法响应回调函数,因为Menu是继承至Layer,也就继承了触摸的相关事件,而MenuItem只是从Node继承而来,并不响应触摸,因此无法调用回调函数. 由于CCMenu的父类为Layer,所以锚点为(0,0),且无法设置

Linux——解决RedHat6/CentOS6系统中“弹出界面eth0:设备似乎不存在”的问题

刚刚在自己的CentOS6系统中执行service network restart时,竟然提示: 弹出界面 eth0: 设备 似乎不存在, 初始化操作将被延迟.   [失败] 这事可真神奇.于是手动编辑网卡配置文件/etc/sysconfig/network-scripts/ifcfg-eth0,根据自己的忘记进行了一番设置,再次执行service network restart,竟然又弹出一个: 弹出界面 eth0: 错误:没有找到合适的设备:没有找到可用于连接 'eth0' 的设备. 后来发

linux系统中用户的添加、删除和改密

用户的添加.删除和改密 一:用户的添加: useradd.adduser (1)作用:useradd命令用于建立用户帐号.帐号建好之后,再用passwd设定帐号的密码: 可用userdel删除帐号.使用useradd指令所建立的帐号,实际上是保存在/etc/passwd文本文件中. 语法为:useradd -D [-b][-e <有效期限>][-f <缓冲天数>][-g <群组>][-G <群组>][-s <shell>] 类型 例程 添加一般的

从源代码剖析Struts2中用户自定义配置转换器的两种方式——基于字段的配置转换器和基于类型的配置转换器(解决了实际系统中,因没有区分这两种工作方式的生命周期而引起的异常错误问题)

自定义类型转换器必须实现ongl.TypeConverter接口或对这个接口的某种具体实现做扩展 <<interface>>com.opensymphony.xwork2.conversion.TypeConverter à com.opensymphony.xwork2.conversion.impl.DefaultTypeConverter à org.apache.struts2.util.StrutsTypeConverter 接口及类进行解析 TypeConverter(