From 46319004c1d5094dfcd108a591aa6dfb1318ab28 Mon Sep 17 00:00:00 2001 From: Winson Chung Date: Tue, 22 Jun 2021 14:01:28 -0700 Subject: [PATCH] Tweak live tile rotation handling - With ag/15023409, the system will screenshot and cancel the recents animation based on the hint provided by launcher when there is a global config change. As such, we can remove extra handling of the configuration change on the launcher side, and handle the cancel with the provided snapshot. To handle the snapshot, we need to hook into the gesture state recents animation callbacks (which actually are of the lifecycle of the animation and not just the gesture). Bug: 189843542 Test: With live-tile enabled, swipe up to overview and rotate Change-Id: If74f3fc5d47c327f9f5cca8f1f5d23b48cd3c954 --- .../android/quickstep/AbsSwipeUpHandler.java | 18 +++++++-- .../com/android/quickstep/GestureState.java | 17 +++++++++ .../quickstep/RecentsAnimationController.java | 16 ++++++++ .../android/quickstep/views/RecentsView.java | 37 +++++++++---------- 4 files changed, 66 insertions(+), 22 deletions(-) diff --git a/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java b/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java index 4d47ef15c1..7f38923671 100644 --- a/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java +++ b/quickstep/src/com/android/quickstep/AbsSwipeUpHandler.java @@ -42,6 +42,7 @@ import static com.android.quickstep.GestureState.GestureEndTarget.NEW_TASK; import static com.android.quickstep.GestureState.GestureEndTarget.RECENTS; import static com.android.quickstep.GestureState.STATE_END_TARGET_ANIMATION_FINISHED; import static com.android.quickstep.GestureState.STATE_END_TARGET_SET; +import static com.android.quickstep.GestureState.STATE_RECENTS_ANIMATION_CANCELED; import static com.android.quickstep.GestureState.STATE_RECENTS_SCROLLING_FINISHED; import static com.android.quickstep.MultiStateCallback.DEBUG_STATES; import static com.android.quickstep.util.NavigationModeFeatureFlag.LIVE_TILE; @@ -378,6 +379,17 @@ public abstract class AbsSwipeUpHandler, activity.runOnceOnStart(this::onLauncherStart); } + // Set up a entire animation lifecycle callback to notify the current recents view when + // the animation is canceled + mGestureState.runOnceAtState(STATE_RECENTS_ANIMATION_CANCELED, () -> { + ThumbnailData snapshot = mGestureState.getRecentsAnimationCanceledSnapshot(); + if (snapshot != null) { + RecentsModel.INSTANCE.get(mContext).onTaskSnapshotChanged( + mRecentsView.getRunningTaskId(), snapshot); + mRecentsView.onRecentsAnimationComplete(); + } + }); + setupRecentsViewUi(); linkRecentsViewScroll(); @@ -671,6 +683,9 @@ public abstract class AbsSwipeUpHandler, mRecentsAnimationController.setUseLauncherSystemBarFlags(swipeUpThresholdPassed || (quickswitchThresholdPassed && centermostTaskFlags != 0)); mRecentsAnimationController.setSplitScreenMinimized(swipeUpThresholdPassed); + // Provide a hint to WM the direction that we will be settling in case the animation + // needs to be canceled + mRecentsAnimationController.setWillFinishToHome(swipeUpThresholdPassed); if (swipeUpThresholdPassed) { mActivity.getSystemUiController().updateUiState(UI_STATE_FULLSCREEN_TASK, 0); @@ -1467,9 +1482,6 @@ public abstract class AbsSwipeUpHandler, final boolean refreshView = !LIVE_TILE.get() /* refreshView */; boolean finishTransitionPosted = false; if (mRecentsAnimationController != null) { - if (LIVE_TILE.get()) { - mRecentsAnimationController.getController().setWillFinishToHome(true); - } // Update the screenshot of the task if (mTaskSnapshot == null) { UI_HELPER_EXECUTOR.execute(() -> { diff --git a/quickstep/src/com/android/quickstep/GestureState.java b/quickstep/src/com/android/quickstep/GestureState.java index 6ad7f55a3a..a302a07bca 100644 --- a/quickstep/src/com/android/quickstep/GestureState.java +++ b/quickstep/src/com/android/quickstep/GestureState.java @@ -142,6 +142,8 @@ public class GestureState implements RecentsAnimationCallbacks.RecentsAnimationL private RemoteAnimationTargetCompat mLastAppearedTaskTarget; private Set mPreviouslyAppearedTaskIds = new HashSet<>(); private int mLastStartedTaskId = -1; + private RecentsAnimationController mRecentsAnimationController; + private ThumbnailData mRecentsAnimationCanceledSnapshot; /** The time when the swipe up gesture is triggered. */ private long mSwipeUpStartTimeMs; @@ -351,13 +353,20 @@ public class GestureState implements RecentsAnimationCallbacks.RecentsAnimationL @Override public void onRecentsAnimationStart(RecentsAnimationController controller, RecentsAnimationTargets targets) { + mRecentsAnimationController = controller; mStateCallback.setState(STATE_RECENTS_ANIMATION_STARTED); } @Override public void onRecentsAnimationCanceled(ThumbnailData thumbnailData) { + mRecentsAnimationCanceledSnapshot = thumbnailData; mStateCallback.setState(STATE_RECENTS_ANIMATION_CANCELED); mStateCallback.setState(STATE_RECENTS_ANIMATION_ENDED); + if (mRecentsAnimationCanceledSnapshot != null) { + // Clean up the screenshot to finalize the recents animation cancel + mRecentsAnimationController.cleanupScreenshot(); + mRecentsAnimationCanceledSnapshot = null; + } } @Override @@ -366,6 +375,14 @@ public class GestureState implements RecentsAnimationCallbacks.RecentsAnimationL mStateCallback.setState(STATE_RECENTS_ANIMATION_ENDED); } + /** + * Returns the canceled animation thumbnail data. This call only returns a value while + * STATE_RECENTS_ANIMATION_CANCELED state is being set. + */ + ThumbnailData getRecentsAnimationCanceledSnapshot() { + return mRecentsAnimationCanceledSnapshot; + } + void setSwipeUpStartTimeMs(long uptimeMs) { mSwipeUpStartTimeMs = uptimeMs; } diff --git a/quickstep/src/com/android/quickstep/RecentsAnimationController.java b/quickstep/src/com/android/quickstep/RecentsAnimationController.java index 0ebe13be8d..53b66752e2 100644 --- a/quickstep/src/com/android/quickstep/RecentsAnimationController.java +++ b/quickstep/src/com/android/quickstep/RecentsAnimationController.java @@ -155,6 +155,14 @@ public class RecentsAnimationController { }); } + /** + * @see IRecentsAnimationController#cleanupScreenshot() + */ + @UiThread + public void cleanupScreenshot() { + UI_HELPER_EXECUTOR.execute(() -> mController.cleanupScreenshot()); + } + /** * @see RecentsAnimationControllerCompat#detachNavigationBarFromApp */ @@ -171,6 +179,14 @@ public class RecentsAnimationController { UI_HELPER_EXECUTOR.execute(() -> mController.animateNavigationBarToApp(duration)); } + /** + * @see IRecentsAnimationController#setWillFinishToHome(boolean) + */ + @UiThread + public void setWillFinishToHome(boolean willFinishToHome) { + UI_HELPER_EXECUTOR.execute(() -> mController.setWillFinishToHome(willFinishToHome)); + } + /** * Sets the final surface transaction on a Task. This is used by Launcher to notify the system * that animating Activity to PiP has completed and the associated task surface should be diff --git a/quickstep/src/com/android/quickstep/views/RecentsView.java b/quickstep/src/com/android/quickstep/views/RecentsView.java index 8c3e5b513b..a36f2d4c8a 100644 --- a/quickstep/src/com/android/quickstep/views/RecentsView.java +++ b/quickstep/src/com/android/quickstep/views/RecentsView.java @@ -392,8 +392,6 @@ public abstract class RecentsView finishRecentsAnimation(true /* toRecents */, false /* showPip */, - this::updateRecentsRotation)); - mEnableDrawingLiveTile = false; - } else { - updateRecentsRotation(); - } - mOrientation = newConfig.orientation; + updateRecentsRotation(); } /** @@ -3404,16 +3393,26 @@ public abstract class RecentsView