Loading core/java/android/view/ViewRootImpl.java +21 −0 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_M import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_APPEARANCE_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_BEHAVIOR_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FIT_INSETS_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DECOR_VIEW_VISIBILITY; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_INSET_PARENT_FRAME_BY_IME; Loading Loading @@ -1385,6 +1386,7 @@ public final class ViewRootImpl implements ViewParent, // Keep track of the actual window flags supplied by the client. mClientWindowLayoutFlags = attrs.flags; adjustLayoutInDisplayCutoutMode(attrs); setAccessibilityFocus(null, null); if (view instanceof RootViewSurfaceTaker) { Loading Loading @@ -1987,6 +1989,9 @@ public final class ViewRootImpl implements ViewParent, final int appearanceAndBehaviorPrivateFlags = mWindowAttributes.privateFlags & (PRIVATE_FLAG_APPEARANCE_CONTROLLED | PRIVATE_FLAG_BEHAVIOR_CONTROLLED); // Calling this before copying prevents redundant LAYOUT_CHANGED. final int layoutInDisplayCutoutModeFromCaller = adjustLayoutInDisplayCutoutMode(attrs); final int changes = mWindowAttributes.copyFrom(attrs); if ((changes & WindowManager.LayoutParams.TRANSLUCENT_FLAGS_CHANGED) != 0) { // Recompute system ui visibility. Loading @@ -2003,6 +2008,9 @@ public final class ViewRootImpl implements ViewParent, mWindowAttributes.packageName = mBasePackageName; } // Restore the layoutInDisplayCutoutMode of the caller; attrs.layoutInDisplayCutoutMode = layoutInDisplayCutoutModeFromCaller; // Restore preserved flags. mWindowAttributes.systemUiVisibility = systemUiVisibility; mWindowAttributes.subtreeSystemUiVisibility = subtreeSystemUiVisibility; Loading Loading @@ -2046,6 +2054,19 @@ public final class ViewRootImpl implements ViewParent, } } private int adjustLayoutInDisplayCutoutMode(WindowManager.LayoutParams attrs) { final int originalMode = attrs.layoutInDisplayCutoutMode; if ((attrs.privateFlags & PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED) != 0 && attrs.isFullscreen() && attrs.getFitInsetsTypes() == 0 && attrs.getFitInsetsSides() == 0) { if (originalMode != LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS) { attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; } } return originalMode; } void handleAppVisibility(boolean visible) { if (Trace.isTagEnabled(Trace.TRACE_TAG_VIEW)) { Trace.instant(Trace.TRACE_TAG_VIEW, TextUtils.formatSimple( Loading core/java/com/android/internal/policy/PhoneWindow.java +0 −3 Original line number Diff line number Diff line Loading @@ -2486,9 +2486,6 @@ public class PhoneWindow extends Window implements MenuBuilder.Callback { setFlags(FLAG_LAYOUT_IN_SCREEN|FLAG_LAYOUT_INSET_DECOR, flagsToUpdate); params.setFitInsetsSides(0); params.setFitInsetsTypes(0); if (mEdgeToEdgeEnforced) { params.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; } } if (a.getBoolean(R.styleable.Window_windowNoTitle, false)) { Loading core/res/res/values/attrs.xml +9 −8 Original line number Diff line number Diff line Loading @@ -2300,7 +2300,7 @@ ensure that the status bar has enough contrast with the contents of this app, and set an appropriate effective bar background accordingly. See: {@link android.R.attr#enforceStatusBarContrast} <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading @@ -2320,7 +2320,7 @@ ensure that the navigation bar has enough contrast with the contents of this app, and set an appropriate effective bar background accordingly. See: {@link android.R.attr#enforceNavigationBarContrast} <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading @@ -2335,7 +2335,7 @@ have been requested to be translucent with {@link android.R.attr#windowTranslucentNavigation}. Corresponds to {@link android.view.Window#setNavigationBarDividerColor(int)}. <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading Loading @@ -2427,7 +2427,9 @@ <!-- Controls how the window is laid out if there is a {@code DisplayCutout}. <p> Defaults to {@code default}. Defaults to {@code default}. But if the window fills the screen, and it belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, the behavior will be the same as specifying {@code always} regardless. <p> See also {@link android.view.WindowManager.LayoutParams#layoutInDisplayCutoutMode Loading Loading @@ -2524,8 +2526,8 @@ <!-- Flag indicating whether this window would opt-out the edge-to-edge enforcement. <p>If this is false, the edge-to-edge enforcement will be applied to the window if its app targets <p>If this is false, the edge-to-edge enforcement will be applied to the window if it belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above. The affected behaviors are: <ul> Loading @@ -2533,9 +2535,8 @@ through the {@link android.view.WindowInsets} to the content view, as if calling {@link android.view.Window#setDecorFitsSystemWindows(boolean)} with false. <li>{@link android.view.WindowManager.LayoutParams#layoutInDisplayCutoutMode} of the non-floating windows will be set to {@link the fill-screen windows will behave as specifying {@link android.view.WindowManager.LayoutParams#LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS}. Changing it to other values will cause {@link lang.IllegalArgumentException}. <li>The framework will set {@link android.R.attr#statusBarColor}, {@link android.R.attr#navigationBarColor}, and {@link android.R.attr#navigationBarDividerColor} to transparent. Loading core/tests/coretests/src/com/android/internal/policy/PhoneWindowTest.java +2 −9 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_M import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT; import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER; import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY; import static android.view.flags.Flags.FLAG_TOOLKIT_SET_FRAME_RATE_READ_ONLY; Loading Loading @@ -82,15 +81,9 @@ public final class PhoneWindowTest { createPhoneWindowWithTheme(R.style.LayoutInDisplayCutoutModeUnset); installDecor(); if ((mPhoneWindow.getAttributes().privateFlags & PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED) != 0 && !mPhoneWindow.isFloating()) { assertThat(mPhoneWindow.getAttributes().layoutInDisplayCutoutMode, is(LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS)); } else { assertThat(mPhoneWindow.getAttributes().layoutInDisplayCutoutMode, is(LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT)); } } @Test public void layoutInDisplayCutoutMode_default() throws Exception { Loading Loading
core/java/android/view/ViewRootImpl.java +21 −0 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_M import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_APPEARANCE_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_BEHAVIOR_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FIT_INSETS_CONTROLLED; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DECOR_VIEW_VISIBILITY; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_INSET_PARENT_FRAME_BY_IME; Loading Loading @@ -1385,6 +1386,7 @@ public final class ViewRootImpl implements ViewParent, // Keep track of the actual window flags supplied by the client. mClientWindowLayoutFlags = attrs.flags; adjustLayoutInDisplayCutoutMode(attrs); setAccessibilityFocus(null, null); if (view instanceof RootViewSurfaceTaker) { Loading Loading @@ -1987,6 +1989,9 @@ public final class ViewRootImpl implements ViewParent, final int appearanceAndBehaviorPrivateFlags = mWindowAttributes.privateFlags & (PRIVATE_FLAG_APPEARANCE_CONTROLLED | PRIVATE_FLAG_BEHAVIOR_CONTROLLED); // Calling this before copying prevents redundant LAYOUT_CHANGED. final int layoutInDisplayCutoutModeFromCaller = adjustLayoutInDisplayCutoutMode(attrs); final int changes = mWindowAttributes.copyFrom(attrs); if ((changes & WindowManager.LayoutParams.TRANSLUCENT_FLAGS_CHANGED) != 0) { // Recompute system ui visibility. Loading @@ -2003,6 +2008,9 @@ public final class ViewRootImpl implements ViewParent, mWindowAttributes.packageName = mBasePackageName; } // Restore the layoutInDisplayCutoutMode of the caller; attrs.layoutInDisplayCutoutMode = layoutInDisplayCutoutModeFromCaller; // Restore preserved flags. mWindowAttributes.systemUiVisibility = systemUiVisibility; mWindowAttributes.subtreeSystemUiVisibility = subtreeSystemUiVisibility; Loading Loading @@ -2046,6 +2054,19 @@ public final class ViewRootImpl implements ViewParent, } } private int adjustLayoutInDisplayCutoutMode(WindowManager.LayoutParams attrs) { final int originalMode = attrs.layoutInDisplayCutoutMode; if ((attrs.privateFlags & PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED) != 0 && attrs.isFullscreen() && attrs.getFitInsetsTypes() == 0 && attrs.getFitInsetsSides() == 0) { if (originalMode != LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS) { attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; } } return originalMode; } void handleAppVisibility(boolean visible) { if (Trace.isTagEnabled(Trace.TRACE_TAG_VIEW)) { Trace.instant(Trace.TRACE_TAG_VIEW, TextUtils.formatSimple( Loading
core/java/com/android/internal/policy/PhoneWindow.java +0 −3 Original line number Diff line number Diff line Loading @@ -2486,9 +2486,6 @@ public class PhoneWindow extends Window implements MenuBuilder.Callback { setFlags(FLAG_LAYOUT_IN_SCREEN|FLAG_LAYOUT_INSET_DECOR, flagsToUpdate); params.setFitInsetsSides(0); params.setFitInsetsTypes(0); if (mEdgeToEdgeEnforced) { params.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS; } } if (a.getBoolean(R.styleable.Window_windowNoTitle, false)) { Loading
core/res/res/values/attrs.xml +9 −8 Original line number Diff line number Diff line Loading @@ -2300,7 +2300,7 @@ ensure that the status bar has enough contrast with the contents of this app, and set an appropriate effective bar background accordingly. See: {@link android.R.attr#enforceStatusBarContrast} <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading @@ -2320,7 +2320,7 @@ ensure that the navigation bar has enough contrast with the contents of this app, and set an appropriate effective bar background accordingly. See: {@link android.R.attr#enforceNavigationBarContrast} <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading @@ -2335,7 +2335,7 @@ have been requested to be translucent with {@link android.R.attr#windowTranslucentNavigation}. Corresponds to {@link android.view.Window#setNavigationBarDividerColor(int)}. <p>If the app targets <p>If the window belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, this attribute is ignored. @deprecated Draw proper background behind Loading Loading @@ -2427,7 +2427,9 @@ <!-- Controls how the window is laid out if there is a {@code DisplayCutout}. <p> Defaults to {@code default}. Defaults to {@code default}. But if the window fills the screen, and it belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above, the behavior will be the same as specifying {@code always} regardless. <p> See also {@link android.view.WindowManager.LayoutParams#layoutInDisplayCutoutMode Loading Loading @@ -2524,8 +2526,8 @@ <!-- Flag indicating whether this window would opt-out the edge-to-edge enforcement. <p>If this is false, the edge-to-edge enforcement will be applied to the window if its app targets <p>If this is false, the edge-to-edge enforcement will be applied to the window if it belongs to an app targeting {@link android.os.Build.VERSION_CODES#VANILLA_ICE_CREAM VANILLA_ICE_CREAM} or above. The affected behaviors are: <ul> Loading @@ -2533,9 +2535,8 @@ through the {@link android.view.WindowInsets} to the content view, as if calling {@link android.view.Window#setDecorFitsSystemWindows(boolean)} with false. <li>{@link android.view.WindowManager.LayoutParams#layoutInDisplayCutoutMode} of the non-floating windows will be set to {@link the fill-screen windows will behave as specifying {@link android.view.WindowManager.LayoutParams#LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS}. Changing it to other values will cause {@link lang.IllegalArgumentException}. <li>The framework will set {@link android.R.attr#statusBarColor}, {@link android.R.attr#navigationBarColor}, and {@link android.R.attr#navigationBarDividerColor} to transparent. Loading
core/tests/coretests/src/com/android/internal/policy/PhoneWindowTest.java +2 −9 Original line number Diff line number Diff line Loading @@ -20,7 +20,6 @@ import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_M import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT; import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER; import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY; import static android.view.flags.Flags.FLAG_TOOLKIT_SET_FRAME_RATE_READ_ONLY; Loading Loading @@ -82,15 +81,9 @@ public final class PhoneWindowTest { createPhoneWindowWithTheme(R.style.LayoutInDisplayCutoutModeUnset); installDecor(); if ((mPhoneWindow.getAttributes().privateFlags & PRIVATE_FLAG_EDGE_TO_EDGE_ENFORCED) != 0 && !mPhoneWindow.isFloating()) { assertThat(mPhoneWindow.getAttributes().layoutInDisplayCutoutMode, is(LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS)); } else { assertThat(mPhoneWindow.getAttributes().layoutInDisplayCutoutMode, is(LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT)); } } @Test public void layoutInDisplayCutoutMode_default() throws Exception { Loading