diff options
author | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2024-01-11 01:39:43 +0000 |
---|---|---|
committer | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2024-01-11 01:39:43 +0000 |
commit | 9be8bf7ce9be6f66472ada645af50f31093f8bfe (patch) | |
tree | 10921915d38cec2408188d87d7b6af14c70d46fa | |
parent | a2be7aa2fc030ae124ce0d24396b54f5c08dee35 (diff) | |
parent | 467b57b2ee1818039eb3f65e0d76a973d0626dbe (diff) | |
download | base-9be8bf7ce9be6f66472ada645af50f31093f8bfe.tar.gz |
Merge cherrypicks of ['googleplex-android-review.googlesource.com/25779963', 'googleplex-android-review.googlesource.com/25834515', 'googleplex-android-review.googlesource.com/25812532', 'googleplex-android-review.googlesource.com/25832083'] into 24Q1-release.
Change-Id: Idce83e9705cd4836e9fd9828eab98e135e3da4a8
9 files changed, 86 insertions, 33 deletions
diff --git a/core/api/test-current.txt b/core/api/test-current.txt index a3cd3dc87db3..30bd5f65a070 100644 --- a/core/api/test-current.txt +++ b/core/api/test-current.txt @@ -3672,6 +3672,7 @@ package android.view.animation { public class AnimationUtils { method @FlaggedApi("android.view.flags.expected_presentation_time_read_only") public static void lockAnimationClock(long, long); + method public static void lockAnimationClock(long); method public static void unlockAnimationClock(); } diff --git a/core/java/android/view/animation/AnimationUtils.java b/core/java/android/view/animation/AnimationUtils.java index b3359b711989..c1f42d25d0de 100644 --- a/core/java/android/view/animation/AnimationUtils.java +++ b/core/java/android/view/animation/AnimationUtils.java @@ -124,6 +124,40 @@ public class AnimationUtils { } /** + * Locks AnimationUtils{@link #currentAnimationTimeMillis()} to a fixed value for the current + * thread. This is used by {@link android.view.Choreographer} to ensure that all accesses + * during a vsync update are synchronized to the timestamp of the vsync. + * + * It is also exposed to tests to allow for rapid, flake-free headless testing. + * + * Must be followed by a call to {@link #unlockAnimationClock()} to allow time to + * progress. Failing to do this will result in stuck animations, scrolls, and flings. + * + * Note that time is not allowed to "rewind" and must perpetually flow forward. So the + * lock may fail if the time is in the past from a previously returned value, however + * time will be frozen for the duration of the lock. The clock is a thread-local, so + * ensure that {@link #lockAnimationClock(long)}, {@link #unlockAnimationClock()}, and + * {@link #currentAnimationTimeMillis()} are all called on the same thread. + * + * This is also not reference counted in any way. Any call to {@link #unlockAnimationClock()} + * will unlock the clock for everyone on the same thread. It is therefore recommended + * for tests to use their own thread to ensure that there is no collision with any existing + * {@link android.view.Choreographer} instance. + * + * Have to add the method back because of b/307888459. + * Remove this method once the lockAnimationClock(long, long) change + * is landed to aosp/android14-tests-dev branch. + * + * @hide + */ + @TestApi + public static void lockAnimationClock(long vsyncMillis) { + AnimationState state = sAnimationState.get(); + state.animationClockLocked = true; + state.currentVsyncTimeMillis = vsyncMillis; + } + + /** * Frees the time lock set in place by {@link #lockAnimationClock(long)}. Must be called * to allow the animation clock to self-update. * diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/IPip.aidl b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/IPip.aidl index 3906599b7581..8b3de6298b2a 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/IPip.aidl +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/IPip.aidl @@ -52,9 +52,10 @@ interface IPip { * @param componentName ComponentName represents the Activity * @param destinationBounds the destination bounds the PiP window lands into * @param overlay an optional overlay to fade out after entering PiP + * @param appBounds the bounds used to set the buffer size of the optional content overlay */ oneway void stopSwipePipToHome(int taskId, in ComponentName componentName, - in Rect destinationBounds, in SurfaceControl overlay) = 2; + in Rect destinationBounds, in SurfaceControl overlay, in Rect appBounds) = 2; /** * Notifies the swiping Activity to PiP onto home transition is aborted diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTaskOrganizer.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTaskOrganizer.java index 3635165d76ce..a9a3f788cb7e 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTaskOrganizer.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTaskOrganizer.java @@ -334,6 +334,16 @@ public class PipTaskOrganizer implements ShellTaskOrganizer.TaskListener, @Nullable SurfaceControl mPipOverlay; + /** + * The app bounds used for the buffer size of the + * {@link com.android.wm.shell.pip.PipContentOverlay.PipAppIconOverlay}. + * + * Note that this is empty if the overlay is removed or if it's some other type of overlay + * defined in {@link PipContentOverlay}. + */ + @NonNull + final Rect mAppBounds = new Rect(); + public PipTaskOrganizer(Context context, @NonNull SyncTransactionQueue syncTransactionQueue, @NonNull PipTransitionState pipTransitionState, @@ -464,15 +474,15 @@ public class PipTaskOrganizer implements ShellTaskOrganizer.TaskListener, * Expect {@link #onTaskAppeared(ActivityManager.RunningTaskInfo, SurfaceControl)} afterwards. */ public void stopSwipePipToHome(int taskId, ComponentName componentName, Rect destinationBounds, - SurfaceControl overlay) { + SurfaceControl overlay, Rect appBounds) { ProtoLog.d(ShellProtoLogGroup.WM_SHELL_PICTURE_IN_PICTURE, - "stopSwipePipToHome: %s, state=%s", componentName, mPipTransitionState); + "stopSwipePipToHome: %s, stat=%s", componentName, mPipTransitionState); // do nothing if there is no startSwipePipToHome being called before if (!mPipTransitionState.getInSwipePipToHomeTransition()) { return; } mPipBoundsState.setBounds(destinationBounds); - mPipOverlay = overlay; + setContentOverlay(overlay, appBounds); if (ENABLE_SHELL_TRANSITIONS && overlay != null) { // With Shell transition, the overlay was attached to the remote transition leash, which // will be removed when the current transition is finished, so we need to reparent it @@ -1888,7 +1898,7 @@ public class PipTaskOrganizer implements ShellTaskOrganizer.TaskListener, "%s: trying to remove overlay (%s) which is not local reference (%s)", TAG, surface, mPipOverlay); } - mPipOverlay = null; + clearContentOverlay(); } if (mPipTransitionState.getTransitionState() == PipTransitionState.UNDEFINED) { // Avoid double removal, which is fatal. @@ -1905,6 +1915,20 @@ public class PipTaskOrganizer implements ShellTaskOrganizer.TaskListener, if (callback != null) callback.run(); } + void clearContentOverlay() { + mPipOverlay = null; + mAppBounds.setEmpty(); + } + + void setContentOverlay(@Nullable SurfaceControl leash, @NonNull Rect appBounds) { + mPipOverlay = leash; + if (mPipOverlay != null) { + mAppBounds.set(appBounds); + } else { + mAppBounds.setEmpty(); + } + } + private void resetShadowRadius() { if (mPipTransitionState.getTransitionState() == PipTransitionState.UNDEFINED) { // mLeash is undefined when in PipTransitionState.UNDEFINED diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTransition.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTransition.java index f5f15d81ea44..89dcc4c1d261 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTransition.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/PipTransition.java @@ -141,8 +141,6 @@ public class PipTransition extends PipTransitionController { /** Whether the PIP window has fade out for fixed rotation. */ private boolean mHasFadeOut; - private Rect mInitBounds = new Rect(); - /** Used for setting transform to a transaction from animator. */ private final PipAnimationController.PipTransactionHandler mTransactionConsumer = new PipAnimationController.PipTransactionHandler() { @@ -465,12 +463,13 @@ public class PipTransition extends PipTransitionController { mSurfaceTransactionHelper.crop(tx, leash, destinationBounds) .resetScale(tx, leash, destinationBounds) .round(tx, leash, true /* applyCornerRadius */); - if (mPipOrganizer.mPipOverlay != null && !mInitBounds.isEmpty()) { + final Rect appBounds = mPipOrganizer.mAppBounds; + if (mPipOrganizer.mPipOverlay != null && !appBounds.isEmpty()) { // Resetting the scale for pinned task while re-adjusting its crop, // also scales the overlay. So we need to update the overlay leash too. Rect overlayBounds = new Rect(destinationBounds); final int overlaySize = PipContentOverlay.PipAppIconOverlay - .getOverlaySize(mInitBounds, destinationBounds); + .getOverlaySize(appBounds, destinationBounds); overlayBounds.offsetTo( (destinationBounds.width() - overlaySize) / 2, @@ -479,7 +478,6 @@ public class PipTransition extends PipTransitionController { mPipOrganizer.mPipOverlay, overlayBounds); } } - mInitBounds.setEmpty(); wct.setBoundsChangeTransaction(taskInfo.token, tx); } final int displayRotation = taskInfo.getConfiguration().windowConfiguration @@ -617,7 +615,7 @@ public class PipTransition extends PipTransitionController { // if overlay is present remove it immediately, as exit transition came before it faded out if (mPipOrganizer.mPipOverlay != null) { startTransaction.remove(mPipOrganizer.mPipOverlay); - clearPipOverlay(); + mPipOrganizer.clearContentOverlay(); } if (pipChange == null) { ProtoLog.w(ShellProtoLogGroup.WM_SHELL_PICTURE_IN_PICTURE, @@ -951,9 +949,6 @@ public class PipTransition extends PipTransitionController { final Rect destinationBounds = mPipBoundsAlgorithm.getEntryDestinationBounds(); final Rect currentBounds = pipChange.getStartAbsBounds(); - // Cache the start bounds for overlay manipulations as a part of finishCallback. - mInitBounds.set(currentBounds); - int rotationDelta = deltaRotation(startRotation, endRotation); Rect sourceHintRect = PipBoundsAlgorithm.getValidSourceHintRect( taskInfo.pictureInPictureParams, currentBounds, destinationBounds); @@ -1022,7 +1017,7 @@ public class PipTransition extends PipTransitionController { } else { throw new RuntimeException("Unrecognized animation type: " + enterAnimationType); } - mPipOrganizer.mPipOverlay = animator.getContentOverlayLeash(); + mPipOrganizer.setContentOverlay(animator.getContentOverlayLeash(), currentBounds); animator.setTransitionDirection(TRANSITION_DIRECTION_TO_PIP) .setPipAnimationCallback(mPipAnimationCallback) .setDuration(mEnterExitAnimationDuration); @@ -1073,10 +1068,6 @@ public class PipTransition extends PipTransitionController { ProtoLog.w(ShellProtoLogGroup.WM_SHELL_TRANSITIONS, "%s: SwipePipToHome should not use fixed rotation %d", TAG, mEndFixedRotation); } - Rect appBounds = pipTaskInfo.configuration.windowConfiguration.getAppBounds(); - if (mFixedRotationState == FIXED_ROTATION_CALLBACK && appBounds != null) { - mInitBounds.set(appBounds); - } final SurfaceControl swipePipToHomeOverlay = mPipOrganizer.mPipOverlay; if (swipePipToHomeOverlay != null) { // Launcher fade in the overlay on top of the fullscreen Task. It is possible we @@ -1106,7 +1097,7 @@ public class PipTransition extends PipTransitionController { sendOnPipTransitionFinished(TRANSITION_DIRECTION_TO_PIP); if (swipePipToHomeOverlay != null) { mPipOrganizer.fadeOutAndRemoveOverlay(swipePipToHomeOverlay, - this::clearPipOverlay /* callback */, false /* withStartDelay */); + null /* callback */, false /* withStartDelay */); } mPipTransitionState.setInSwipePipToHomeTransition(false); } @@ -1250,10 +1241,6 @@ public class PipTransition extends PipTransitionController { mPipMenuController.updateMenuBounds(destinationBounds); } - private void clearPipOverlay() { - mPipOrganizer.mPipOverlay = null; - } - @Override public void dump(PrintWriter pw, String prefix) { final String innerPrefix = prefix + " "; diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java index 63f20fd8e997..238e6b5bf2af 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/pip/phone/PipController.java @@ -982,8 +982,9 @@ public class PipController implements PipTransitionController.PipTransitionCallb } private void stopSwipePipToHome(int taskId, ComponentName componentName, Rect destinationBounds, - SurfaceControl overlay) { - mPipTaskOrganizer.stopSwipePipToHome(taskId, componentName, destinationBounds, overlay); + SurfaceControl overlay, Rect appBounds) { + mPipTaskOrganizer.stopSwipePipToHome(taskId, componentName, destinationBounds, overlay, + appBounds); } private void abortSwipePipToHome(int taskId, ComponentName componentName) { @@ -1280,13 +1281,13 @@ public class PipController implements PipTransitionController.PipTransitionCallb @Override public void stopSwipePipToHome(int taskId, ComponentName componentName, - Rect destinationBounds, SurfaceControl overlay) { + Rect destinationBounds, SurfaceControl overlay, Rect appBounds) { if (overlay != null) { overlay.setUnreleasedWarningCallSite("PipController.stopSwipePipToHome"); } executeRemoteCallWithTaskPermission(mController, "stopSwipePipToHome", (controller) -> controller.stopSwipePipToHome( - taskId, componentName, destinationBounds, overlay)); + taskId, componentName, destinationBounds, overlay, appBounds)); } @Override diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTransitions.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTransitions.java index 7dec12aac39b..bc1a57572c63 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTransitions.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/SplitScreenTransitions.java @@ -388,6 +388,7 @@ class SplitScreenTransitions { IBinder startResizeTransition(WindowContainerTransaction wct, Transitions.TransitionHandler handler, + @Nullable TransitionConsumedCallback consumedCallback, @Nullable TransitionFinishedCallback finishCallback) { if (mPendingResize != null) { mPendingResize.cancel(null); @@ -396,13 +397,14 @@ class SplitScreenTransitions { } IBinder transition = mTransitions.startTransition(TRANSIT_CHANGE, wct, handler); - setResizeTransition(transition, finishCallback); + setResizeTransition(transition, consumedCallback, finishCallback); return transition; } void setResizeTransition(@NonNull IBinder transition, + @Nullable TransitionConsumedCallback consumedCallback, @Nullable TransitionFinishedCallback finishCallback) { - mPendingResize = new TransitSession(transition, null /* consumedCb */, finishCallback); + mPendingResize = new TransitSession(transition, consumedCallback, finishCallback); ProtoLog.v(ShellProtoLogGroup.WM_SHELL_TRANSITIONS, " splitTransition " + " deduced Resize split screen"); } diff --git a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java index 96e57e71f05c..0781a9e440f3 100644 --- a/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java +++ b/libs/WindowManager/Shell/src/com/android/wm/shell/splitscreen/StageCoordinator.java @@ -2236,8 +2236,11 @@ public class StageCoordinator implements SplitLayout.SplitLayoutHandler, sendOnBoundsChanged(); if (ENABLE_SHELL_TRANSITIONS) { mSplitLayout.setDividerInteractive(false, false, "onSplitResizeStart"); - mSplitTransitions.startResizeTransition(wct, this, (finishWct, t) -> - mSplitLayout.setDividerInteractive(true, false, "onSplitResizeFinish")); + mSplitTransitions.startResizeTransition(wct, this, (aborted) -> { + mSplitLayout.setDividerInteractive(true, false, "onSplitResizeConsumed"); + }, (finishWct, t) -> { + mSplitLayout.setDividerInteractive(true, false, "onSplitResizeFinish"); + }); } else { // Only need screenshot for legacy case because shell transition should screenshot // itself during transition. diff --git a/packages/SystemUI/res/values/styles.xml b/packages/SystemUI/res/values/styles.xml index c48dd9d2f68b..e3d4419afceb 100644 --- a/packages/SystemUI/res/values/styles.xml +++ b/packages/SystemUI/res/values/styles.xml @@ -921,7 +921,7 @@ <style name="Theme.ControlsActivity" parent="@android:style/Theme.DeviceDefault.NoActionBar"> <item name="android:windowActivityTransitions">true</item> <item name="android:windowContentTransitions">false</item> - <item name="android:windowIsTranslucent">false</item> + <item name="android:windowIsTranslucent">true</item> <item name="android:windowBackground">@android:color/black</item> <item name="android:windowAnimationStyle">@null</item> <item name="android:statusBarColor">@android:color/black</item> |