diff --git a/services/core/java/com/android/server/input/GestureMonitorSpyWindow.java b/services/core/java/com/android/server/input/GestureMonitorSpyWindow.java index e222c644da9e9..d238dae634adf 100644 --- a/services/core/java/com/android/server/input/GestureMonitorSpyWindow.java +++ b/services/core/java/com/android/server/input/GestureMonitorSpyWindow.java @@ -27,8 +27,6 @@ import android.view.InputWindowHandle; import android.view.SurfaceControl; import android.view.WindowManager; -import com.android.server.policy.WindowManagerPolicy; - /** * An internal implementation of an {@link InputMonitor} that uses a spy window. * @@ -69,9 +67,7 @@ class GestureMonitorSpyWindow { final SurfaceControl.Transaction t = new SurfaceControl.Transaction(); t.setInputWindowInfo(mInputSurface, mWindowHandle); - // Gesture monitor should be above handwriting event surface, hence setting it to - // WindowManagerPolicy.INPUT_DISPLAY_OVERLAY_LAYER + 1 - t.setLayer(mInputSurface, WindowManagerPolicy.INPUT_DISPLAY_OVERLAY_LAYER + 1); + t.setLayer(mInputSurface, Integer.MAX_VALUE); t.setPosition(mInputSurface, 0, 0); t.setCrop(mInputSurface, null /* crop to parent surface */); t.show(mInputSurface); diff --git a/services/core/java/com/android/server/inputmethod/HandwritingEventReceiverSurface.java b/services/core/java/com/android/server/inputmethod/HandwritingEventReceiverSurface.java index 5438faa8793e3..8180e66166d93 100644 --- a/services/core/java/com/android/server/inputmethod/HandwritingEventReceiverSurface.java +++ b/services/core/java/com/android/server/inputmethod/HandwritingEventReceiverSurface.java @@ -27,8 +27,6 @@ import android.view.InputWindowHandle; import android.view.SurfaceControl; import android.view.WindowManager; -import com.android.server.policy.WindowManagerPolicy; - final class HandwritingEventReceiverSurface { public static final String TAG = HandwritingEventReceiverSurface.class.getSimpleName(); @@ -38,8 +36,7 @@ final class HandwritingEventReceiverSurface { // is above gesture monitors, then edge-back and swipe-up gestures won't work when this surface // is intercepting. // TODO(b/217538817): Specify the ordering in WM by usage. - private static final int HANDWRITING_SURFACE_LAYER = - WindowManagerPolicy.INPUT_DISPLAY_OVERLAY_LAYER; + private static final int HANDWRITING_SURFACE_LAYER = Integer.MAX_VALUE - 1; private final InputWindowHandle mWindowHandle; private final InputChannel mClientChannel; diff --git a/services/core/java/com/android/server/policy/WindowManagerPolicy.java b/services/core/java/com/android/server/policy/WindowManagerPolicy.java index 89178139ffec2..7ca09ab5154f4 100644 --- a/services/core/java/com/android/server/policy/WindowManagerPolicy.java +++ b/services/core/java/com/android/server/policy/WindowManagerPolicy.java @@ -156,10 +156,6 @@ public interface WindowManagerPolicy extends WindowManagerPolicyConstants { int FINISH_LAYOUT_REDO_ANIM = 0x0008; /** Layer for the screen off animation */ int COLOR_FADE_LAYER = 0x40000001; - /** Layer for Input overlays for capturing inputs for gesture detection, etc. */ - int INPUT_DISPLAY_OVERLAY_LAYER = 0x7f000000; - /** Layer for Screen Decoration: The top most visible layer just below input overlay layers */ - int SCREEN_DECOR_DISPLAY_OVERLAY_LAYER = INPUT_DISPLAY_OVERLAY_LAYER - 1; /** * Register shortcuts for window manager to dispatch. diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java index 72b996c4662d1..79aef00750a12 100644 --- a/services/core/java/com/android/server/wm/DisplayContent.java +++ b/services/core/java/com/android/server/wm/DisplayContent.java @@ -3233,10 +3233,11 @@ class DisplayContent extends RootDisplayArea implements WindowManagerPolicy.Disp } public void setRotationAnimation(ScreenRotationAnimation screenRotationAnimation) { - if (mScreenRotationAnimation != null) { - mScreenRotationAnimation.kill(); - } + final ScreenRotationAnimation prev = mScreenRotationAnimation; mScreenRotationAnimation = screenRotationAnimation; + if (prev != null) { + prev.kill(); + } // Hide the windows which are not significant in rotation animation. So that the windows // don't need to block the unfreeze time. diff --git a/services/core/java/com/android/server/wm/InputManagerCallback.java b/services/core/java/com/android/server/wm/InputManagerCallback.java index b7ddbd070460c..33cdd2e98113d 100644 --- a/services/core/java/com/android/server/wm/InputManagerCallback.java +++ b/services/core/java/com/android/server/wm/InputManagerCallback.java @@ -265,7 +265,7 @@ final class InputManagerCallback implements InputManagerService.WindowManagerCal .setContainerLayer() .setName(name) .setCallsite("createSurfaceForGestureMonitor") - .setParent(dc.getOverlayLayer()) + .setParent(dc.getSurfaceControl()) .build(); } } diff --git a/services/core/java/com/android/server/wm/ScreenRotationAnimation.java b/services/core/java/com/android/server/wm/ScreenRotationAnimation.java index f80e732c8212a..f31a3cc9bcb3e 100644 --- a/services/core/java/com/android/server/wm/ScreenRotationAnimation.java +++ b/services/core/java/com/android/server/wm/ScreenRotationAnimation.java @@ -40,9 +40,11 @@ import android.graphics.Matrix; import android.graphics.Point; import android.graphics.Rect; import android.hardware.HardwareBuffer; +import android.os.IBinder; import android.os.Trace; import android.util.Slog; import android.util.proto.ProtoOutputStream; +import android.view.DisplayAddress; import android.view.DisplayInfo; import android.view.Surface; import android.view.Surface.OutOfResourcesException; @@ -165,23 +167,43 @@ class ScreenRotationAnimation { final SurfaceControl.Transaction t = mService.mTransactionFactory.get(); try { - SurfaceControl.LayerCaptureArgs.Builder builder = - new SurfaceControl.LayerCaptureArgs.Builder(displayContent.getSurfaceControl()) - .setCaptureSecureLayers(true) - .setAllowProtected(true) - .setSourceCrop(new Rect(0, 0, width, height)); - + final SurfaceControl.ScreenshotHardwareBuffer screenshotBuffer; if (isSizeChanged) { + final DisplayAddress address = displayInfo.address; + if (!(address instanceof DisplayAddress.Physical)) { + Slog.e(TAG, "Display does not have a physical address: " + displayId); + return; + } + final DisplayAddress.Physical physicalAddress = + (DisplayAddress.Physical) address; + final IBinder displayToken = SurfaceControl.getPhysicalDisplayToken( + physicalAddress.getPhysicalDisplayId()); + if (displayToken == null) { + Slog.e(TAG, "Display token is null."); + return; + } + // Temporarily not skip screenshot for the rounded corner overlays and screenshot + // the whole display to include the rounded corner overlays. + setSkipScreenshotForRoundedCornerOverlays(false, t); mRoundedCornerOverlay = displayContent.findRoundedCornerOverlays(); + final SurfaceControl.DisplayCaptureArgs captureArgs = + new SurfaceControl.DisplayCaptureArgs.Builder(displayToken) + .setSourceCrop(new Rect(0, 0, width, height)) + .setAllowProtected(true) + .setCaptureSecureLayers(true) + .build(); + screenshotBuffer = SurfaceControl.captureDisplay(captureArgs); } else { - // Exclude rounded corner overlay from screenshot buffer. Rounded - // corner overlay windows are un-rotated during rotation animation - // for a seamless transition. - builder.setExcludeLayers(displayContent.findRoundedCornerOverlays()); + SurfaceControl.LayerCaptureArgs captureArgs = + new SurfaceControl.LayerCaptureArgs.Builder( + displayContent.getSurfaceControl()) + .setCaptureSecureLayers(true) + .setAllowProtected(true) + .setSourceCrop(new Rect(0, 0, width, height)) + .build(); + screenshotBuffer = SurfaceControl.captureLayers(captureArgs); } - SurfaceControl.ScreenshotHardwareBuffer screenshotBuffer = - SurfaceControl.captureLayers(builder.build()); if (screenshotBuffer == null) { Slog.w(TAG, "Unable to take screenshot of display " + displayId); return; @@ -280,6 +302,21 @@ class ScreenRotationAnimation { t.apply(); } + void setSkipScreenshotForRoundedCornerOverlays( + boolean skipScreenshot, SurfaceControl.Transaction t) { + mDisplayContent.forAllWindows(w -> { + if (!w.mToken.mRoundedCornerOverlay || !w.isVisible() || !w.mWinAnimator.hasSurface()) { + return; + } + t.setSkipScreenshot(w.mWinAnimator.mSurfaceController.mSurfaceControl, skipScreenshot); + }, false); + if (!skipScreenshot) { + // Use sync apply to apply the change immediately, so that the next + // SC.captureDisplay can capture the screen decor layers. + t.apply(true /* sync */); + } + } + public void dumpDebug(ProtoOutputStream proto, long fieldId) { final long token = proto.start(fieldId); proto.write(STARTED, mStarted); @@ -488,10 +525,15 @@ class ScreenRotationAnimation { } mBackColorSurface = null; } + if (mRoundedCornerOverlay != null) { - for (SurfaceControl sc : mRoundedCornerOverlay) { - if (sc.isValid()) { - t.show(sc); + if (mDisplayContent.getRotationAnimation() == null + || mDisplayContent.getRotationAnimation() == this) { + setSkipScreenshotForRoundedCornerOverlays(true, t); + for (SurfaceControl sc : mRoundedCornerOverlay) { + if (sc.isValid()) { + t.show(sc); + } } } mRoundedCornerOverlay = null; diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java index 52af39ee64b31..902218621cd00 100644 --- a/services/core/java/com/android/server/wm/WindowManagerService.java +++ b/services/core/java/com/android/server/wm/WindowManagerService.java @@ -8215,7 +8215,7 @@ public class WindowManagerService extends IWindowManager.Stub .setContainerLayer() .setName("IME Handwriting Surface") .setCallsite("getHandwritingSurfaceForDisplay") - .setParent(dc.getOverlayLayer()) + .setParent(dc.getSurfaceControl()) .build(); } } diff --git a/services/core/java/com/android/server/wm/WindowToken.java b/services/core/java/com/android/server/wm/WindowToken.java index 18f60b1a9a20e..d2e56faa0914c 100644 --- a/services/core/java/com/android/server/wm/WindowToken.java +++ b/services/core/java/com/android/server/wm/WindowToken.java @@ -368,7 +368,7 @@ class WindowToken extends WindowContainer { super.assignRelativeLayer(t, mDisplayContent.getDefaultTaskDisplayArea().getSplitScreenDividerAnchor(), 1); } else if (mRoundedCornerOverlay) { - super.assignLayer(t, WindowManagerPolicy.SCREEN_DECOR_DISPLAY_OVERLAY_LAYER); + super.assignLayer(t, WindowManagerPolicy.COLOR_FADE_LAYER + 1); } else { super.assignLayer(t, layer); } @@ -378,7 +378,7 @@ class WindowToken extends WindowContainer { SurfaceControl.Builder makeSurface() { final SurfaceControl.Builder builder = super.makeSurface(); if (mRoundedCornerOverlay) { - builder.setParent(getDisplayContent().getOverlayLayer()); + builder.setParent(null); } return builder; }