Reland "Set system bar appearance using WindowInsetsController" (flutter/engine#29403)

This commit is contained in:
Emmanuel Garcia
2021-10-29 16:13:03 -07:00
committed by GitHub
parent 64fc8078e0
commit 28a5062995
6 changed files with 121 additions and 9 deletions

2
DEPS
View File

@@ -570,7 +570,7 @@ deps = {
'packages': [
{
'package': 'flutter/android/embedding_bundle',
'version': 'last_updated:2021-10-18T13:21:02-0700'
'version': 'last_updated:2021-10-28T23:34:47-0700'
}
],
'condition': 'download_android_deps',

View File

@@ -20,6 +20,7 @@ import androidx.activity.OnBackPressedDispatcherOwner;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.annotation.VisibleForTesting;
import androidx.core.view.WindowInsetsControllerCompat;
import io.flutter.Log;
import io.flutter.embedding.engine.systemchannels.PlatformChannel;
import java.io.FileNotFoundException;
@@ -364,7 +365,8 @@ public class PlatformPlugin {
PlatformChannel.SystemChromeStyle systemChromeStyle) {
Window window = activity.getWindow();
View view = window.getDecorView();
int flags = view.getSystemUiVisibility();
WindowInsetsControllerCompat windowInsetsControllerCompat =
new WindowInsetsControllerCompat(window, view);
// SYSTEM STATUS BAR -------------------------------------------------------------------
// You can't change the color of the system status bar until SDK 21, and you can't change the
@@ -377,11 +379,14 @@ public class PlatformPlugin {
if (systemChromeStyle.statusBarIconBrightness != null) {
switch (systemChromeStyle.statusBarIconBrightness) {
case DARK:
// View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR
flags |= 0x2000;
// Dark status bar icon brightness.
// Light status bar appearance.
windowInsetsControllerCompat.setAppearanceLightStatusBars(true);
break;
case LIGHT:
flags &= ~0x2000;
// Light status bar icon brightness.
// Dark status bar appearance.
windowInsetsControllerCompat.setAppearanceLightStatusBars(false);
break;
}
}
@@ -408,11 +413,14 @@ public class PlatformPlugin {
if (systemChromeStyle.systemNavigationBarIconBrightness != null) {
switch (systemChromeStyle.systemNavigationBarIconBrightness) {
case DARK:
// View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
flags |= 0x10;
// Dark navigation bar icon brightness.
// Light navigation bar appearance.
windowInsetsControllerCompat.setAppearanceLightNavigationBars(true);
break;
case LIGHT:
flags &= ~0x10;
// Light navigation bar icon brightness.
// Dark navigation bar appearance.
windowInsetsControllerCompat.setAppearanceLightNavigationBars(false);
break;
}
}
@@ -438,7 +446,6 @@ public class PlatformPlugin {
systemChromeStyle.systemNavigationBarContrastEnforced);
}
view.setSystemUiVisibility(flags);
currentTheme = systemChromeStyle;
}

View File

@@ -1,5 +1,7 @@
package io.flutter.plugin.platform;
import static android.view.WindowInsetsController.APPEARANCE_LIGHT_NAVIGATION_BARS;
import static android.view.WindowInsetsController.APPEARANCE_LIGHT_STATUS_BARS;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
@@ -20,6 +22,7 @@ import android.net.Uri;
import android.os.Build;
import android.view.View;
import android.view.Window;
import android.view.WindowInsetsController;
import androidx.activity.OnBackPressedCallback;
import androidx.fragment.app.FragmentActivity;
import io.flutter.embedding.engine.systemchannels.PlatformChannel;
@@ -216,6 +219,98 @@ public class PlatformPluginTest {
}
}
@Config(sdk = 30)
@Test
public void setNavigationBarIconBrightness() {
if (Build.VERSION.SDK_INT >= 30) {
View fakeDecorView = mock(View.class);
WindowInsetsController fakeWindowInsetsController = mock(WindowInsetsController.class);
Window fakeWindow = mock(Window.class);
when(fakeWindow.getDecorView()).thenReturn(fakeDecorView);
when(fakeWindow.getInsetsController()).thenReturn(fakeWindowInsetsController);
Activity fakeActivity = mock(Activity.class);
when(fakeActivity.getWindow()).thenReturn(fakeWindow);
PlatformChannel fakePlatformChannel = mock(PlatformChannel.class);
PlatformPlugin platformPlugin = new PlatformPlugin(fakeActivity, fakePlatformChannel);
SystemChromeStyle style =
new SystemChromeStyle(
null, // statusBarColor
null, // statusBarIconBrightness
null, // systemStatusBarContrastEnforced
null, // systemNavigationBarColor
Brightness.LIGHT, // systemNavigationBarIconBrightness
null, // systemNavigationBarDividerColor
null); // systemNavigationBarContrastEnforced
platformPlugin.mPlatformMessageHandler.setSystemUiOverlayStyle(style);
verify(fakeWindowInsetsController)
.setSystemBarsAppearance(0, APPEARANCE_LIGHT_NAVIGATION_BARS);
style =
new SystemChromeStyle(
null, // statusBarColor
null, // statusBarIconBrightness
null, // systemStatusBarContrastEnforced
null, // systemNavigationBarColor
Brightness.DARK, // systemNavigationBarIconBrightness
null, // systemNavigationBarDividerColor
null); // systemNavigationBarContrastEnforced
platformPlugin.mPlatformMessageHandler.setSystemUiOverlayStyle(style);
verify(fakeWindowInsetsController)
.setSystemBarsAppearance(
APPEARANCE_LIGHT_NAVIGATION_BARS, APPEARANCE_LIGHT_NAVIGATION_BARS);
}
}
@Config(sdk = 30)
@Test
public void setStatusBarIconBrightness() {
if (Build.VERSION.SDK_INT >= 30) {
View fakeDecorView = mock(View.class);
WindowInsetsController fakeWindowInsetsController = mock(WindowInsetsController.class);
Window fakeWindow = mock(Window.class);
when(fakeWindow.getDecorView()).thenReturn(fakeDecorView);
when(fakeWindow.getInsetsController()).thenReturn(fakeWindowInsetsController);
Activity fakeActivity = mock(Activity.class);
when(fakeActivity.getWindow()).thenReturn(fakeWindow);
PlatformChannel fakePlatformChannel = mock(PlatformChannel.class);
PlatformPlugin platformPlugin = new PlatformPlugin(fakeActivity, fakePlatformChannel);
SystemChromeStyle style =
new SystemChromeStyle(
null, // statusBarColor
Brightness.LIGHT, // statusBarIconBrightness
null, // systemStatusBarContrastEnforced
null, // systemNavigationBarColor
null, // systemNavigationBarIconBrightness
null, // systemNavigationBarDividerColor
null); // systemNavigationBarContrastEnforced
platformPlugin.mPlatformMessageHandler.setSystemUiOverlayStyle(style);
verify(fakeWindowInsetsController).setSystemBarsAppearance(0, APPEARANCE_LIGHT_STATUS_BARS);
style =
new SystemChromeStyle(
null, // statusBarColor
Brightness.DARK, // statusBarIconBrightness
null, // systemStatusBarContrastEnforced
null, // systemNavigationBarColor
null, // systemNavigationBarIconBrightness
null, // systemNavigationBarDividerColor
null); // systemNavigationBarContrastEnforced
platformPlugin.mPlatformMessageHandler.setSystemUiOverlayStyle(style);
verify(fakeWindowInsetsController)
.setSystemBarsAppearance(APPEARANCE_LIGHT_STATUS_BARS, APPEARANCE_LIGHT_STATUS_BARS);
}
}
@Config(sdk = 29)
@Test
public void setSystemUiMode() {

View File

@@ -37,6 +37,7 @@ android {
dependencies {
testImplementation files(project.property("flutter_jar"))
testImplementation "androidx.annotation:annotation:1.1.0"
testImplementation "androidx.core:core:1.6.0"
testImplementation "androidx.fragment:fragment:1.1.0"
testImplementation "androidx.lifecycle:lifecycle-runtime:2.2.0"
testImplementation "androidx.lifecycle:lifecycle-common-java8:2.2.0"

View File

@@ -57,5 +57,13 @@
"provides": [
"androidx.tracing.Trace"
]
},
{
"url": "https://dl.google.com/android/maven2/androidx/core/core/1.6.0/core-1.6.0.aar",
"out_file_name": "androidx_core.aar",
"maven_dependency": "androidx.core:core:1.6.0",
"provides": [
"androidx.core.view.WindowInsetsControllerCompat"
]
}
]

View File

@@ -41,6 +41,7 @@ android {
dependencies {
embedding "androidx.annotation:annotation:1.1.0"
embedding "androidx.core:core:1.6.0"
embedding "androidx.fragment:fragment:1.1.0"
embedding "androidx.tracing:tracing:1.0.0"