android 状态栏占位_Android

前不久在写一个功能的时候,遇到一个添加引导页的需求,直接照搬了之前的引导页的实现方式,使用了 NewbieGuide 来实现,发现在Activity中引导页弹出时无法遮盖状态栏,除了状态栏外的部分才能正常被遮盖,所以探究下这个是什么原因导致的

项目中其他地方的遮罩可以完整的盖住整个手机屏幕,连同状态栏一起,所以先去看看这些地方是如何实现的,一共有两种:

布局中设置android:fitsSystemWindows=”true”的同时,使用了自定义的TransLinearLayout这个TranslinearLayout中的onMeasure方法中,加上了WindowInsets的getSystemWindowInsetTop取得的高度

而WindowInsets这里的inset的直译是插入物,可以理解为特定屏幕区域,WindowInsets的三个成员变量mSystemWindowInsets,mWindowDecorInsets,mStableInsets表示了三种屏幕区域,而SystemWindowInsets系统窗口区域代表着整个屏幕窗口上,状态栏,导航栏,输入法等系统窗口占用的区域

这里的top表示的是顶部占位区域的宽度,即状态栏的宽度,长度默认是屏宽

某些Activity的Theme中加上windowTranslucentStatus=true属性,或者在活动的onCreate代码中设置

true

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {

window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS)

}

setContentView(R.layout.ai_kline_act_kline_master)

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {

val titleBar = findViewById(R.id.ai_kline_master_title_bar)

var statusBarHeight = 60

if (ScreenUtil.getStatusBarHeight(this) != 0) {

statusBarHeight = ScreenUtil.getStatusBarHeight(this)

}

titleBar.setPadding(titleBar.paddingLeft, titleBar.paddingTop + statusBarHeight, titleBar.paddingRight, titleBar.paddingBottom)

val titleBarLayoutParams = titleBar.layoutParams

titleBarLayoutParams.height = titleBarLayoutParams.height + statusBarHeight

titleBar.layoutParams = titleBarLayoutParams

}

至此明白了需要怎样去实现,解决了问题,但是从这里可以看出我对主题,状态栏相关的知识不够扎实,故对相关内容重新整理归纳一下

首先是主题相关的内容,Android5.0发布后,support-v7-appcompat 也更新到V21,增加了ToolBar、recyclerview、cardview等控件。Android从5.0开始支持 Material Design 应用,可以通过修改各项参数来达到不同的主题效果,以下是各项参数的作用

textColorPrimary 应用的主要文字颜色,ActionBar的标题文字默认使用该颜色

colorPrimary 应用的主要色调,actionBar默认使用该颜色,Toolbar导航栏的底色

statusBarColor 状态栏颜色,默认使用colorPrimaryDark

colorPrimaryDark 应用的主要暗色调,statusBarColor默认使用该颜色

windowBackground 窗口背景颜色

navigationBarColor 底部栏颜色

colorAccent CheckBox,RadioButton,SwitchCompat等一般控件的选中效果默认采用该颜色

colorForeground 应用的前景色,ListView的分割线,switch滑动区默认使用该颜色

colorBackground 应用的背景色,popMenu的背景默认使用该颜色

colorControlNormal CheckBox,RadioButton,SwitchCompat等默认状态的颜色。

colorControlHighlight 控件按压时的色调

colorControlActivated 控件选中时的颜色,默认使用colorAccent

colorButtonNormal 默认按钮的背景颜色

editTextColor :默认EditView输入框字体的颜色。

textColor Button,textView的文字颜色

textColorPrimaryDisableOnly RadioButton checkbox等控件的文字

colorSwitchThumbNormal switch thumbs 默认状态的颜色. (switch off)

false

false

false

false

又发现到AppCompatActivity中出现了windowNoTitle属性,前边不需要加”android:”,那这两个有什么区别吗?

其实带android的是系统的,不带android是兼容样式的,就是Theme.AppCompat样式的,因为是 support 包里重新定义了这个属性,即windowNoTitle是appcompat-v7中的属性,在appcompat-v7\res\values\values.xml中定义了,可以打开appcompat-v7\res\values\values.xml搜索AppCompatTheme,可以找到定义的”windowNoTitle”、”windowActionBar”等属性。

“windowNoTitle”属性在代码中可以使用R.attr.windowNoTitle访问,

“android:windowNoTitle”则需要使用android.R.attr.windowNoTitle访问。

使用AppCompatActivity时(Activity必须使用Theme.AppCompat主题及其子主题),测试发现:

“android:windowActionBar”属性在AppCompatActivity中不起作用

windowNoTitle = false 并且 android:windowNoTitle = false 时,会出现两个标题,位于下方的是AppCompatActivity的标题栏

当windowNoTitle = false,windowActionBar = false 时,会报错: AppCompat does not support the current theme features

windowNoTitle = true 并且 android:windowNoTitle = true时 ,无标题

然后是状态栏的沉浸式实现的转变:

Android4.4(API 19) - Android 5.0(API 21): 这个阶段可以实现沉浸式,但是表现得还不是很好,实现方式为: 通过FLAG_TRANSLUCENT_STATUS设置状态栏为透明并且为全屏模式,然后通过添加一个与StatusBar 一样大小的View,将View 的 background 设置为我们想要的颜色,或者是像上文那样动态设置一个padding,从而来实现沉浸式

这里的FLAG_TRANSLUCENT_STATUS的含义是:设置状态栏透明,并且变为全屏模式,从注释中看到,当window的这个属性有效的时候,会自动设置 system ui visibility的标志SYSTEM_UI_FLAG_LAYOUT_STABLE 和 SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN

Android 5.0(API 21)以上版本: 在Android 5.0的时候,加入了一个重要的属性和方法 android:statusBarColor (对应方法为 setStatusBarColor),通过这个方法我们就可以轻松实现沉浸式

Android 6.0(API 23)以上版本:Android6.0以上的实现方式和Android 5.0 +是一样,但是从Android 6.0(API 23)开始,我们可以改状态栏的绘制模式,可以显示白色或浅黑色的内容和图标(除了魅族手机,魅族自家有做源码更改,6.0以下就能实现)示例

//6.0 以上可以设置状态栏的字体为黑色,使用下面代码可以打开亮色状态栏模式,实现黑色字体,白底的需求用这句setStatusBarColor(Color.WHITE)

window.decorView.systemUiVisibility = View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR

更新

同样的操作,在 Android 8.0 以上似乎并不能很好地实现,而是更符合 flag 原本的定义,FLAG_TRANSLUCENT_STATUS 其中的 TRANSLUCENT 的意思是半透明的意思,所以在 8.0 以上的时候,设置这个 FLAG 会让状态栏半透明,同时 SYSTEM_UI_FLAG_LAYOUT_STABLE(让应用的主体内容占用系统状态栏的空间)和SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN(全屏)也会生效,造成顶部和状态栏重叠的情况,同时有一条半透明的状态栏在上面,这样子的话,在 Android7.0 中可以完美实现的沉浸式,在 8.0 的时候还是会显示一条半透明状态栏,所以如果要实现沉浸式,设置 FLAG_TRANSLUCENT_STATUS 和 android:windowTranslucentStatus = true 其实并不是太可取,应该要动态改变状态栏的颜色来实现真正的沉浸式,可以设置状态栏颜色与下方控件颜色一致,或者在没有设置 FLAG_TRANSLUCENT_STATUS 而设置了 FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS 的同时,设置状态栏颜色为透明,因为设置 FLAG_TRANSLUCENT_STATUS 会使得状态栏默认为半透明颜色

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值