实现沉浸式状态栏效果

android:fitsSystemWindows属性可以实现状态栏沉浸式效果,但是xml中需要配合CoordinatorLayout处理,但是在CoordinatorLayout中的组件会自动显示在状态栏下面,如果希望设置一张图片,填满状态栏,那么可以配合CollapsingToolbarLayout、DrawerLayout等进行处理

<?xml version="1.0" encoding="utf-8"?>
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#ff66ff"
    android:fitsSystemWindows="true">

    <com.google.android.material.appbar.CollapsingToolbarLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true">

        <ImageView
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:scaleType="centerCrop"
            android:src="@drawable/bg"
            android:fitsSystemWindows="true"
            />

    </com.google.android.material.appbar.CollapsingToolbarLayout>

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button"
        />

</androidx.coordinatorlayout.widget.CoordinatorLayout>

这里我们在ImageView的外面又包裹了一层CollapsingToolbarLayout,并且给CollapsingToolbarLayout也设置了android:fitsSystemWindows属性,这样CollapsingToolbarLayout就可以将内容延申到状态栏区域了。

给ImageView同样设置了android:fitsSystemWindows属性,如此一来,就可以让图片显示在状态栏的背后了。

如果采用FrameLayout布局,那么为了实现沉浸式状态栏的效果,我们手动在MainActivity当中调用setSystemUiVisibility()函数,来将FrameLayout的内容延伸到状态栏区域:

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        window.statusBarColor = Color.TRANSPARENT
        val frameLayout = findViewById<FrameLayout>(R.id.root_layout)
        frameLayout.systemUiVisibility = (SYSTEM_UI_FLAG_LAYOUT_STABLE
                or SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN)
    }

}

这样xml中的组件会直接占用状态栏空间,如果需要设置某些组件在状态栏下显示,那么可以借助setOnApplyWindowInsetsListener()函数去监听WindowInsets发生变化的事件,当有监听到发生变化时,我们可以读取顶部Insets的大小,然后对控件进行相应距离的偏移。

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        window.statusBarColor = Color.TRANSPARENT
        val frameLayout = findViewById<FrameLayout>(R.id.root_layout)
        frameLayout.systemUiVisibility = (SYSTEM_UI_FLAG_LAYOUT_STABLE
                or SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN)

        val button = findViewById<Button>(R.id.button)
        ViewCompat.setOnApplyWindowInsetsListener(button) { view, insets ->
            val params = view.layoutParams as FrameLayout.LayoutParams
            params.topMargin = insets.systemWindowInsetTop
            insets
        }
    }

}

参考链接:https://blog.csdn.net/guolin_blog/article/details/123023395

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容