天天看點

Android 新特性沉浸式與透明狀态欄

項目一個階段完成,終于有時間可以把這段時間用到的東西整理整理了~_~,最近看到網上很多人都在整Android 4.4那個狀态欄新特性,是以在自己項目中也加了這個,本來直接在國内看的資料,但國内說什麼的都有,這讓我有些迷糊,不知道這個新特性到底是怎麼回事,後來隻能去Google看了官方資料,終于知道這到底是怎麼回事了。

一.有過的疑問

  1. 這個新特性到底是叫Translucent Bars(透明欄)還是叫Immersive Mode(沉浸式模式)呢?
  2. 到底這兩個有什麼差別呢?
  3. 怎麼單獨設定狀态欄的顔色呢?

二.沉浸式設計是什麼(沉浸設計的介紹)

沉浸就是讓人專注在目前的目标情境下感到愉悅與滿足,進而忘記時間的流逝。
這個也就是心流理論,心流理論的核心就是人們廢寝忘食地投入一件事情的狀态。
如果在這種狀态就會出現對時間的錯覺,也就是對時間的認知發生扭曲,在體驗中将時間認知拉長或縮短。
是以,我們可以将為了沉浸式(心流)而進行的設計稱為沉浸式設計也叫心流設計。
           

三.官網與别人對沉浸式的解釋

别人的解釋:

  • 沉浸式就是透明欄也就是Translucent Bars,就是狀态欄與頂部顔色融為一體。
  • android 4.4中的透明漸變狀态欄和虛拟按鈕的樣式,也就是沉浸式。就像Action Bar和狀态欄融為一體。

    如圖:

    Android 新特性沉浸式與透明狀态欄
    ps:到了5.0後就可以為狀态欄設定顔色,是以我認為所謂的沉浸式狀态欄不等于狀态欄變色,即便是變色後跟ActionBar顔色一緻。
  • Translucent Bars隻是透明 狀态/導航 欄的意思,4.4裡是半透明的,在5.0裡是全透明的。而Immersive Mode是屬于全屏狀态,隐藏了狀态欄和導航欄。

Translucent Bars

4.4效果

Android 新特性沉浸式與透明狀态欄

5.0效果

Android 新特性沉浸式與透明狀态欄

谷歌官方的解釋

原文:

Immersive full-screen mode

To provide your app with a layout that fills the entire screen,

the new SYSTEM_UI_FLAG_IMMERSIVE flag for setSystemUiVisibility() (when combined with SYSTEM_UI_FLAG_HIDE_NAVIGATION) enables a new immersive full-screen mode. While immersive full-screen mode is enabled, your activity continues to receive all touch events. The user can reveal the system bars with an inward swipe along the region where the system bars normally appear. This clears the SYSTEM_UI_FLAG_HIDE_NAVIGATION flag (and the SYSTEM_UI_FLAG_FULLSCREEN flag, if applied) so the system bars remain visible. However, if you’d like the system bars to hide again after a few moments, you can instead use the SYSTEM_UI_FLAG_IMMERSIVE_STICKY flag.

Translucent system bars

You can now make the system bars partially translucent with new themes, Theme.Holo.NoActionBar.TranslucentDecor and Theme.Holo.Light.NoActionBar.TranslucentDecor. By enabling translucent system bars, your layout will fill the area behind the system bars, so you must also enable fitsSystemWindows for the portion of your layout that should not be covered by the system bars.

If you’re creating a custom theme, set one of these themes as the parent theme or include the windowTranslucentNavigation and windowTranslucentStatus style properties in your theme.

大概含義:

身臨其境的全屏模式(就是沉浸模式)

為你的app提供了一個全屏的布局檔案,用setSystemUiVisibility() 使用SYSTEM_UI_FLAG_IMMERSIVE标志(與SYSTEM_UI_FLAG_HIDE_NAVIGATION結合)支援新的沉浸模式。這個模式被激活後你的activity還是可以繼續接收觸摸事件。使用者可以用最上端下拉來清除SYSTEM_UI_FLAG_HIDE_NAVIGATION标志,讓狀态欄可見。如果你想讓狀态欄過片刻後在自動隐藏,可以使用SYSTEM_UI_FLAG_IMMERSIVE_STICKY标志。

透明系統欄

你可以使用系統的新主題Theme.Holo.NoActionBar.TranslucentDecor和Theme.Holo.Light.NoActionBar.TranslucentDecor來讓系統欄透明。

如果使用了這個你的布局将填補系統欄後面的區域,是以你也必須在不久中使用fitsSystemWindows=”true”來讓布局不包括系統欄的部分。

如果你要建立一個自定義主題,需要在你的主題樣式中設定windowTranslucentNavigation和windowTranslucentStatus屬性。

是以,Translucent Bars(透明欄)與Immersive Mode(沉浸式模式)是不同的,Translucent Bars還是會顯示狀态欄的,隻不過是透明了;而Immersive Mode不會顯示,而當需要檢視通知的時候隻需要從頂部向下滑動就能呼出通知欄。,然後又會自動隐藏。

四.使用的方法與圖例

* Translucent Bars透明欄*

: 直接設定系統主題方式

因為這個特性是Android 4.4才出現的,隻能在sdk 19以後才能用,是以這個需要在res目錄下建立values-v19目錄(如果沒有),然後在這個目錄下建立檔案 styles.xml。

styles.xml檔案内容

<resources>
    <style name="AppBaseTheme" 
    parent="android:Theme.Holo.NoActionBar.TranslucentDecor">
        <!-- API 19 theme customizations can go here. -->
    </style>
</resources>
           

Theme的值還有:

android:Theme.Holo.Light.NoActionBar.TranslucentDecor
android:Theme.DeviceDefault.Light.NoActionBar.TranslucentDecor
           

: 自定義主題方式

需要在values-v19目錄的styles.xml檔案中添加兩個屬性
<item name="android:windowTranslucentStatus">true</item>
<item name="android:windowTranslucentNavigation">true</item>
           
第二個是管底部導航欄的,是以如果手機沒有底部導航欄可以不加這個。 然後你就可以在values目錄的styles.xml定義自己的主題。
代碼中實作方式
//隐藏ActionBar
requestWindowFeature(Window.FEATURE_NO_TITLE);
    if (VERSION.SDK_INT >= VERSION_CODES.KITKAT) {
    // 透明狀态欄
    getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
    // 透明導航欄
    getWindow().addFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION);
}
           

注意:在代碼中的這個一定要放到setContentView方法之前,否則會報異常:android.util.AndroidRuntimeException: requestFeature() must be called before adding content。

效果圖
Android 新特性沉浸式與透明狀态欄

我們可以看到文字在是在狀态欄底下,我們需要在布局檔案中添加

android:fitsSystemWindows=”true”這個,意思是設定應用布局時是否考慮系統視窗布局;如果為true,将調整系統視窗布局以适應你自定義的布局。
調整後的效果圖
Android 新特性沉浸式與透明狀态欄

* 5 . 0的變色狀态欄*

要想讓狀态欄變化為自己指定的顔色可以使用一個開源庫SystemBarTint

使用前提:

如果要想改變狀态欄的顔色,必須要記得先要設定狀态欄透明。

使用方法:

可以直接把SystemBarTint這個項目中的SystemBarTintManager.java檔案拷貝到你的工程中,然後在你要改變狀态欄顔色的activity中使用如下代碼:

SystemBarTintManager mTintManager = new SystemBarTintManager(this);
mTintManager.setStatusBarTintEnabled(true);
mTintManager.setNavigationBarTintEnabled(true);
mTintManager.setTintColor(color);
           

效果圖:

Android 新特性沉浸式與透明狀态欄

其實改變狀态欄顔色的原理是利用了反射,擷取到了系統修改狀态欄與導航欄點方法,然後進行修改。

Immersive Mode沉浸式模式
直接設定系統主題方式
<resources>
    <style name="AppBaseTheme" parent="android:Theme.NoTitleBar.Fullscreen"/>
    </style>
</resources>
           

還可以設定讓背景透明的主題

<resources>
    <style name="AppBaseTheme" parent="android:Theme.Translucent.NoTitleBar.Fullscreen"/>
    </style>
</resources>
           

: 代碼中實作方式

/* 代碼中實作沉浸式 */
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        // 去掉Activity上面的狀态欄
        if (VERSION.SDK_INT >= VERSION_CODES.KITKAT) {
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
        WindowManager.LayoutParams.FLAG_FULLSCREEN);
        }
           

如果是帶底部導航欄的可以使用如下代碼:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            int UI_OPTIONS = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_FULLSCREEN | View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
            getWindow().getDecorView().setSystemUiVisibility(UI_OPTIONS);
        }
           
效果圖

背景透明與不透明的

Android 新特性沉浸式與透明狀态欄

擴充

使用系統的style自定義actionbar的背景顔色,actionbar上字型的大小與顔色。

<style name="AppTheme" parent="android:Theme.Holo.Light.DarkActionBar">
        <item name="android:actionBarStyle">@style/MyActionBar</item>
    </style>

    <style name="MyActionBar" parent="@android:style/Widget.Holo.Light.ActionBar.Solid.Inverse">
        <!-- 改變actionbar背景色 -->
        <item name="android:background">@color/green</item>
        <item name="android:titleTextStyle">@style/MyActionBara</item>
    </style>

    <style name="MyActionBara" parent="@android:style/TextAppearance.Holo.Widget.ActionBar.Title.Inverse">
        <!-- 改變actionbar字型大小和顔色 -->
        <item name="android:textSize">sp</item>
        <item name="android:textColor">@color/green</item>
    </style>
           

沉浸式——源碼下載下傳位址1

透明——源碼下載下傳位址2

改變狀态欄與actionbar顔色——源碼下載下傳位址3