原文链接: https://blog.csdn.net/u011386173/article/details/84568092

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/u011386173/article/details/84568092
这篇文章可结合Android9.0 完全隐藏导航栏、状态栏

Android应用设置沉浸式全屏时,一般会使用到如下的Flag:

View.SYSTEM_UI_FLAG_IMMERSIVE或View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY以及View.SYSTEM_UI_FLAG_HIDE_NAVIGATION。

使用了以上的Flag组合后呢,系统会弹窗提示用户当前是全屏显示,弹框如下:

大标题是Viewing full screen,小字部分是Swipe down from the top to exit full screen.”的提示,即从上往下滑动可退出全屏。

这个提示是友好的,但是大多数情况下,这个提示框可能因为挡住了要显示的内容而不满足全屏要求。那么如何去除“Viewing full screen”弹窗呢?要去除这个弹框,就先要从这个弹框出现的位置开始分析。

在/framework/base/servics/core/java/com/server/policy/ImmersiveModeConfirmation.java中有如下函数:

1、首先看看这个isImmersiveMode参数,系统是如何判断当前是否为沉浸式的呢?
【/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java】的函数updateSystemBarsLw:

vis就是来判断显示界面设置给systemUiVisibility 的flag的。看看isImmersiveMode:

也就是如果systemUiVisibility设置了SYSTEM_UI_FLAG_HIDE_NAVIGATION + SYSTEM_UI_FLAG_IMMERSIVE、SYSTEM_UI_FLAG_IMMERSIVE_STICKY中的一个或两个,且存在NavigationBar,那么就是沉浸式模式。

2、再看一下mHandler中是如何处理H.SHOW消息的


再看看handleShow函数:

当当当,这个时候那个弹窗就显示出来了。

解决方案
既然我们要解决弹窗显示的问题,那么根据以上显示弹窗的分析,方案就来了。

①mHandler中接收到消息后不做show confirmation的操作;

②弹窗显示后就调用其隐藏的操作;

③不发送显示弹框的消息SHOW到mHandler中。

接下来分析一下这三种方案:

①mHandler中接收到消息后不做show confirmation的操作
因为这个文件是framework层的,所以就是要修改系统源码。而且一旦接收到消息后不做show confirmation的操作,那么系统中的所有应用沉浸式全屏的时候都不会弹出提示框,而非当前的沉浸式全屏引用。这样的需求一般不是我们所需要的,不过当然也是一种方案,这种方案对于看不到系统源码的开发者来说并不友好。修改方案如下:

②弹窗显示后就调用其隐藏的操作
其实从刚刚的源码分析可以看到,因此弹框,也就是handleHide里做的事。而这个handleHide被执行到,就需要给mHandler发送HIDE消息。But, 发送HIDE消息的就两处:

第一处:这个要屏幕沉浸式显示的模式变更后才会执行(即退出沉浸式模式)。

第二处:很明显,这是和VR相关的,我们一般用不到。

那么,我们可以试试不通过发送消息,而是直接执行handleHide里的操作呀!!!

好的,这个函数是私有的。如果APP想调用,可以通过反射。=-=,这个类好像是不对外的吧,反正反射也没有啥用。。。亲测没成功。。。。

③不发送显示弹框的消息SHOW到mHandler中
终极方法终于来了!!!

在ImmersiveModeConfirmation.java文件中,有且仅有一处发送了SHOW消息:

没错!!就是这个函数。那么为了不发送SHOW消息,所以就要if条件不满足。

通过分析,这个navBarEmpty条件最容易被APP修改,我们只要让这个值为true就好了。

那么来看看这个参数navBarEmpty的由来:

【/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java】

函数updateSystemBarsLw:

来看看isNavBarEmpty是个什么鬼:

没错,这要这个isNavBarEmpty返回true,就不会show 弹出了。

从这个函数可以看到,只要在应用界面显示的systemUiVisibility参数中加上这三个FLAG那么这个函数就会返回true。从而那个Viewing Full Screen的弹窗也不会出现了(亲测有用)。

修改如下:

WindowManager.LayoutParams lp = new WindowManager.LayoutParams(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
lp.systemUiVisibility = View.STATUS_BAR_DISABLE_HOME | View.STATUS_BAR_DISABLE_BACK | View.STATUS_BAR_DISABLE_RECENT |
              View.SYSTEM_UI_FLAG_HIDE_NAVIGATION |View.SYSTEM_UI_FLAG_FULLSCREEN |
              View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY |
               View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
这种方法,并不是对所有应用起作用。而仅仅是对自己的沉浸式全屏应用其作用,当应用退出时,这个弹窗还是对其他应用有效的。o(* ̄︶ ̄*)o
————————————————
版权声明:本文为CSDN博主「明朗晨光」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/u011386173/article/details/84568092

更多相关文章

  1. Android(安卓)应用第一次运行时,引导页面的设置方法(只让程序Aciti
  2. android spinner自定义背景文字显示不全解决办法
  3. Thread、Handler和HandlerThread关系详解
  4. android jni 包裹文件(jni wrapper) 以 speex 库为例
  5. Android(安卓)UI开发第三十二篇——Creating a Navigation Drawe
  6. 在Android(安卓)2.3中如何使用native_activity.h编写本地应用
  7. Android中使用GridView分页显示系统所安装的应用,支持拖动与手势
  8. framework telephony
  9. 详解Android使GridView横向水平滚动的实现方式

随机推荐

  1. 自动完成AutoCompleteTextView(android)
  2. android activity 测试
  3. Optimizing Apps for Android(安卓)3.0
  4. Android+Apache+Servlet+MySQL简易粗糙Mi
  5. Android用View实现显示中英文混排的文字
  6. android音乐播放器监听电话状态
  7. [Android]simplelistadapter 与数据库绑
  8. spring mvc+mybatis 构建cms内容发布系统
  9. android自定义dialog,软件键盘弹出挡住输
  10. android3.2系统removeHeadView空指针异常