前段时间由于项目需要实现了展开通知栏的功能,所谓展开通知栏,就是通过expandstatusbar的方式将所有通知显示出来,也就是手势由顶部下滑展开的界面,statusbar属于全局且系统级别的界面,API中并没有开放独立的接口供我们调用以完成通知栏的展开,所以这里需要用到反射,通过反射调用方法,使用的方法是invoke(),这个方法是Method的方法,可能大家不太理解,我对这部分也知之甚少,用我自己最粗浅的理解就是,通过方法名创建Method对象,通过该对象的invoke()方法反射出方法(这一步其实就是方法的执行),供我们调用,这样说起来很苍白,先上一段代码解释下吧。

public class Test {     public static void main(String args[]){         A a = new A;         Class class = A.getClass();         Method m1 = class.getDeclaredMethod("outInfo");         Method m2 = clazz.getDeclaredMethod("setMsg", String.class);         Method m3 = clazz.getDeclaredMethod("getMsg");         m1.invoke(a);         m2.invoke(a, "重新设置msg信息!");         String msg = (String) m3.invoke(a);         System.out.println(msg);     } } class A {     private String msg;     public A(String msg) {         this.msg = msg;     }     public void setMsg(String msg) {         this.msg = msg;     }     public String getMsg() {         return msg;     }     public void outInfo() {         System.out.println("这是测试Java反射的测试类");     } }


这里用到的是最简单的反射调用方法的实现,更深入的反射的使用还需要我们继续深入的学习,下面就是解决android展开通知栏的问题,先上代码再粗浅的解释下。

public void OpenNotify() {// TODO Auto-generated method stubtry {Object service = getSystemService("statusbar");Class<?> statusbarManager = Class.forName("android.app.StatusBarManager");Method expand = null;if (service != null) {expand = statusbarManager.getMethod("expand");expand.setAccessible(true);expand.invoke(service);}} catch (Exception e) {}}

首先我们需要获得系统服务,前面说过,statusbar是全局且系统级别的布局,然而对其实现展开还需要增加一项权限,这个不能忽略

<uses-permissionandroid:name="android.permission.EXPAND_STATUS_BAR"/>

然后,通过StatusBarManager的包名反射得到statusbarManager对象,再通过expand方法名得到Method这个类的对象expand,下面执行该方法,expand.invoke().这样便能实现展开通知栏,这个方法在android4.2以下版本中测试良好,可是近来发现4.2及以上版本中这个方法失效了,4.2中对通知栏做了改变,由两部分组成,一个是我们通常意义上的通知栏,如下图


仔细看右上角有个头像按钮,点击这个,通知栏便会翻转至另外一个界面,同样是通过通知栏的形式展示的,如下图


这便进入了快速设置的功能,这对于用户来说是非常方便的,同样我们可以通过点击右上角的按钮返回上面通知栏的界面。这点改进对用户来说十分方便,但是开发者就遇到了问题,常用的展开方法失效了,我查了官网也没看到相关的API的更新,于是我上了神网stackoverflow,反编译了别的APK,最后终于被我试出来了,现在把代码给大家贴一下。

public void OpenNotify() {// TODO Auto-generated method stubint currentApiVersion = android.os.Build.VERSION.SDK_INT;try {Object service = getSystemService("statusbar");Class<?> statusbarManager = Class.forName("android.app.StatusBarManager");Method expand = null;if (service != null) {if (currentApiVersion <= 16) {expand = statusbarManager.getMethod("expand");} else {expand = statusbarManager.getMethod("expandNotificationsPanel");}expand.setAccessible(true);expand.invoke(service);}} catch (Exception e) {}}

就是在上面代码的基础上做了点改进,很一目了然,不做多的解释了。要说声抱歉,第一次发的文章格式很有问题,现在已经改正了。

demo下载地址http://download.csdn.net/user/beiminglei。



更多相关文章

  1. 这可能是最好的 Android/Kotlin日志输出方法
  2. 【SMS】android 短信接收流程分析——-拦截短信示例代码
  3. Android学习路线(十四)Activity生命周期——停止和重启(Stopping a
  4. [置顶] Android中webview里js和java的相互调用--含代码demo解析
  5. Evenbus思想解决切换网络高级处理(高级篇)
  6. Android中后台线程如何与UI线程交互
  7. Android全屏截图的方法,返回Bitmap并且保存在SD卡上
  8. Android(安卓)多主题切换 (theme + style) 及 selector/drawable
  9. Android中java线程的暂停与恢复

随机推荐

  1. Android WebRTC使用解析
  2. 使用MNN在Android上部署mnist模型
  3. [Android] 压缩图片并保存
  4. RTFSC系列之Retrofit
  5. Android 进程和线程
  6. Android 关键字 收集
  7. Android(安卓)APK文件拆解方法
  8. 初次在Android上使用OpenCV
  9. android 摄像头图像数据YUV转Bitmap, 再转
  10. Android TextView文字过多时通过滚动条显