From 791332f4d5f856402dc7be93667cd27405640985 Mon Sep 17 00:00:00 2001 From: Riddle Hsu Date: Tue, 14 Jul 2020 17:31:32 +0800 Subject: [PATCH] Add debounce for hide animation of fixed rotation recents If navigation bar is pressed, it may trigger recents animation with fixed rotation, and if the touch is released immediately, the show/hide animation will apply in a short time that looks blinking. Bug: 160238664 Test: With 2 button navigation, launch a landscape activity and press home key. The status bar should fade out and fade in smoothly. Change-Id: I2e92e614c95b30a1e5de53e28b4140a430015414 --- .../com/android/server/wm/DisplayContent.java | 36 ++++++++++++++++--- 1 file changed, 32 insertions(+), 4 deletions(-) diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java index 127e10a6966bd..f2078a02a52bc 100644 --- a/services/core/java/com/android/server/wm/DisplayContent.java +++ b/services/core/java/com/android/server/wm/DisplayContent.java @@ -490,6 +490,8 @@ class DisplayContent extends RootDisplayArea implements WindowManagerPolicy.Disp */ private ActivityRecord mFixedRotationLaunchingApp; + /** The delay to avoid toggling the animation quickly. */ + private static final long FIXED_ROTATION_HIDE_ANIMATION_DEBOUNCE_DELAY_MS = 250; private FixedRotationAnimationController mFixedRotationAnimationController; final FixedRotationTransitionListener mFixedRotationTransitionListener = @@ -1524,10 +1526,10 @@ class DisplayContent extends RootDisplayArea implements WindowManagerPolicy.Disp void setFixedRotationLaunchingAppUnchecked(@Nullable ActivityRecord r, int rotation) { if (mFixedRotationLaunchingApp == null && r != null) { mWmService.mDisplayNotificationController.dispatchFixedRotationStarted(this, rotation); - if (mFixedRotationAnimationController == null) { - mFixedRotationAnimationController = new FixedRotationAnimationController(this); - mFixedRotationAnimationController.hide(); - } + startFixedRotationAnimation( + // Delay the hide animation to avoid blinking by clicking navigation bar that + // may toggle fixed rotation in a short time. + r == mFixedRotationTransitionListener.mAnimatingRecents /* shouldDebounce */); } else if (mFixedRotationLaunchingApp != null && r == null) { mWmService.mDisplayNotificationController.dispatchFixedRotationFinished(this); finishFixedRotationAnimationIfPossible(); @@ -1625,6 +1627,32 @@ class DisplayContent extends RootDisplayArea implements WindowManagerPolicy.Disp } } + /** + * Starts the hide animation for the windows which will be rotated seamlessly. + * + * @return {@code true} if the animation is executed right now. + */ + private boolean startFixedRotationAnimation(boolean shouldDebounce) { + if (shouldDebounce) { + mWmService.mH.postDelayed(() -> { + synchronized (mWmService.mGlobalLock) { + if (mFixedRotationLaunchingApp != null + && startFixedRotationAnimation(false /* shouldDebounce */)) { + // Apply the transaction so the animation leash can take effect immediately. + getPendingTransaction().apply(); + } + } + }, FIXED_ROTATION_HIDE_ANIMATION_DEBOUNCE_DELAY_MS); + return false; + } + if (mFixedRotationAnimationController == null) { + mFixedRotationAnimationController = new FixedRotationAnimationController(this); + mFixedRotationAnimationController.hide(); + return true; + } + return false; + } + /** Re-show the previously hidden windows if all seamless rotated windows are done. */ void finishFixedRotationAnimationIfPossible() { final FixedRotationAnimationController controller = mFixedRotationAnimationController;