Keywords: Android | Immersive Mode | Navigation Bar Hiding
Abstract: This technical article provides an in-depth analysis of implementing permanent navigation bar hiding in Android activities, focusing on the immersive mode introduced in Android 4.4+. The article examines key system UI flags such as View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY and demonstrates their application through comprehensive code examples. It covers essential lifecycle methods including onWindowFocusChanged and OnSystemUiVisibilityChangeListener, addressing common issues like navigation bar reappearance during volume button operations. The implementation ensures the navigation bar remains hidden throughout the activity lifecycle until onStop().
Application of Immersive Mode in Android System UI Management
In Android application development, achieving a full-screen experience often requires hiding the system navigation bar. Developers initially attempted using the View.SYSTEM_UI_FLAG_HIDE_NAVIGATION flag, but this approach has a significant limitation: the navigation bar reappears when the user touches the screen. This does not meet the requirement of "permanently hiding until the activity's onStop()" method.
Immersive Mode Implementation for Android 4.4+
For Android 4.4 (API level 19) and above, Google introduced immersive mode, providing an official solution for permanently hiding the navigation bar. Immersive mode allows applications to temporarily hide system bars while maintaining the ability for users to recall them with specific gestures.
Analysis of Core Flag Combinations
Implementing permanent navigation bar hiding requires combining multiple system UI flags:
final int flags = 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;
The View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY flag is particularly crucial, as it causes system bars to automatically hide after brief display without clearing other flags. This "sticky" behavior is fundamental to achieving the permanent hiding effect.
Complete Activity Implementation Solution
The following code demonstrates a comprehensive implementation for permanently hiding the navigation bar in an Activity:
private int currentApiVersion;
@Override
@SuppressLint("NewApi")
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
currentApiVersion = android.os.Build.VERSION.SDK_INT;
final int flags = 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;
if (currentApiVersion >= Build.VERSION_CODES.KITKAT) {
getWindow().getDecorView().setSystemUiVisibility(flags);
final View decorView = getWindow().getDecorView();
decorView.setOnSystemUiVisibilityChangeListener(
new View.OnSystemUiVisibilityChangeListener() {
@Override
public void onSystemUiVisibilityChange(int visibility) {
if ((visibility & View.SYSTEM_UI_FLAG_FULLSCREEN) == 0) {
decorView.setSystemUiVisibility(flags);
}
}
});
}
}
@SuppressLint("NewApi")
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
if (currentApiVersion >= Build.VERSION_CODES.KITKAT && hasFocus) {
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);
}
}
Volume Button Operation Issues and Solutions
During testing, it was discovered that when users press volume buttons, the navigation bar may reappear and not automatically hide again. This occurs because the system temporarily alters the system UI state while processing volume button events. By implementing an OnSystemUiVisibilityChangeListener, developers can detect changes in system UI visibility and immediately reapply the hiding flags when the navigation bar appears.
Version Compatibility Considerations
For versions below Android 4.4, different implementation approaches are required. Alternative solutions suggest providing adaptation strategies for different API levels:
public void FullScreencall() {
if (Build.VERSION.SDK_INT > 11 && Build.VERSION.SDK_INT < 19) {
View v = this.getWindow().getDecorView();
v.setSystemUiVisibility(View.GONE);
} else if (Build.VERSION.SDK_INT >= 19) {
View decorView = getWindow().getDecorView();
int uiOptions = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
| View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
decorView.setSystemUiVisibility(uiOptions);
}
}
For older API versions, while immersive mode is unavailable, basic hiding functionality can be achieved through View.GONE. It is recommended to call this function in the onResume() method to ensure hiding settings are reapplied each time the activity resumes.
In-depth Analysis of Implementation Principles
Immersive mode implementation is based on Android's window management system. The setSystemUiVisibility() method communicates with WindowManagerService to request changes to the current window's system UI state. The LAYOUT-related flags in the combination ensure that content layout remains stable despite system bar hiding, maintaining UI consistency.
The invocation of the onWindowFocusChanged() method is critical because system UI state may be reset when an activity regains focus after losing it (such as when a dialog appears). By reapplying flags in this method, developers can ensure the navigation bar remains consistently hidden.
Best Practice Recommendations
1. Always check API versions to ensure code runs on supported devices
2. Set system UI flags in both onCreate() and onWindowFocusChanged()
3. Use OnSystemUiVisibilityChangeListener to handle unexpected display scenarios
4. Provide fallback solutions for applications requiring backward compatibility
5. Thoroughly test on devices with different manufacturer customizations to ensure compatibility
Conclusion
By appropriately combining system UI flags, particularly leveraging the sticky特性 of View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY, along with proper lifecycle management and event listening, developers can achieve permanent navigation bar hiding on Android 4.4+ devices. This approach maintains system usability (users can still recall system bars with specific gestures) while providing applications with a true full-screen experience, representing current best practices for implementing immersive interfaces in Android development.