ITJscott
ITJscott

Reputation: 552

How can I prevent the Nav Bar from leaving behind a black bar? (immersive mode)

An app that uses immersive mode leaves a black bar at the bottom of the screen when the app is returned to after waiting a while (activity is destroyed).

What is happening: (I have enabled the developer option: "Don't keep activities" to reproduce this).

  1. First time launch of the app. Immersive mode works as expected.

  2. Swipe up to reveal the 'immersive sticky' nav bar, and use the 'Home' button to leave the app. The background of the nav bar briefly shows a black background before the app closes.

  3. Use the 'Recents' button, and select the app to resume it.

  4. The app opens to briefly reveal the nav bar over a black bar. The system ui collapses into immersive mode but the black bar remains. systemuiblackbar

This bug also only appears on Lollipop, not KitKat.

I have stripped back the app to simply launching a dummy activity with no functionality apart from setting System UI flags:

public class DummyActivity extends FragmentActivity {

@Override
public void onWindowFocusChanged(boolean hasFocus) {
    super.onWindowFocusChanged(hasFocus);
    if (hasFocus) {
        setSystemUiVisibility();
    }
}

public void setSystemUiVisibility() {
    if (getWindow() != null && getWindow().getDecorView() != null) {
        getWindow().getDecorView().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);
        }
    }
}

EDIT: After creating a new fresh project with only this Activity I have seen this issue reproduced when using an app theme extending "android:Theme.Holo"..., and fixed the issue in this sample project when I extend the Material theme instead:

Change

<style name="AppTheme" parent="android:Theme.Holo.Light.NoActionBar.Fullscreen">
</style>

to

<style name="AppTheme"parent="android:Theme.Material.Light.NoActionBar.Fullscreen">
</style>

Unfortunately this fix hasn't solved the issues in my main project, but it brings me closer to a solution and might help others with the same issue.

Upvotes: 7

Views: 2988

Answers (3)

Badr Bujbara
Badr Bujbara

Reputation: 8691

For me it was a black bar at the top. Key thing was this in the activity style:

// Important to draw behind cutouts
<item name="android:windowLayoutInDisplayCutoutMode">shortEdges</item> 

Here is my code:

1- In Activity

private fun hideSystemUI() {
    sysUIHidden = true
    // Enables regular immersive mode.
    // For "lean back" mode, remove SYSTEM_UI_FLAG_IMMERSIVE.
    // Or for "sticky immersive," replace it with SYSTEM_UI_FLAG_IMMERSIVE_STICKY
    window.decorView.systemUiVisibility = (
            View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
            or View.SYSTEM_UI_FLAG_LAYOUT_STABLE 
            // Hide the nav bar and status bar
            or View.SYSTEM_UI_FLAG_HIDE_NAVIGATION // Hide nav bar
            or View.SYSTEM_UI_FLAG_FULLSCREEN // Hide status bar
            )
}


private fun showSystemUI() {
    sysUIHidden = false
    window.decorView.systemUiVisibility = (
            View.SYSTEM_UI_FLAG_LAYOUT_STABLE
            // Set the content to appear under the system bars so that the
            // content doesn't resize when the system bars hide and show.
            or View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION // layout Behind nav bar
            or View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN // layout Behind status bar
            )
}

2- In root view of xml layout

android:fitsSystemWindows="false"

3- Style for the Full screen Activity:

<style name="FullscreenTheme" parent="AppTheme">
    <item name="android:actionBarStyle">@style/FullscreenActionBarStyle</item>
    <item name="android:windowActionBarOverlay">true</item>
    <item name="android:windowBackground">@null</item>
    <item name="metaButtonBarStyle">?android:attr/buttonBarStyle</item>
    <item name="metaButtonBarButtonStyle">?android:attr/buttonBarButtonStyle</item>
    <item name="android:statusBarColor">#50000000</item>
    <item name="android:navigationBarColor">#50000000</item>
    // Important to draw behind cutouts
    <item name="android:windowLayoutInDisplayCutoutMode">shortEdges</item> 
</style>

<style name="FullscreenActionBarStyle" parent="Widget.AppCompat.ActionBar">
    <item name="android:background">@color/sysTransparent</item>
</style>

Upvotes: 3

Ogosoka
Ogosoka

Reputation: 11

Using

<style name="AppTheme"parent="android:Theme.Material.Light.NoActionBar.Fullscreen"> </style>

does solved the problem, but it only work for api:21.

In order to make it works for all system. You can create a directory called style-v21 in res directory, and put that style.xml there. Android system is smart enough to pick which one to use for new or old phone.

Upvotes: 1

Nick
Nick

Reputation: 89

I was having the same problem. Here are a few updates I made which made it go away. Hopefully one of these works for you!

activity_main.xml

android:fitsSystemWindows="false"

style-v21

<item name="android:windowTranslucentStatus">true</item>
<item name="android:windowSharedElementsUseOverlay">false</item>

MainActivity.java

getWindow().getDecorView().setSystemUiVisibility(
            View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
                    | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
                    | View.SYSTEM_UI_FLAG_FULLSCREEN
    );

Upvotes: 3

Related Questions