Launcher3: Fix overview scrolling scale animation

Adapt it for Live Tile support + fix landscape handling

Change-Id: I1cf5d79aa6373e836d33bc7ddb15c0c5258a63d7
Signed-off-by: Adithya R <gh0strider.2k18.reborn@gmail.com>
This commit is contained in:
nift4
2023-10-03 23:30:41 +02:00
committed by MrSluffy
parent 6fc64ce9b7
commit 0312589cf5
3 changed files with 122 additions and 31 deletions

View File

@@ -191,19 +191,18 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
protected MultiStateCallback mStateCallback;
protected boolean mCanceled;
private boolean mRecentsViewScrollLinked = false;
private final ActivityLifecycleCallbacksAdapter mLifecycleCallbacks =
new ActivityLifecycleCallbacksAdapter() {
@Override
public void onActivityDestroyed(Activity activity) {
if (mActivity != activity) {
return;
}
ActiveGestureLog.INSTANCE.addLog("Launcher destroyed", LAUNCHER_DESTROYED);
mRecentsView = null;
mActivity = null;
mStateCallback.clearState(STATE_LAUNCHER_PRESENT);
}
};
private final ActivityLifecycleCallbacksAdapter mLifecycleCallbacks = new ActivityLifecycleCallbacksAdapter() {
@Override
public void onActivityDestroyed(Activity activity) {
if (mActivity != activity) {
return;
}
ActiveGestureLog.INSTANCE.addLog("Launcher destroyed", LAUNCHER_DESTROYED);
mRecentsView = null;
mActivity = null;
mStateCallback.clearState(STATE_LAUNCHER_PRESENT);
}
};
private static int FLAG_COUNT = 0;
private static int getNextStateFlag(String name) {
@@ -670,7 +669,6 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
runningTasks = cachedTaskInfo.getPlaceholderTasks();
}
// Safeguard against any null tasks being sent to recents view, happens when
// quickswitching
// very quickly w/ split tasks because TopTaskTracker provides stale information
@@ -1502,13 +1500,25 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
ArrayList<IBinder> launchCookies, long duration, boolean isTargetTranslucent,
boolean appCanEnterPip, RemoteAnimationTarget runningTaskTarget);
private final TaskStackChangeListener mActivityRestartListener=new TaskStackChangeListener(){@Override public void onActivityRestartAttempt(ActivityManager.RunningTaskInfo task,boolean homeTaskVisible,boolean clearedTask,boolean wasVisible){boolean taskRunningAndNotHome=Arrays.stream(mGestureState.getRunningTaskIds(true /*
* getMultipleTasks
*/)).anyMatch(taskId->task.taskId==taskId&&task.configuration.windowConfiguration.getActivityType()!=ACTIVITY_TYPE_HOME);if(taskRunningAndNotHome){
// Since this is an edge case, just cancel and relaunch with default activity
// options (since we don't know if there's an associated app icon to launch
// from)
endRunningWindowAnim(true /* cancel */);TaskStackChangeListeners.getInstance().unregisterTaskStackListener(mActivityRestartListener);ActivityManagerWrapper.getInstance().startActivityFromRecents(task.taskId,null);}}};
private final TaskStackChangeListener mActivityRestartListener = new TaskStackChangeListener() {
@Override
public void onActivityRestartAttempt(ActivityManager.RunningTaskInfo task, boolean homeTaskVisible,
boolean clearedTask, boolean wasVisible) {
boolean taskRunningAndNotHome = Arrays.stream(mGestureState.getRunningTaskIds(true /*
* getMultipleTasks
*/))
.anyMatch(taskId -> task.taskId == taskId
&& task.configuration.windowConfiguration.getActivityType() != ACTIVITY_TYPE_HOME);
if (taskRunningAndNotHome) {
// Since this is an edge case, just cancel and relaunch with default activity
// options (since we don't know if there's an associated app icon to launch
// from)
endRunningWindowAnim(true /* cancel */);
TaskStackChangeListeners.getInstance().unregisterTaskStackListener(mActivityRestartListener);
ActivityManagerWrapper.getInstance().startActivityFromRecents(task.taskId, null);
}
}
};
@UiThread
private void animateToProgressInternal(float start, float end, long duration,
@@ -1544,11 +1554,12 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
if (mGestureState.getEndTarget() == HOME) {
getOrientationHandler().adjustFloatingIconStartVelocity(velocityPxPerMs);
// Take first task ID, if there are multiple we don't have any special home
// animation so doesn't matter for splitscreen.. though the "allowEnterPip" might change
// animation so doesn't matter for splitscreen.. though the "allowEnterPip"
// might change
// depending on which task it is..
final RemoteAnimationTarget runningTaskTarget = mRecentsAnimationTargets != null
? mRecentsAnimationTargets
.findTask(mGestureState.getTopRunningTaskId())
.findTask(mGestureState.getTopRunningTaskId())
: null;
final ArrayList<IBinder> cookies = Utilities.ATLEAST_S && runningTaskTarget != null
&& runningTaskTarget.taskInfo != null
@@ -1577,7 +1588,8 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
mSwipePipToHomeReleaseCheck.setCanRelease(false);
}
// grab a screenshot before the PipContentOverlay gets parented on top of the task
// grab a screenshot before the PipContentOverlay gets parented on top of the
// task
UI_HELPER_EXECUTOR.execute(() -> {
// Directly use top task, split to pip handled on shell side
final int taskId = mGestureState.getTopRunningTaskId();
@@ -1603,7 +1615,7 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
windowAnim[0].addAnimatorListener(new AnimationSuccessListener() {
@Override
@Override
public void onAnimationSuccess(Animator animator) {
if (mRecentsAnimationController == null) {
// If the recents animation is interrupted, we still end the running
@@ -2435,7 +2447,8 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
transaction.forSurface(target.leash).setAlpha(1).setLayer(-1).setShow();
}
surfaceApplier.scheduleApply(transaction);
if (!LawnchairQuickstepCompat.ATLEAST_S) return;
if (!LawnchairQuickstepCompat.ATLEAST_S)
return;
SplashScreenExitAnimationUtils.startAnimations(splashView, taskTarget.leash,
mSplashMainWindowShiftLength, new TransactionPool(), new Rect(),
SPLASH_ANIMATION_DURATION, SPLASH_FADE_OUT_DURATION,
@@ -2521,6 +2534,7 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
startInterceptingTouchesForGesture();
}
for (RemoteTargetHandle remoteHandle : mRemoteTargetHandles) {
float scrollScale = setRecentsScroll ? mRecentsView.getScrollScale(remoteHandle) : 1f;
AnimatorControllerWithResistance playbackController = remoteHandle.getPlaybackController();
if (playbackController != null) {
playbackController.setProgress(progress, mDragLengthFactor);
@@ -2528,6 +2542,7 @@ public abstract class AbsSwipeUpHandler<T extends StatefulActivity<S>, Q extends
if (notSwipingToHome) {
TaskViewSimulator taskViewSimulator = remoteHandle.getTaskViewSimulator();
taskViewSimulator.scrollScale.value = scrollScale;
if (setRecentsScroll) {
taskViewSimulator.setScroll(scrollOffset);
}

View File

@@ -90,6 +90,7 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy {
private final FullscreenDrawParams mCurrentFullscreenParams;
public final AnimatedFloat taskPrimaryTranslation = new AnimatedFloat();
public final AnimatedFloat taskSecondaryTranslation = new AnimatedFloat();
public final AnimatedFloat scrollScale = new AnimatedFloat();
// RecentsView properties
public final AnimatedFloat recentsViewScale = new AnimatedFloat();
@@ -119,6 +120,9 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy {
mOrientationStateId = mOrientationState.getStateId();
Resources resources = context.getResources();
mIsRecentsRtl = mOrientationState.getOrientationHandler().getRecentsRtlSetting(resources);
//nick@lmo-20231004 this does belong here to avoid flicker in animation due to race of setting
// value to 1. other code assumes it starts with 1 anyway, so let's just do it here
this.scrollScale.value = 1;
}
/**
@@ -344,6 +348,7 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy {
}
float fullScreenProgress = Utilities.boundToRange(this.fullScreenProgress.value, 0, 1);
float scrollScale = this.scrollScale.value * (1f - fullScreenProgress) + fullScreenProgress;
mCurrentFullscreenParams.setProgress(fullScreenProgress, recentsViewScale.value,
/* taskViewScale= */1f, mTaskRect.width(), mDp, mPositionHelper);
@@ -355,6 +360,8 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy {
// Apply TaskView matrix: taskRect, translate
mMatrix.postTranslate(mTaskRect.left, mTaskRect.top);
mMatrix.postScale(scrollScale, scrollScale, mTaskRect.left + (mTaskRect.width() / 2),
mTaskRect.top + (mTaskRect.height() / 2));
mOrientationState.getOrientationHandler().setPrimary(mMatrix, MATRIX_POST_TRANSLATE,
taskPrimaryTranslation.value);
mOrientationState.getOrientationHandler().setSecondary(mMatrix, MATRIX_POST_TRANSLATE,
@@ -392,6 +399,8 @@ public class TaskViewSimulator implements TransformParams.BuilderProxy {
+ " recentsSecondaryT: " + recentsViewSecondaryTranslation.value
+ " taskSecondaryT: " + taskSecondaryTranslation.value
+ " recentsScroll: " + recentsViewScroll.value
+ " scrollScale: " + scrollScale
+ " this.scrollScale.value: " + this.scrollScale.value
+ " pivot: " + mPivot
);
}

View File

@@ -3710,16 +3710,42 @@ public abstract class RecentsView<ACTIVITY_TYPE extends StatefulActivity<STATE_T
}
}
int scrollDiff = newScroll[i] - oldScroll[i] + offset;
if (i == dismissedIndex + 1 ||
dismissedIndex == taskCount -1 && i == dismissedIndex - 1) {
if (child.getScaleX() <= dismissedTaskView.getScaleX())
if (child.getScaleX() <= dismissedTaskView.getScaleX()) {
anim.setFloat(child, SCALE_PROPERTY,
dismissedTaskView.getScaleX(), LINEAR);
else
if (child instanceof TaskView && mRemoteTargetHandles != null) {
TaskView tv = (TaskView) child;
for (RemoteTargetHandle rth : mRemoteTargetHandles) {
TransformParams params = rth.getTransformParams();
RemoteAnimationTargets targets = params.getTargetSet();
boolean match = false;
for (int id : tv.getTaskIds()) {
if (targets != null && targets.findTask(id) != null) {
match = true;
}
}
if (match) {
anim.addOnFrameCallback(() -> {
rth.getTaskViewSimulator().scrollScale.value =
mOrientationHandler.getPrimaryValue(
tv.getScaleX(),
tv.getScaleY()
);
// if scrollDiff != 0, we redraw in later(AOSP) code
if (mEnableDrawingLiveTile && scrollDiff == 0) {
redrawLiveTile();
}
});
}
}
}
} else
anim.setFloat(child, SCALE_PROPERTY, 1f, LINEAR);
}
int scrollDiff = newScroll[i] - oldScroll[i] + offset;
if (scrollDiff != 0) {
FloatProperty translationProperty = child instanceof TaskView
? ((TaskView) child).getPrimaryDismissTranslationProperty()
@@ -6174,10 +6200,16 @@ public abstract class RecentsView<ACTIVITY_TYPE extends StatefulActivity<STATE_T
if (showAsGrid())
return;
boolean isInLandscape = mOrientationState.getTouchRotation() != ROTATION_0
//nick@lmo-20231004 if rotating launcher is enabled, rotation works differently
// There are many edge cases (going from landscape app to recents, rotating in recents etc)
boolean touchInLandscape = mOrientationState.getTouchRotation() != ROTATION_0
&& mOrientationState.getTouchRotation() != ROTATION_180;
boolean layoutInLandscape = mOrientationState.getRecentsActivityRotation() != ROTATION_0
&& mOrientationState.getRecentsActivityRotation() != ROTATION_180;
boolean canRotateRecents = mOrientationState.isRecentsActivityRotationAllowed();
int childCount = Math.min(mPageScrolls.length, getChildCount());
int curScroll = isInLandscape ? getScrollY() : getScrollX();
int curScroll = !canRotateRecents && touchInLandscape && !layoutInLandscape
? getScrollY() : getScrollX();
for (int i = 0; i < childCount; i++) {
View child = getChildAt(i);
@@ -6192,9 +6224,44 @@ public abstract class RecentsView<ACTIVITY_TYPE extends StatefulActivity<STATE_T
child.setScaleX(scale);
child.setScaleY(scale);
}
if (!(child instanceof TaskView && mRemoteTargetHandles != null)) continue;
TaskView tv = (TaskView) child;
for (RemoteTargetHandle rth : mRemoteTargetHandles) {
TransformParams params = rth.getTransformParams();
RemoteAnimationTargets targets = params.getTargetSet();
for (int id : tv.getTaskIds()) {
if (targets != null && targets.findTask(id) != null) {
rth.getTaskViewSimulator().scrollScale.value =
mOrientationHandler.getPrimaryValue(
tv.getScaleX(),
tv.getScaleY()
);
}
}
}
}
}
public float getScrollScale(RemoteTargetHandle rth) {
int childCount = Math.min(mPageScrolls.length, getChildCount());
for (int i = 0; i < childCount; i++) {
View child = getChildAt(i);
if (!(child instanceof TaskView && !showAsGrid())) continue;
TaskView tv = (TaskView) child;
TransformParams params = rth.getTransformParams();
RemoteAnimationTargets targets = params.getTargetSet();
for (int id : tv.getTaskIds()) {
if (targets != null && targets.findTask(id) != null) {
return mOrientationHandler.getPrimaryValue(
tv.getScaleX(),
tv.getScaleY()
);
}
}
}
return 1f;
}
private void dispatchScrollChanged() {
runActionOnRemoteHandles(
remoteTargetHandle -> remoteTargetHandle.getTaskViewSimulator().setScroll(getScrollOffset()));