Window Manager Flag Migration (7/n)
Introduce new APIs in Window/WindowManager.LayoutParams for developers
to decide which types of insets at which side a window should avoid:
setFitWindowInsetsTypes(@InsetsType int types)
setFitWindowInsetsSides(@InsetsSide int sides)
setFitIgnoreVisibility(boolean ignore)
The existing logic in DisplayPolicy.layoutWindowLw uses combinations of
window types, window flags, and system UI flags to decide what frames a
window should have, which is very complex, difficult to maintain, and
should be replaced with the new APIs.
Bug: 118118435
Test: atest InsetsSourceProviderTest InsetsStateControllerTest
InsetsPolicyTest WindowStateTests CommandQueueTest
RegisterStatusBarResultTest InsetsFlagsTest
LightBarControllerTest RegisterStatusBarResultTest
ViewRootImplTest DisplayPolicyLayoutTests
DisplayPolicyInsetsTests DisplayPolicyTests
TaskSnapshotSurfaceTest
Change-Id: I06ddc9d0d2887ba4ded7bb8adbf9c9c0da4bf7b4
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index 8435a82..cb110c3 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -4949,6 +4949,7 @@
mBootMsgDialog.getWindow().setDimAmount(1);
WindowManager.LayoutParams lp = mBootMsgDialog.getWindow().getAttributes();
lp.screenOrientation = ActivityInfo.SCREEN_ORIENTATION_NOSENSOR;
+ lp.setFitWindowInsetsTypes(0 /* types */);
mBootMsgDialog.getWindow().setAttributes(lp);
mBootMsgDialog.setCancelable(false);
mBootMsgDialog.show();
diff --git a/services/core/java/com/android/server/wm/DisplayPolicy.java b/services/core/java/com/android/server/wm/DisplayPolicy.java
index 2283041..667e713 100644
--- a/services/core/java/com/android/server/wm/DisplayPolicy.java
+++ b/services/core/java/com/android/server/wm/DisplayPolicy.java
@@ -33,6 +33,7 @@
import static android.view.InsetsState.ITYPE_STATUS_BAR;
import static android.view.InsetsState.ITYPE_TOP_GESTURES;
import static android.view.InsetsState.ITYPE_TOP_TAPPABLE_ELEMENT;
+import static android.view.View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
import static android.view.View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
import static android.view.ViewRootImpl.NEW_INSETS_MODE_FULL;
@@ -49,7 +50,6 @@
import static android.view.WindowManager.LayoutParams.FLAG_FULLSCREEN;
import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_ATTACHED_IN_DECOR;
import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_OVERSCAN;
import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS;
import static android.view.WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
@@ -63,6 +63,7 @@
import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_STATUS_BAR_VISIBLE_TRANSPARENT;
import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_IS_SCREEN_DECOR;
import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_ONLY_DRAW_BOTTOM_BAR_BACKGROUND;
import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING;
import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
@@ -149,13 +150,17 @@
import android.view.InputEvent;
import android.view.InputEventReceiver;
import android.view.InsetsFlags;
+import android.view.InsetsState;
import android.view.InsetsState.InternalInsetsType;
import android.view.MotionEvent;
import android.view.PointerIcon;
import android.view.Surface;
import android.view.View;
import android.view.ViewRootImpl;
-import android.view.WindowInsets;
+import android.view.WindowInsets.Side;
+import android.view.WindowInsets.Side.InsetsSide;
+import android.view.WindowInsets.Type;
+import android.view.WindowInsets.Type.InsetsType;
import android.view.WindowInsetsController.Appearance;
import android.view.WindowManager;
import android.view.WindowManager.LayoutParams;
@@ -337,6 +342,7 @@
private int mLastAppearance;
private int mLastFullscreenAppearance;
private int mLastDockedAppearance;
+ private int mLastBehavior;
private final Rect mNonDockedStackBounds = new Rect();
private final Rect mDockedStackBounds = new Rect();
private final Rect mLastNonDockedStackBounds = new Rect();
@@ -353,6 +359,7 @@
private static final Rect sTmpRect = new Rect();
private static final Rect sTmpNavFrame = new Rect();
private static final Rect sTmpLastParentFrame = new Rect();
+ private static final int[] sTmpTypesAndSides = new int[2];
private WindowState mTopFullscreenOpaqueWindowState;
private WindowState mTopFullscreenOpaqueOrDimmingWindowState;
@@ -1228,7 +1235,8 @@
final boolean screenDecor = (pfl & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0;
if (layoutInScreenAndInsetDecor && !screenDecor) {
- if ((sysUiVis & SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0) {
+ if ((sysUiVis & SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0
+ || (attrs.getFitWindowInsetsTypes() & Type.navigationBars()) == 0) {
outFrame.set(displayFrames.mUnrestricted);
} else {
outFrame.set(displayFrames.mRestricted);
@@ -1281,11 +1289,27 @@
}
}
+ private static void getImpliedTypesAndSidesToFit(LayoutParams attrs, int[] typesAndSides) {
+ typesAndSides[0] = attrs.getFitWindowInsetsTypes();
+ typesAndSides[1] = attrs.getFitWindowInsetsSides();
+ final boolean forceDrawsBarBackgrounds =
+ (attrs.privateFlags & PRIVATE_FLAG_FORCE_DRAW_BAR_BACKGROUNDS) != 0
+ && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT;
+ if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0 || forceDrawsBarBackgrounds) {
+ if ((attrs.privateFlags & PRIVATE_FLAG_ONLY_DRAW_BOTTOM_BAR_BACKGROUND) != 0) {
+ typesAndSides[1] &= ~Side.BOTTOM;
+ } else {
+ typesAndSides[0] &= ~Type.systemBars();
+ }
+ }
+ }
+
+ // TODO(b/118118435): remove after migration
private static int getImpliedSysUiFlagsForLayout(LayoutParams attrs) {
int impliedFlags = 0;
final boolean forceWindowDrawsBarBackgrounds =
(attrs.privateFlags & PRIVATE_FLAG_FORCE_DRAW_BAR_BACKGROUNDS) != 0
- && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT;
+ && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT;
if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0
|| forceWindowDrawsBarBackgrounds) {
impliedFlags |= SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
@@ -1300,6 +1324,13 @@
synchronized (mLock) {
mForceClearedSystemUiFlags &= ~View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
mDisplayContent.reevaluateStatusBarVisibility();
+ if (ViewRootImpl.sNewInsetsMode == NEW_INSETS_MODE_FULL && mNavigationBar != null) {
+ final InsetsControlTarget target =
+ mNavigationBar.getControllableInsetProvider().getControlTarget();
+ if (target != null) {
+ target.showInsets(Type.navigationBars(), false /* fromIme */);
+ }
+ }
}
}
};
@@ -1376,11 +1407,18 @@
// For purposes of putting out fake window up to steal focus, we will
// drive nav being hidden only by whether it is requested.
final int sysui = mLastSystemUiFlags;
- boolean navVisible = (sysui & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0;
+ final int behavior = mLastBehavior;
+ boolean navVisible = ViewRootImpl.sNewInsetsMode != ViewRootImpl.NEW_INSETS_MODE_FULL
+ ? (sysui & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0
+ : mNavigationBar != null && mNavigationBar.getControllableInsetProvider() != null
+ && mNavigationBar.getControllableInsetProvider().isClientVisible()
+ && !mDisplayContent.getInsetsPolicy().isTransient(ITYPE_NAVIGATION_BAR);
boolean navTranslucent = (sysui
& (View.NAVIGATION_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSPARENT)) != 0;
- boolean immersive = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0;
- boolean immersiveSticky = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
+ boolean immersive = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0
+ || (behavior & BEHAVIOR_SHOW_BARS_BY_SWIPE) != 0;
+ boolean immersiveSticky = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0
+ || (behavior & BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE) != 0;
boolean navAllowedHidden = immersive || immersiveSticky;
navTranslucent &= !immersiveSticky; // transient trumps translucent
boolean isKeyguardShowing = isStatusBarKeyguard()
@@ -1464,6 +1502,9 @@
displayFrames.mUnrestricted /* stableFrame */);
w.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
w.computeFrameLw();
+ if (w.getControllableInsetProvider() != null) {
+ w.getControllableInsetProvider().updateSourceFrame();
+ }
final Rect frame = w.getFrameLw();
if (frame.left <= 0 && frame.top <= 0) {
@@ -1526,6 +1567,11 @@
// Let the status bar determine its size.
mStatusBar.computeFrameLw();
+ // Update the source frame to provide insets to other windows during layout.
+ if (mStatusBar.getControllableInsetProvider() != null) {
+ mStatusBar.getControllableInsetProvider().updateSourceFrame();
+ }
+
// For layout, the status bar is always at the top with our fixed height.
displayFrames.mStable.top = displayFrames.mUnrestricted.top
+ mStatusBarHeightForRotation[displayFrames.mRotation];
@@ -1540,7 +1586,8 @@
sTmpRect.bottom = displayFrames.mStable.top; // Use collapsed status bar size
mStatusBarController.setContentFrame(sTmpRect);
- boolean statusBarTransient = (sysui & View.STATUS_BAR_TRANSIENT) != 0;
+ boolean statusBarTransient = (sysui & View.STATUS_BAR_TRANSIENT) != 0
+ || mDisplayContent.getInsetsPolicy().isTransient(ITYPE_STATUS_BAR);
boolean statusBarTranslucent = (sysui
& (View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT)) != 0;
@@ -1676,6 +1723,9 @@
navigationFrame /* stableFrame */);
mNavigationBar.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
mNavigationBar.computeFrameLw();
+ if (mNavigationBar.getControllableInsetProvider() != null) {
+ mNavigationBar.getControllableInsetProvider().updateSourceFrame();
+ }
mNavigationBarController.setContentFrame(mNavigationBar.getContentFrameLw());
if (DEBUG_LAYOUT) Slog.i(TAG, "mNavigationBar frame: " + navigationFrame);
@@ -1811,19 +1861,44 @@
final int adjust = sim & SOFT_INPUT_MASK_ADJUST;
- final boolean requestedFullscreen = (fl & FLAG_FULLSCREEN) != 0
- || (requestedSysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
-
final boolean layoutInScreen = (fl & FLAG_LAYOUT_IN_SCREEN) == FLAG_LAYOUT_IN_SCREEN;
final boolean layoutInsetDecor = (fl & FLAG_LAYOUT_INSET_DECOR) == FLAG_LAYOUT_INSET_DECOR;
sf.set(displayFrames.mStable);
- if (type == TYPE_INPUT_METHOD) {
+ if (ViewRootImpl.sNewInsetsMode == NEW_INSETS_MODE_FULL) {
+ getImpliedTypesAndSidesToFit(attrs, sTmpTypesAndSides);
+ final @InsetsType int typesToFit = sTmpTypesAndSides[0];
+ final @InsetsSide int sidesToFit = sTmpTypesAndSides[1];
+ final ArraySet<Integer> types = InsetsState.toInternalType(typesToFit);
+ final Rect dfu = displayFrames.mUnrestricted;
+ Insets insets = Insets.of(0, 0, 0, 0);
+ for (int i = types.size() - 1; i >= 0; i--) {
+ insets = Insets.max(insets, mDisplayContent.getInsetsStateController()
+ .getInsetsForDispatch(win).getSource(types.valueAt(i))
+ .calculateInsets(dfu, attrs.getFitIgnoreVisibility()));
+ }
+ final int left = (sidesToFit & Side.LEFT) != 0 ? insets.left : 0;
+ final int top = (sidesToFit & Side.TOP) != 0 ? insets.top : 0;
+ final int right = (sidesToFit & Side.RIGHT) != 0 ? insets.right : 0;
+ final int bottom = (sidesToFit & Side.BOTTOM) != 0 ? insets.bottom : 0;
+ df.set(left, top, dfu.right - right, dfu.bottom - bottom);
+ if (attached == null) {
+ pf.set(df);
+ vf.set(adjust != SOFT_INPUT_ADJUST_NOTHING
+ ? displayFrames.mCurrent : displayFrames.mDock);
+ } else {
+ pf.set((fl & FLAG_LAYOUT_IN_SCREEN) == 0 ? attached.getFrameLw() : df);
+ vf.set(attached.getVisibleFrameLw());
+ }
+ cf.set(adjust != SOFT_INPUT_ADJUST_RESIZE
+ ? displayFrames.mDock : displayFrames.mContent);
+ dcf.set(displayFrames.mSystem);
+ } else if (type == TYPE_INPUT_METHOD) {
vf.set(displayFrames.mDock);
cf.set(displayFrames.mDock);
df.set(displayFrames.mDock);
- windowFrames.mParentFrame.set(displayFrames.mDock);
+ pf.set(displayFrames.mDock);
// IM dock windows layout below the nav bar...
pf.bottom = df.bottom = displayFrames.mUnrestricted.bottom;
// ...with content insets above the nav bar
@@ -1989,7 +2064,7 @@
}
}
} else if (layoutInScreen || (sysUiFl
- & (View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
+ & (SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
| SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION)) != 0) {
if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
+ "): IN_SCREEN");
@@ -2039,7 +2114,7 @@
cf.set(displayFrames.mUnrestricted);
df.set(displayFrames.mUnrestricted);
pf.set(displayFrames.mUnrestricted);
- } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN) != 0) {
+ } else if ((sysUiFl & SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN) != 0) {
df.set(displayFrames.mRestricted);
pf.set(displayFrames.mRestricted);
@@ -2111,8 +2186,12 @@
final int cutoutMode = attrs.layoutInDisplayCutoutMode;
final boolean attachedInParent = attached != null && !layoutInScreen;
+ final boolean requestedFullscreen = (fl & FLAG_FULLSCREEN) != 0
+ || (requestedSysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0
+ || !win.getClientInsetsState().getSource(ITYPE_STATUS_BAR).isVisible();
final boolean requestedHideNavigation =
- (requestedSysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0;
+ (requestedSysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0
+ || !win.getClientInsetsState().getSource(ITYPE_NAVIGATION_BAR).isVisible();
// TYPE_BASE_APPLICATION windows are never considered floating here because they don't get
// cropped / shifted to the displayFrame in WindowState.
@@ -2195,6 +2274,9 @@
}
win.computeFrameLw();
+ if (win.getControllableInsetProvider() != null) {
+ win.getControllableInsetProvider().updateSourceFrame();
+ }
// Dock windows carve out the bottom of the screen, so normal windows
// can't appear underneath them.
if (type == TYPE_INPUT_METHOD && win.isVisibleLw()
@@ -2985,7 +3067,7 @@
mDisplayContent.getInsetsPolicy().showTransient(IntArray.wrap(
new int[]{ITYPE_STATUS_BAR, ITYPE_NAVIGATION_BAR}));
} else {
- controlTarget.showInsets(WindowInsets.Type.systemBars(), false);
+ controlTarget.showInsets(Type.systemBars(), false);
}
} else {
boolean sb = mStatusBarController.checkShowTransientBarLw();
@@ -3109,6 +3191,7 @@
&& mLastAppearance == appearance
&& mLastFullscreenAppearance == fullscreenAppearance
&& mLastDockedAppearance == dockedAppearance
+ && mLastBehavior == behavior
&& mLastFocusIsFullscreen == isFullscreen
&& mLastFocusIsImmersive == isImmersive
&& mFocusedApp == win.getAppToken()
@@ -3125,6 +3208,7 @@
mLastAppearance = appearance;
mLastFullscreenAppearance = fullscreenAppearance;
mLastDockedAppearance = dockedAppearance;
+ mLastBehavior = behavior;
mLastFocusIsFullscreen = isFullscreen;
mLastFocusIsImmersive = isImmersive;
mFocusedApp = win.getAppToken();
diff --git a/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java b/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
index 82ac6b8..bef1442 100644
--- a/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
+++ b/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
@@ -46,6 +46,7 @@
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewTreeObserver;
+import android.view.WindowInsets.Type;
import android.view.WindowManager;
import android.view.animation.Animation;
import android.view.animation.AnimationUtils;
@@ -189,6 +190,7 @@
| WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED
| WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
PixelFormat.TRANSLUCENT);
+ lp.setFitWindowInsetsTypes(lp.getFitWindowInsetsTypes() & ~Type.statusBars());
lp.privateFlags |= WindowManager.LayoutParams.SYSTEM_FLAG_SHOW_FOR_ALL_USERS;
lp.setTitle("ImmersiveModeConfirmation");
lp.windowAnimations = com.android.internal.R.style.Animation_ImmersiveModeConfirmation;
diff --git a/services/core/java/com/android/server/wm/InsetsPolicy.java b/services/core/java/com/android/server/wm/InsetsPolicy.java
index d50bcc4..af84836 100644
--- a/services/core/java/com/android/server/wm/InsetsPolicy.java
+++ b/services/core/java/com/android/server/wm/InsetsPolicy.java
@@ -45,7 +45,7 @@
private final IntArray mShowingTransientTypes = new IntArray();
private WindowState mFocusedWin;
- private BarWindow mTopBar = new BarWindow(StatusBarManager.WINDOW_STATUS_BAR);
+ private BarWindow mStatusBar = new BarWindow(StatusBarManager.WINDOW_STATUS_BAR);
private BarWindow mNavBar = new BarWindow(StatusBarManager.WINDOW_NAVIGATION_BAR);
InsetsPolicy(InsetsStateController stateController, DisplayContent displayContent) {
@@ -57,15 +57,15 @@
/** Updates the target which can control system bars. */
void updateBarControlTarget(@Nullable WindowState focusedWin) {
mFocusedWin = focusedWin;
- mStateController.onBarControlTargetChanged(getTopControlTarget(focusedWin),
- getFakeTopControlTarget(focusedWin),
+ mStateController.onBarControlTargetChanged(getStatusControlTarget(focusedWin),
+ getFakeStatusControlTarget(focusedWin),
getNavControlTarget(focusedWin),
getFakeNavControlTarget(focusedWin));
if (ViewRootImpl.sNewInsetsMode != ViewRootImpl.NEW_INSETS_MODE_FULL) {
return;
}
- mTopBar.setVisible(focusedWin == null
- || focusedWin != getTopControlTarget(focusedWin)
+ mStatusBar.setVisible(focusedWin == null
+ || focusedWin != getStatusControlTarget(focusedWin)
|| focusedWin.getClientInsetsState().getSource(ITYPE_STATUS_BAR).isVisible());
mNavBar.setVisible(focusedWin == null
|| focusedWin != getNavControlTarget(focusedWin)
@@ -110,6 +110,10 @@
mStateController.notifyInsetsChanged();
}
+ boolean isTransient(@InternalInsetsType int type) {
+ return mShowingTransientTypes.indexOf(type) != -1;
+ }
+
/**
* @see InsetsStateController#getInsetsForDispatch
*/
@@ -130,8 +134,8 @@
if (ViewRootImpl.sNewInsetsMode != ViewRootImpl.NEW_INSETS_MODE_FULL) {
return;
}
- if (windowState == getTopControlTarget(mFocusedWin)) {
- mTopBar.setVisible(state.getSource(ITYPE_STATUS_BAR).isVisible());
+ if (windowState == getStatusControlTarget(mFocusedWin)) {
+ mStatusBar.setVisible(state.getSource(ITYPE_STATUS_BAR).isVisible());
}
if (windowState == getNavControlTarget(mFocusedWin)) {
mNavBar.setVisible(state.getSource(ITYPE_NAVIGATION_BAR).isVisible());
@@ -164,7 +168,8 @@
}
}
- private @Nullable InsetsControlTarget getFakeTopControlTarget(@Nullable WindowState focused) {
+ private @Nullable InsetsControlTarget getFakeStatusControlTarget(
+ @Nullable WindowState focused) {
if (mShowingTransientTypes.indexOf(ITYPE_STATUS_BAR) != -1) {
return focused;
}
@@ -178,7 +183,7 @@
return null;
}
- private @Nullable InsetsControlTarget getTopControlTarget(@Nullable WindowState focusedWin) {
+ private @Nullable InsetsControlTarget getStatusControlTarget(@Nullable WindowState focusedWin) {
if (mShowingTransientTypes.indexOf(ITYPE_STATUS_BAR) != -1) {
return mTransientControlTarget;
}
diff --git a/services/core/java/com/android/server/wm/InsetsSourceProvider.java b/services/core/java/com/android/server/wm/InsetsSourceProvider.java
index 69e8fdc..0821873 100644
--- a/services/core/java/com/android/server/wm/InsetsSourceProvider.java
+++ b/services/core/java/com/android/server/wm/InsetsSourceProvider.java
@@ -141,9 +141,10 @@
}
/**
- * Called when a layout pass has occurred.
+ * The source frame can affect the layout of other windows, so this should be called once the
+ * window gets laid out.
*/
- void onPostLayout() {
+ void updateSourceFrame() {
if (mWin == null) {
return;
}
@@ -155,6 +156,17 @@
mTmpRect.inset(mWin.mGivenContentInsets);
}
mSource.setFrame(mTmpRect);
+ }
+
+ /**
+ * Called when a layout pass has occurred.
+ */
+ void onPostLayout() {
+ if (mWin == null) {
+ return;
+ }
+
+ updateSourceFrame();
if (mControl != null) {
final Rect frame = mWin.getWindowFrames().mFrame;
if (mControl.setSurfacePosition(frame.left, frame.top)) {
diff --git a/services/core/java/com/android/server/wm/TaskSnapshotController.java b/services/core/java/com/android/server/wm/TaskSnapshotController.java
index c1a36c4..f5b46f4 100644
--- a/services/core/java/com/android/server/wm/TaskSnapshotController.java
+++ b/services/core/java/com/android/server/wm/TaskSnapshotController.java
@@ -403,7 +403,7 @@
final LayoutParams attrs = mainWindow.getAttrs();
final SystemBarBackgroundPainter decorPainter = new SystemBarBackgroundPainter(attrs.flags,
attrs.privateFlags, attrs.systemUiVisibility, task.getTaskDescription(),
- mFullSnapshotScale);
+ mFullSnapshotScale, mainWindow.getClientInsetsState());
final int width = (int) (task.getBounds().width() * mFullSnapshotScale);
final int height = (int) (task.getBounds().height() * mFullSnapshotScale);
diff --git a/services/core/java/com/android/server/wm/TaskSnapshotSurface.java b/services/core/java/com/android/server/wm/TaskSnapshotSurface.java
index b3750e9..1484d6a 100644
--- a/services/core/java/com/android/server/wm/TaskSnapshotSurface.java
+++ b/services/core/java/com/android/server/wm/TaskSnapshotSurface.java
@@ -71,6 +71,7 @@
import android.view.SurfaceSession;
import android.view.View;
import android.view.ViewGroup.LayoutParams;
+import android.view.ViewRootImpl;
import android.view.WindowManager;
import android.view.WindowManagerGlobal;
@@ -154,6 +155,7 @@
final MergedConfiguration tmpMergedConfiguration = new MergedConfiguration();
final TaskDescription taskDescription = new TaskDescription();
taskDescription.setBackgroundColor(WHITE);
+ final WindowState topFullscreenWindow;
final int sysUiVis;
final int windowFlags;
final int windowPrivateFlags;
@@ -173,7 +175,7 @@
+ task);
return null;
}
- final WindowState topFullscreenWindow = topFullscreenActivity.getTopFullscreenWindow();
+ topFullscreenWindow = topFullscreenActivity.getTopFullscreenWindow();
if (mainWindow == null || topFullscreenWindow == null) {
Slog.w(TAG, "TaskSnapshotSurface.create: Failed to find main window for activity="
+ activity);
@@ -220,7 +222,7 @@
final TaskSnapshotSurface snapshotSurface = new TaskSnapshotSurface(service, window,
surfaceControl, snapshot, layoutParams.getTitle(), taskDescription, sysUiVis,
windowFlags, windowPrivateFlags, taskBounds,
- currentOrientation);
+ currentOrientation, topFullscreenWindow.getClientInsetsState());
window.setOuter(snapshotSurface);
try {
session.relayout(window, window.mSeq, layoutParams, -1, -1, View.VISIBLE, 0, -1,
@@ -238,7 +240,7 @@
TaskSnapshotSurface(WindowManagerService service, Window window, SurfaceControl surfaceControl,
TaskSnapshot snapshot, CharSequence title, TaskDescription taskDescription,
int sysUiVis, int windowFlags, int windowPrivateFlags, Rect taskBounds,
- int currentOrientation) {
+ int currentOrientation, InsetsState insetsState) {
mService = service;
mSurface = service.mSurfaceFactory.get();
mHandler = new Handler(mService.mH.getLooper());
@@ -251,7 +253,7 @@
mBackgroundPaint.setColor(backgroundColor != 0 ? backgroundColor : WHITE);
mTaskBounds = taskBounds;
mSystemBarBackgroundPainter = new SystemBarBackgroundPainter(windowFlags,
- windowPrivateFlags, sysUiVis, taskDescription, 1f);
+ windowPrivateFlags, sysUiVis, taskDescription, 1f, insetsState);
mStatusBarColor = taskDescription.getStatusBarColor();
mOrientationOnCreation = currentOrientation;
mTransaction = mService.mTransactionFactory.get();
@@ -502,9 +504,10 @@
private final int mWindowPrivateFlags;
private final int mSysUiVis;
private final float mScale;
+ private final InsetsState mInsetsState;
SystemBarBackgroundPainter(int windowFlags, int windowPrivateFlags, int sysUiVis,
- TaskDescription taskDescription, float scale) {
+ TaskDescription taskDescription, float scale, InsetsState insetsState) {
mWindowFlags = windowFlags;
mWindowPrivateFlags = windowPrivateFlags;
mSysUiVis = sysUiVis;
@@ -524,6 +527,7 @@
&& context.getResources().getBoolean(R.bool.config_navBarNeedsScrim));
mStatusBarPaint.setColor(mStatusBarColor);
mNavigationBarPaint.setColor(mNavigationBarColor);
+ mInsetsState = insetsState;
}
void setInsets(Rect contentInsets, Rect stableInsets) {
@@ -534,8 +538,11 @@
int getStatusBarColorViewHeight() {
final boolean forceBarBackground =
(mWindowPrivateFlags & PRIVATE_FLAG_FORCE_DRAW_BAR_BACKGROUNDS) != 0;
- if (STATUS_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
- mSysUiVis, mStatusBarColor, mWindowFlags, forceBarBackground)) {
+ if (ViewRootImpl.sNewInsetsMode != ViewRootImpl.NEW_INSETS_MODE_FULL
+ ? STATUS_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
+ mSysUiVis, mStatusBarColor, mWindowFlags, forceBarBackground)
+ : STATUS_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
+ mInsetsState, mStatusBarColor, mWindowFlags, forceBarBackground)) {
return (int) (getColorViewTopInset(mStableInsets.top, mContentInsets.top) * mScale);
} else {
return 0;
@@ -545,8 +552,11 @@
private boolean isNavigationBarColorViewVisible() {
final boolean forceBarBackground =
(mWindowPrivateFlags & PRIVATE_FLAG_FORCE_DRAW_BAR_BACKGROUNDS) != 0;
- return NAVIGATION_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
- mSysUiVis, mNavigationBarColor, mWindowFlags, forceBarBackground);
+ return ViewRootImpl.sNewInsetsMode != ViewRootImpl.NEW_INSETS_MODE_FULL
+ ? NAVIGATION_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
+ mSysUiVis, mNavigationBarColor, mWindowFlags, forceBarBackground)
+ : NAVIGATION_BAR_COLOR_VIEW_ATTRIBUTES.isVisible(
+ mInsetsState, mNavigationBarColor, mWindowFlags, forceBarBackground);
}
void drawDecors(Canvas c, @Nullable Rect alreadyDrawnFrame) {
diff --git a/services/core/java/com/android/server/wm/WindowFrames.java b/services/core/java/com/android/server/wm/WindowFrames.java
index 0490bac..97186b4 100644
--- a/services/core/java/com/android/server/wm/WindowFrames.java
+++ b/services/core/java/com/android/server/wm/WindowFrames.java
@@ -207,6 +207,7 @@
return (mLastFrame.width() != mFrame.width()) || (mLastFrame.height() != mFrame.height());
}
+ // TODO(b/118118435): Remove after migration.
/**
* Calculate the insets for the type
* {@link android.view.WindowManager.LayoutParams#TYPE_DOCK_DIVIDER}