美文网首页Android潜修者Android-ui效果Android开发学习
另外两种android沉浸式状态栏实现思路

另外两种android沉浸式状态栏实现思路

作者: dongjunkun | 来源:发表于2015-12-30 11:50 被阅读17931次

    关于沉浸式状态栏相信大家都不陌生,IOS系统很早就有,android5.0及以后版本都支持给状态栏着色,而目前android主流版本还是4.4,网上通用实现4.4(API19)沉浸式状态栏也都是依赖于可以将状态栏变为透明的属性,再为其着色,主要实现代码:

    @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_match_actionbar);
                    //只对api19以上版本有效
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
                setTranslucentStatus(true);
            }
                    //为状态栏着色
            SystemBarTintManager tintManager = new SystemBarTintManager(this);
            tintManager.setStatusBarTintEnabled(true);
            tintManager.setStatusBarTintResource(R.color.statusbar_bg);
    
        }
    
        @TargetApi(19) 
        private void setTranslucentStatus(boolean on) {
            Window win = getWindow();
            WindowManager.LayoutParams winParams = win.getAttributes();
            final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
            if (on) {
                winParams.flags |= bits;
            } else {
                winParams.flags &= ~bits;
            }
            win.setAttributes(winParams);
        }
    
    

    再在根布局添加以下两个属性:

     android:fitsSystemWindows="true" 
     android:clipToPadding="false" 
    

    这样就可以了,以上着色使用了SystemBarTint

    为什么我要寻找其他的方案?

    面对大多数的界面自然是没有多大问题,但是针对类似QQ这种侧滑的界面,如图:

    Screenshot_2015-12-30-09-55-33.png

    我的手机系统版本是4.4的,如果想做成QQ侧滑背景这样的效果,使用上面的方案就变成了这样

    Screenshot_2015-12-30-09-55-34.png

    这样出来的效果就会很丑,于是才有了改进版的方案,不知QQ是否是这样做的。
    除了上述的缺陷以外,还有一点看着不是很舒服,就是当我使用抽屉菜单或者滑动返回效果的时候是这样的


    状态栏并没有阴影效果

    我想要的效果是这样的

    状态栏也会跟着一起滑动

    第一种思路

    自定义一个状态栏,不能添加“ android:fitsSystemWindows="true"
    ”这个属性,不然无法填充到状态栏,如下

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
                  android:layout_width="match_parent"
                  android:layout_height="match_parent"
                  android:background="@color/colorAccent"
                  android:orientation="vertical">
    
        <View
            android:id="@+id/status_bar"
            android:layout_width="match_parent"
            android:layout_height="20dp"/>
    
        <FrameLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"/>
    
    </LinearLayout>
    

    在到代码中判断

     @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            View statusBar = findViewById(R.id.status_bar);
    
            setContentView(R.layout.activity_test);
            //判断SDK版本是否大于等于19,大于就让他显示,小于就要隐藏,不然低版本会多出来一个
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
                setTranslucentStatus(true);
                statusBar.setVisibility(View.VISIBLE);
                //还有设置View的高度,因为每个型号的手机状态栏高度都不相同
            }else{
                statusBar.setVisibility(View.GONE);
            }
        }
        @TargetApi(19)
        private void setTranslucentStatus(boolean on) {
            Window win = getWindow();
            WindowManager.LayoutParams winParams = win.getAttributes();
            final int bits = WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
            if (on) {
                winParams.flags |= bits;
            } else {
                winParams.flags &= ~bits;
            }
            win.setAttributes(winParams);
        }~~~
    其实,这样已经解决了我上面提出的两个问题
    ####第二种实现方案
    第二种方案是为了解决第一种方案中遇到的奇葩问题,设置了透明属性的界面(聊天及底下评论的框框)不能被系统输入法顶上去,之前写过一篇[Android 聊天界面背景图片被输入法“顶上去”问题解析](http://www.jianshu.com/p/c632fa3e44a1),现在遇到的就是无论如何聊天的输入框都不能被系统输入法顶上去(就是打字看不到输入框),经过一番测试,发现竟然和“ android:fitsSystemWindows="true" 
    ”这个属性有关,加上去输入框就没问题,但自定义的状态栏不能被填充到真正的状态栏位置
    ![未标题-1.png](http:https://img.haomeiwen.com/i697635/a3862bb468776506.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
    陷入了两难的境地,加还是不加都有问题,而且都特别明显,说了半天,来看看第二种方案。
    

    <?xml version="1.0" encoding="utf-8"?>
    <RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@android:color/holo_green_light"
    android:fitsSystemWindows="true"
    tools:context="com.saidtx.myapplication.TestActivity">

    <ScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_above="@+id/edit"
        android:background="@android:color/white">
    
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
    
            <TextView
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:gravity="center"
                android:padding="20dp"
                android:text="@string/previews"/>
        </LinearLayout>
    </ScrollView>
    
    <LinearLayout
        android:id="@+id/edit"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:background="@android:color/white">
    
        <EditText
            android:layout_width="match_parent"
            android:layout_height="wrap_content"/>
    </LinearLayout>
    

    </RelativeLayout>

    关键在于下面两个属性,还有需要在其他子布局添加背景,不然就跟随了最外层的背景,代码部分还是采用网上通用方案,只是不需要自定义的状态栏了,也不需要计算状态栏的高度
    

    android:fitsSystemWindows="true"
    android:background="@android:color/holo_green_light"

    ![最终效果](http:https://img.haomeiwen.com/i697635/9061309dd3ad5546.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
    
    源码下载:[StatusBarDemo](https://github.com/dongjunkun/StatusBarDemo)
    
    > 问题虽然解决了,却还是不明白其中的原由,希望有心人解惑

    相关文章

      网友评论

      • 烤雪迟夏写长信:博主 用了你第一种 ,但是我的标题栏和上方重叠了 怎么办
        dongjunkun:@烤雪迟夏写长信 你运行下我的demo试试,如果没有问题,仔细检查下你的代码
      • huwan:试了,貌似不行。也不留demo。。。。哎。。。
        dongjunkun: @huwan 有demo
      • sendtion:这文章好熟悉
      • artshell:楼主代码,搞乱了逻辑吧:

        //为状态栏着色
        SystemBarTintManager tintManager = new SystemBarTintManager(this);
        tintManager.setStatusBarTintEnabled(true);
        tintManager.setStatusBarTintResource(R.color.statusbar_bg);
        API 19 以下的API也会执行这段代码吧! , 把我搞蒙了
      • Ziv_xiao:“底下聊天及评论输入框不能被输入法顶上去” 问题的解决方案可以看下这里http://www.jianshu.com/p/a95a1b84da11
      • 星际之痕:这种解决方案不适用于使用actionbar或者toolbar的情况!感觉不太实用。
      • Kejin:关于那个 Navigation View 的状态栏问题, 其实是支持沉浸式的,不过是 v21以上, 我的这篇blog有写 你可以看一下: https://liungkejin.github.io/2016/04/10/Custom-NavigationView-Problems.html
      • pousemoi:能不能把沉浸式状态栏不影响输入框上移的demo发一份,,感激不尽
        dongjunkun:@pousemoi https://github.com/dongjunkun/StatusBarDemo
      • a7eb9c8e544c:最近也在研究,谢谢分享
      • SScience:之前也研究过小会status bar,这是我的解决方案http://blog.csdn.net/u013260551/article/details/50372991,请赐教(●'◡'●)
        dongjunkun:@幸运Science 解决了ToolBar的问题,不错
      • 冰冰的冻结:能不能看看实现的Demo
        冰冰的冻结: @dongjunkun 恩恩,我最近也在研究这个,你说的最后一个方案希望来个例子,最近也找了许多例子,没有找到好的哈哈,你要是能发个例子想看看你的实现方式
        dongjunkun:@冰冰的冻结 这个嘛,随手写的,代码真的不多,以上就是全部,但是要理解,注意我提到的一些细节
      • 皮球二二:大神你好,还有一个问题,QQ那种状态栏字体变黑的功能是怎么做,我现在这样做,都是白色字体,这样背景如果也是白的就很难看了
        SScience:@dongjunkun 修改状态栏字体图标颜色只有sdk23以上才有官方api提高修改(SYSTEM_UI_FLAG_LIGHT_STATUS_BAR),miui等是改了framework了吧(?)
        皮球二二:@dongjunkun 嗯,我就找到魅族跟小米的
        dongjunkun:@r17171709 这个问题好像与机型有关系,不同的机型设置状态栏字体颜色的api不一样,比较麻烦
      • 501ce0aa8def:加油↖(^ω^)↗
      • 501ce0aa8def:😍😍😍
      • bd75332b47e4:虽然看不懂,但是我要学
        dongjunkun: @某日遇见 加油
      • 1ab444348f0b:输入法皮肤相同的路过
      • 皮球二二:您好,你的意思是直接在布局中加这两句就行了?就能做出qq侧滑的效果?
        dongjunkun:@r17171709 还得看editText在不在最下边,这个问题是很坑,不过只是目前没有办法,有关输入法方面也得好好研究研究
        皮球二二:@dongjunkun 好的谢谢。我您好,我看你的文章描述的第一种情况有edittext导致bug的情况,如果页面同时有侧滑并且edittext,那就没办法了吧
        dongjunkun:@r17171709 我没有太明白你的意思,好像不止这两句吧,而且我提到了两种方案,不止你说的是哪一种,第二种是无法实现QQ沉浸式状态栏的效果,第一种可行,但具体还得分情况,你可以搜我的开发的应用“赛动美途”看看完整效果(4.4以下是看不到效果的)
      • EthanNJ:我虽然搞过 但是在使用到fragment的时候出现把toolsbar顶到状态栏里面去 后来就把代码注释了
        dongjunkun:@謗謗糖V黄小懒 鸿洋大神的方案我也看过,但好像行不通,那个属性需要加在fragment所在的Activity的根布局上才有用,fragment中添加是无效的
        EthanNJ:@dongjunkun 加了。只有一个fragment里面的toolbar被顶上去,其他都正常! 我是用的张鸿洋的方法!
        dongjunkun:@謗謗糖V黄小懒 toolbar被顶上去,应该是没有加android:fitsSystemWindows="true"
        导致的,第一种方案就是利用了不加这个属性可以将view顶到状态栏里面的特性添加的自定义的状态栏
      • 产品方法论集散地:那19下的咋整呢?
        dongjunkun: @ShanZha 那就没办法了
      • 天空飞过的猪:虽然不懂,但知道你很牛逼

      本文标题:另外两种android沉浸式状态栏实现思路

      本文链接:https://www.haomeiwen.com/subject/ullihttx.html