您的位置:首页 > 移动开发 > Android开发

Android 状态栏全透明策略

2016-06-07 13:41 387 查看
#Android 状态栏全透明策略

@(Android)

展示效果:

Android4.4以下: 状态栏黑乎乎一片



Android4.4以后, 可以将状态栏设置为透明, 或者任意颜色

1. 全屏模式



2. 着色模式



Demo

Github Demo 链接: StatusBarCompat

参考文章

Android开发:Translucent System Bar 的最佳实践

Android状态栏一体化

内容介绍

这篇文章主要是对实现状态栏一体化的一些总结, 参考上面两篇文章, 写得很棒, 推荐大家都看一看!

实现状态栏一体化, 主要分为两种方式. 一种是通过xml配置文件设置, 一种是通过在activity中设置属性. 下面将介绍两种实现方法:

1. 通过配置文件实现

在Android4.4之后提供了可以修改状态栏的属性接口后,我们可以直接通过style文件来配置状态栏, 但是需要注意的是, 为了兼容4.4以下的版本, 所以必须在配置多个API级别的values文件. 这里直接借参考文章中的图:



最基本的在4.4版本之下会加载默认的values/styles.xml, 如果在4.4版本会加载 values-v19/styles.xml, 5.0以上加载 values-v21/styles.xml文件. 具体配置如下:

values/styles.xml

<style name="ImageTranslucentTheme" parent="AppTheme">
<!--在Android 4.4之前的版本上运行,直接跟随系统主题-->
</style>


values-v19/styles.xml

<style name="ImageTranslucentTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<item name="android:windowTranslucentStatus">true</item>
<item name="android:windowTranslucentNavigation">true</item>
</style>


values-v21/styles.xml

<style name="ImageTranslucentTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<item name="android:windowTranslucentStatus">false</item>
<item name="android:windowTranslucentNavigation">true</item>
<!--Android 5.x开始需要把颜色设置透明,否则导航栏会呈现系统默认的浅灰色-->
<item name="android:statusBarColor">@android:color/transparent</item>
</style>


2. 通过代码中设置

通过代码控制, 需要根据不同的版本sdk做不同的设置. 下面的代码将详细说明:

2. 1全屏模式

全屏模式的意思就是: 状态栏显示, 状态栏背景透明, 所以会呈现根Layout的背景.如下图:



Android5.0版本以上

// 5.0版本以上
private void setStatusBarUpperAPI21() {
Window window = getWindow();
//设置透明状态栏,这样才能让 ContentView 向上
window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);

//需要设置这个 flag 才能调用 setStatusBarColor 来设置状态栏颜色
window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);

ViewGroup mContentView = (ViewGroup) findViewById(Window.ID_ANDROID_CONTENT);
View mChildView = mContentView.getChildAt(0);
if (mChildView != null) {
//注意不是设置 ContentView 的 FitsSystemWindows, 而是设置 ContentView 的第一个子 View . 使其不为系统 View 预留空间.
ViewCompat.setFitsSystemWindows(mChildView, false);
}
}


Android4.4版本-Adnroid5.0版本

// 4.4 - 5.0版本
private void setStatusBarUpperAPI19() {
Window window = getWindow();
window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);

ViewGroup mContentView = (ViewGroup) findViewById(Window.ID_ANDROID_CONTENT);
View statusBarView = mContentView.getChildAt(0);
//移除假的 View
if (statusBarView != null && statusBarView.getLayoutParams() != null &&
statusBarView.getLayoutParams().height == getStatusBarHeight()) {
mContentView.removeView(statusBarView);
}
//不预留空间
if (mContentView.getChildAt(0) != null) {
ViewCompat.setFitsSystemWindows(mContentView.getChildAt(0), false);
}
}


2. 2着色模式

着色模式的意思是:状态栏显示,状态栏的背景颜色需要设置.如下图:



Android5.0版本以上

private void setStatusBarUpperAPI21(){
Window window = getWindow();
//取消设置透明状态栏,使 ContentView 内容不再覆盖状态栏
window.clearFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);

//需要设置这个 flag 才能调用 setStatusBarColor 来设置状态栏颜色
window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
//设置状态栏颜色
//由于setStatusBarColor()这个API最低版本支持21, 本人的是15,所以如果要设置颜色,自行到style中通过配置文件设置
//        window.setStatusBarColor(getResources().getColor(R.color.colorPrimary));
ViewGroup mContentView = (ViewGroup) findViewById(Window.ID_ANDROID_CONTENT);
View mChildView = mContentView.getChildAt(0);
if (mChildView != null) {
//注意不是设置 ContentView 的 FitsSystemWindows, 而是设置 ContentView 的第一个子 View . 预留出系统 View 的空间.
ViewCompat.setFitsSystemWindows(mChildView, true);
}
}


Android4.4版本-Adnroid5.0版本

private void setStatusBarUpperAPI19() {
Window window = getWindow();
window.addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);

ViewGroup mContentView = (ViewGroup) findViewById(Window.ID_ANDROID_CONTENT);
int statusBarHeight = getStatusBarHeight();
int statusColor = getResources().getColor(R.color.colorPrimary);

View mTopView = mContentView.getChildAt(0);
if (mTopView != null && mTopView.getLayoutParams() != null &&
mTopView.getLayoutParams().height == statusBarHeight) {
//避免重复添加 View
mTopView.setBackgroundColor(statusColor);
return;
}
//使 ChildView 预留空间
if (mTopView != null) {
ViewCompat.setFitsSystemWindows(mTopView, true);
}

//添加假 View
mTopView = new View(this);
ViewGroup.LayoutParams lp = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, statusBarHeight);
mTopView.setBackgroundColor(statusColor);
mContentView.addView(mTopView, 0, lp);
}


2.3 公共函数

在onCreate()中初始化StatusBar

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_drawcolor_mode);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
setStatusBarUpperAPI21();
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
setStatusBarUpperAPI19();
}
}


获取状态栏高度函数

private int getStatusBarHeight(){
int result = 0;
int resId = getResources().getIdentifier("status_bar_height","dimen","android");
if(resId>0){
result = getResources().getDimensionPixelSize(resId);
}
return result;
}


关于NavigationBar的隐藏

如果你用的是Neux手机, 就会发现手机下面还有NavigationBar, 就是退出,Home,程序 3个按键的软键盘. 在全屏模式中, 是无法隐藏掉NavigationBar的. 下面的代码提供隐藏的方法, 可讲代码加入到全屏模式的Activity中:

/**
* 用于控制NavigationBar的隐藏和显示
*/
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
if (hasFocus) {
hideSystemUI();
}
}

private void showSystemUI() {
mDecorView.setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LAYOUT_STABLE
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);
}

private void hideSystemUI() {
mDecorView.setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LAYOUT_STABLE
| View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
//                        | View.SYSTEM_UI_FLAG_FULLSCREEN
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY);
}


Demo地址

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: