diff options
10 files changed, 266 insertions, 98 deletions
diff --git a/quickstep/src/com/android/launcher3/uioverrides/AllAppsState.java b/quickstep/src/com/android/launcher3/uioverrides/AllAppsState.java index b580992c8..2ac932309 100644 --- a/quickstep/src/com/android/launcher3/uioverrides/AllAppsState.java +++ b/quickstep/src/com/android/launcher3/uioverrides/AllAppsState.java @@ -89,7 +89,7 @@ public class AllAppsState extends LauncherState { } @Override - public float getOverviewTranslationX(Launcher launcher) { + public float getOverviewTranslationFactor(Launcher launcher) { return 0; } diff --git a/quickstep/src/com/android/launcher3/uioverrides/OverviewState.java b/quickstep/src/com/android/launcher3/uioverrides/OverviewState.java index 0b69c582b..68322b0b1 100644 --- a/quickstep/src/com/android/launcher3/uioverrides/OverviewState.java +++ b/quickstep/src/com/android/launcher3/uioverrides/OverviewState.java @@ -58,7 +58,7 @@ public class OverviewState extends LauncherState { } @Override - public float getOverviewTranslationX(Launcher launcher) { + public float getOverviewTranslationFactor(Launcher launcher) { return 0; } diff --git a/quickstep/src/com/android/launcher3/uioverrides/PortraitStatesTouchController.java b/quickstep/src/com/android/launcher3/uioverrides/PortraitStatesTouchController.java index 9f648edd1..1e006e575 100644 --- a/quickstep/src/com/android/launcher3/uioverrides/PortraitStatesTouchController.java +++ b/quickstep/src/com/android/launcher3/uioverrides/PortraitStatesTouchController.java @@ -18,16 +18,24 @@ package com.android.launcher3.uioverrides; import static com.android.launcher3.LauncherState.ALL_APPS; import static com.android.launcher3.LauncherState.NORMAL; import static com.android.launcher3.LauncherState.OVERVIEW; +import static com.android.launcher3.anim.AnimatorSetBuilder.ANIM_OVERVIEW_TRANSLATION; +import static com.android.launcher3.anim.AnimatorSetBuilder.ANIM_VERTICAL_PROGRESS; +import static com.android.launcher3.anim.Interpolators.FAST_OUT_SLOW_IN; +import static com.android.launcher3.anim.Interpolators.LINEAR; +import android.animation.TimeInterpolator; +import android.animation.ValueAnimator; import android.view.MotionEvent; +import android.view.animation.Interpolator; import com.android.launcher3.AbstractFloatingView; import com.android.launcher3.DeviceProfile; import com.android.launcher3.Launcher; import com.android.launcher3.LauncherState; +import com.android.launcher3.anim.AnimatorSetBuilder; +import com.android.launcher3.touch.AbstractStateChangeTouchController; import com.android.launcher3.touch.SwipeDetector; import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType; -import com.android.launcher3.touch.AbstractStateChangeTouchController; import com.android.quickstep.TouchInteractionService; import com.android.quickstep.util.SysuiEventLogger; @@ -36,6 +44,47 @@ import com.android.quickstep.util.SysuiEventLogger; */ public class PortraitStatesTouchController extends AbstractStateChangeTouchController { + private static final float TOTAL_DISTANCE_MULTIPLIER = 2f; + private static final float LINEAR_SCALE_LIMIT = 1 / TOTAL_DISTANCE_MULTIPLIER; + + // Much be greater than LINEAR_SCALE_LIMIT; + private static final float MAXIMUM_DISTANCE_FACTOR = 0.9f; + + // Maximum amount to overshoot. + private static final float MAX_OVERSHOOT = 0.3f; + + private static final double PI_BY_2 = Math.PI / 2; + + private InterpolatorWrapper mAllAppsInterpolatorWrapper = new InterpolatorWrapper(); + + // If > 0, the animation progress is clamped at that value as long as user is dragging. + private float mClampProgressUpdate = -1; + + // If true, we will finish the current animation instantly on second touch. + private boolean mFinishFastOnSecondTouch; + + private final Interpolator mAllAppsDampedInterpolator = new Interpolator() { + + private final double mAngleMultiplier = Math.PI / + (2 * (MAXIMUM_DISTANCE_FACTOR - LINEAR_SCALE_LIMIT)); + + @Override + public float getInterpolation(float v) { + if (v <= LINEAR_SCALE_LIMIT) { + return v * TOTAL_DISTANCE_MULTIPLIER; + } + float overshoot = (v - LINEAR_SCALE_LIMIT); + return (float) (1 + MAX_OVERSHOOT * Math.sin(overshoot * mAngleMultiplier)); + } + }; + + private final Interpolator mOverviewBoundInterpolator = (v) -> { + if (v >= MAXIMUM_DISTANCE_FACTOR) { + return 1; + } + return FAST_OUT_SLOW_IN.getInterpolation(v / MAXIMUM_DISTANCE_FACTOR); + }; + public PortraitStatesTouchController(Launcher l) { super(l, SwipeDetector.VERTICAL); } @@ -43,6 +92,11 @@ public class PortraitStatesTouchController extends AbstractStateChangeTouchContr @Override protected boolean canInterceptTouch(MotionEvent ev) { if (mCurrentAnimation != null) { + if (mFinishFastOnSecondTouch) { + // TODO: Animate to finish instead. + mCurrentAnimation.getAnimationPlayer().end(); + } + // If we are already animating from a previous state, we can intercept. return true; } @@ -100,17 +154,49 @@ public class PortraitStatesTouchController extends AbstractStateChangeTouchContr } } + private AnimatorSetBuilder getNormalToOverviewAnimation() { + mAllAppsInterpolatorWrapper.baseInterpolator = mAllAppsDampedInterpolator; + + AnimatorSetBuilder builder = new AnimatorSetBuilder(); + builder.setInterpolator(ANIM_VERTICAL_PROGRESS, mAllAppsInterpolatorWrapper); + + builder.setInterpolator(ANIM_OVERVIEW_TRANSLATION, mOverviewBoundInterpolator); + return builder; + } + + @Override + protected void updateProgress(float fraction) { + if (mClampProgressUpdate > 0) { + mCurrentAnimation.setPlayFraction(Math.min(fraction, mClampProgressUpdate)); + } else { + super.updateProgress(fraction); + } + } + @Override protected float initCurrentAnimation() { float range = getShiftRange(); long maxAccuracy = (long) (2 * range); - mCurrentAnimation = mLauncher.getStateManager() - .createAnimationToNewWorkspace(mToState, maxAccuracy); float startVerticalShift = mFromState.getVerticalProgress(mLauncher) * range; float endVerticalShift = mToState.getVerticalProgress(mLauncher) * range; float totalShift = endVerticalShift - startVerticalShift; + + final AnimatorSetBuilder builder; + + if (mFromState == NORMAL && mToState == OVERVIEW && totalShift != 0) { + builder = getNormalToOverviewAnimation(); + totalShift = totalShift * TOTAL_DISTANCE_MULTIPLIER; + mClampProgressUpdate = MAXIMUM_DISTANCE_FACTOR; + } else { + builder = new AnimatorSetBuilder(); + mClampProgressUpdate = -1; + } + + mCurrentAnimation = mLauncher.getStateManager() + .createAnimationToNewWorkspace(mToState, builder, maxAccuracy); + if (totalShift == 0) { totalShift = Math.signum(mFromState.ordinal - mToState.ordinal) * OverviewState.getDefaultSwipeHeight(mLauncher); @@ -119,10 +205,87 @@ public class PortraitStatesTouchController extends AbstractStateChangeTouchContr } @Override + protected void updateSwipeCompleteAnimation(ValueAnimator animator, long expectedDuration, + LauncherState targetState, float velocity, boolean isFling) { + if (mFromState == NORMAL && mToState == OVERVIEW && targetState == OVERVIEW) { + mFinishFastOnSecondTouch = true; + + // Update all apps interpolator + float currentFraction = mCurrentAnimation.getProgressFraction(); + float absVelocity = Math.abs(velocity); + float currentValue = mAllAppsDampedInterpolator.getInterpolation(currentFraction); + + if (isFling && absVelocity > 1 && currentFraction < LINEAR_SCALE_LIMIT) { + + // TODO: Clean up these magic calculations + // Linearly interpolate the max value based on the velocity. + float maxValue = Math.max(absVelocity > 4 ? 1 + MAX_OVERSHOOT : + 1 + (absVelocity - 1) * MAX_OVERSHOOT / 3, + currentValue); + double angleToPeak = PI_BY_2 - Math.asin(currentValue / maxValue); + + if (expectedDuration != 0 && angleToPeak != 0) { + + float distanceLeft = 1 - currentFraction; + mAllAppsInterpolatorWrapper.baseInterpolator = (f) -> { + float scaledF = (f - currentFraction) / distanceLeft; + + if (scaledF < 0.5f) { + double angle = PI_BY_2 - angleToPeak + scaledF * angleToPeak / 0.5f; + return (float) (maxValue * Math.sin(angle)); + } + + scaledF = ((scaledF - .5f) / .5f); + double angle = PI_BY_2 + 3 * scaledF * PI_BY_2; + float amplitude = (1 - scaledF) * (1 - scaledF) * (maxValue - 1); + return 1 + (float) (amplitude * Math.sin(angle)); + }; + + animator.setDuration(expectedDuration).setInterpolator(LINEAR); + return; + } + } + + if (currentFraction < LINEAR_SCALE_LIMIT) { + mAllAppsInterpolatorWrapper.baseInterpolator = LINEAR; + super.updateSwipeCompleteAnimation(animator, expectedDuration, targetState, + velocity, isFling); + return; + } + float extraValue = mAllAppsDampedInterpolator.getInterpolation(currentFraction) - 1; + float distanceLeft = 1 - currentFraction; + + animator.setFloatValues(currentFraction, 1); + mAllAppsInterpolatorWrapper.baseInterpolator = (f) -> { + float scaledF = (f - currentFraction) / distanceLeft; + + double angle = scaledF * 1.5 * Math.PI; + float amplitude = (1 - scaledF) * (1 - scaledF) * extraValue; + return 1 + (float) (amplitude * Math.sin(angle)); + }; + animator.setDuration(200).setInterpolator(LINEAR); + return; + } + mFinishFastOnSecondTouch = false; + super.updateSwipeCompleteAnimation(animator, expectedDuration, targetState, + velocity, isFling); + } + + @Override protected void onSwipeInteractionCompleted(LauncherState targetState, int logAction) { super.onSwipeInteractionCompleted(targetState, logAction); if (mFromState == NORMAL && targetState == OVERVIEW) { SysuiEventLogger.writeDummyRecentsTransition(0); } } + + private static class InterpolatorWrapper implements Interpolator { + + public TimeInterpolator baseInterpolator = LINEAR; + + @Override + public float getInterpolation(float v) { + return baseInterpolator.getInterpolation(v); + } + } } diff --git a/quickstep/src/com/android/launcher3/uioverrides/RecentsViewStateController.java b/quickstep/src/com/android/launcher3/uioverrides/RecentsViewStateController.java index b68a3d845..ae747d881 100644 --- a/quickstep/src/com/android/launcher3/uioverrides/RecentsViewStateController.java +++ b/quickstep/src/com/android/launcher3/uioverrides/RecentsViewStateController.java @@ -16,32 +16,30 @@ package com.android.launcher3.uioverrides; import static com.android.launcher3.LauncherState.NORMAL; +import static com.android.launcher3.anim.AlphaUpdateListener.updateVisibility; +import static com.android.launcher3.anim.AnimatorSetBuilder.ANIM_OVERVIEW_TRANSLATION; +import static com.android.launcher3.anim.Interpolators.LINEAR; +import static com.android.launcher3.compat.AccessibilityManagerCompat.isAccessibilityEnabled; +import static com.android.quickstep.views.LauncherRecentsView.TRANSLATION_FACTOR; -import android.animation.Animator; -import android.animation.AnimatorListenerAdapter; -import android.animation.ObjectAnimator; -import android.view.View; +import android.animation.ValueAnimator; +import android.annotation.TargetApi; +import android.os.Build; import com.android.launcher3.Launcher; import com.android.launcher3.LauncherState; import com.android.launcher3.LauncherStateManager.AnimationConfig; import com.android.launcher3.LauncherStateManager.StateHandler; import com.android.launcher3.PagedView; -import com.android.launcher3.anim.AnimationSuccessListener; import com.android.launcher3.anim.AnimatorSetBuilder; -import com.android.launcher3.anim.Interpolators; -import com.android.quickstep.AnimatedFloat; -import com.android.quickstep.views.RecentsView; +import com.android.launcher3.anim.PropertySetter; +import com.android.quickstep.views.LauncherRecentsView; +@TargetApi(Build.VERSION_CODES.O) public class RecentsViewStateController implements StateHandler { private final Launcher mLauncher; - private final RecentsView mRecentsView; - - private final AnimatedFloat mTransitionProgress = new AnimatedFloat(this::onTransitionProgress); - // The fraction representing the visibility of the RecentsView. This allows delaying the - // overall transition while the RecentsView is being shown or hidden. - private final AnimatedFloat mVisibilityMultiplier = new AnimatedFloat(this::onVisibilityProgress); + private final LauncherRecentsView mRecentsView; public RecentsViewStateController(Launcher launcher) { mLauncher = launcher; @@ -50,14 +48,12 @@ public class RecentsViewStateController implements StateHandler { @Override public void setState(LauncherState state) { - setVisibility(state.overviewUi); - setTransitionProgress(state.overviewUi ? 1 : 0); + mRecentsView.setAlpha(state.overviewUi ? 1 : 0); + updateVisibility(mRecentsView, isAccessibilityEnabled(mLauncher)); + mRecentsView.setTranslationFactor(state.getOverviewTranslationFactor(mLauncher)); if (state.overviewUi) { mRecentsView.resetTaskVisuals(); } - float overviewTranslationX = state.getOverviewTranslationX(mLauncher); - int direction = mRecentsView.isRtl() ? -1 : 1; - mRecentsView.setTranslationX(overviewTranslationX * direction); } @Override @@ -76,73 +72,20 @@ public class RecentsViewStateController implements StateHandler { builder.setStartDelay(snapDuration / 4); } - ObjectAnimator progressAnim = - mTransitionProgress.animateToValue(toState.overviewUi ? 1 : 0); - progressAnim.setDuration(config.duration); - progressAnim.setInterpolator(Interpolators.LINEAR); - builder.play(progressAnim); - - ObjectAnimator visibilityAnim = animateVisibility(toState.overviewUi); - visibilityAnim.setDuration(config.duration); - visibilityAnim.setInterpolator(Interpolators.LINEAR); - builder.play(visibilityAnim); + PropertySetter setter = config.getProperSetter(builder); + setter.setFloat(mRecentsView, TRANSLATION_FACTOR, + toState.getOverviewTranslationFactor(mLauncher), + builder.getInterpolator(ANIM_OVERVIEW_TRANSLATION, LINEAR)); + setter.setViewAlpha(mRecentsView, toState.overviewUi ? 1 : 0, LINEAR); - int direction = mRecentsView.isRtl() ? -1 : 1; - float fromTranslationX = fromState.getOverviewTranslationX(mLauncher) * direction; - float toTranslationX = toState.getOverviewTranslationX(mLauncher) * direction; - ObjectAnimator translationXAnim = ObjectAnimator.ofFloat(mRecentsView, View.TRANSLATION_X, - fromTranslationX, toTranslationX); - translationXAnim.setDuration(config.duration); - translationXAnim.setInterpolator(Interpolators.ACCEL); if (toState.overviewUi) { - translationXAnim.addUpdateListener(valueAnimator -> { + ValueAnimator updateAnim = ValueAnimator.ofFloat(0, 1); + updateAnim.addUpdateListener(valueAnimator -> { // While animating into recents, update the visible task data as needed mRecentsView.loadVisibleTaskData(); }); + updateAnim.setDuration(config.duration); + builder.play(updateAnim); } - builder.play(translationXAnim); - } - - public void setVisibility(boolean isVisible) { - mVisibilityMultiplier.cancelAnimation(); - mRecentsView.setVisibility(isVisible ? View.VISIBLE : View.GONE); - mVisibilityMultiplier.updateValue(isVisible ? 1 : 0); - } - - public ObjectAnimator animateVisibility(boolean isVisible) { - ObjectAnimator anim = mVisibilityMultiplier.animateToValue(isVisible ? 1 : 0); - if (isVisible) { - anim.addListener(new AnimatorListenerAdapter() { - @Override - public void onAnimationStart(Animator animation) { - mRecentsView.setVisibility(View.VISIBLE); - } - }); - } else { - anim.addListener(new AnimationSuccessListener() { - @Override - public void onAnimationSuccess(Animator animator) { - mRecentsView.setVisibility(View.GONE); - } - }); - } - return anim; - } - - public void setTransitionProgress(float progress) { - mTransitionProgress.cancelAnimation(); - mTransitionProgress.updateValue(progress); - } - - private void onTransitionProgress() { - applyProgress(); - } - - private void onVisibilityProgress() { - applyProgress(); - } - - private void applyProgress() { - mRecentsView.setAlpha(mTransitionProgress.value * mVisibilityMultiplier.value); } } diff --git a/quickstep/src/com/android/quickstep/views/LauncherRecentsView.java b/quickstep/src/com/android/quickstep/views/LauncherRecentsView.java index 7989e845c..d490f82b9 100644 --- a/quickstep/src/com/android/quickstep/views/LauncherRecentsView.java +++ b/quickstep/src/com/android/quickstep/views/LauncherRecentsView.java @@ -17,6 +17,7 @@ package com.android.quickstep.views; import static com.android.launcher3.LauncherState.NORMAL; +import android.annotation.TargetApi; import android.content.Context; import android.graphics.Bitmap; import android.graphics.BitmapShader; @@ -30,7 +31,9 @@ import android.graphics.Shader; import android.graphics.Shader.TileMode; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; +import android.os.Build; import android.util.AttributeSet; +import android.util.FloatProperty; import android.widget.FrameLayout; import com.android.launcher3.DeviceProfile; @@ -41,14 +44,31 @@ import com.android.launcher3.R; /** * {@link RecentsView} used in Launcher activity */ +@TargetApi(Build.VERSION_CODES.O) public class LauncherRecentsView extends RecentsView<Launcher> implements Insettable { + public static final FloatProperty<LauncherRecentsView> TRANSLATION_FACTOR = + new FloatProperty<LauncherRecentsView>("translationFactor") { + + @Override + public void setValue(LauncherRecentsView view, float v) { + view.setTranslationFactor(v); + } + + @Override + public Float get(LauncherRecentsView view) { + return view.mTranslationFactor; + } + }; + private Bitmap mScrim; private Paint mFadePaint; private Shader mFadeShader; private Matrix mFadeMatrix; private boolean mScrimOnLeft; + private float mTranslationFactor; + public LauncherRecentsView(Context context) { this(context, null); } @@ -131,4 +151,21 @@ public class LauncherRecentsView extends RecentsView<Launcher> implements Insett protected void onAllTasksRemoved() { mActivity.getStateManager().goToState(NORMAL); } + + @Override + protected void onLayout(boolean changed, int left, int top, int right, int bottom) { + super.onLayout(changed, left, top, right, bottom); + + int width = right - left; + setTranslationX(mTranslationFactor * (mIsRtl ? -width : width)); + } + + public void setTranslationFactor(float translationFactor) { + mTranslationFactor = translationFactor; + setTranslationX(translationFactor * (mIsRtl ? -getWidth() : getWidth())); + } + + public float getTranslationFactor() { + return mTranslationFactor; + } } diff --git a/src/com/android/launcher3/LauncherState.java b/src/com/android/launcher3/LauncherState.java index 6185844cc..5c16ca990 100644 --- a/src/com/android/launcher3/LauncherState.java +++ b/src/com/android/launcher3/LauncherState.java @@ -180,8 +180,8 @@ public class LauncherState { return new float[] {1, 0, 0}; } - public float getOverviewTranslationX(Launcher launcher) { - return launcher.getDragLayer().getMeasuredWidth(); + public float getOverviewTranslationFactor(Launcher launcher) { + return 1; } public void onStateEnabled(Launcher launcher) { diff --git a/src/com/android/launcher3/allapps/AllAppsTransitionController.java b/src/com/android/launcher3/allapps/AllAppsTransitionController.java index fbd23d15a..9be123f97 100644 --- a/src/com/android/launcher3/allapps/AllAppsTransitionController.java +++ b/src/com/android/launcher3/allapps/AllAppsTransitionController.java @@ -3,6 +3,7 @@ package com.android.launcher3.allapps; import static com.android.launcher3.LauncherState.ALL_APPS_CONTENT; import static com.android.launcher3.LauncherState.ALL_APPS_HEADER; import static com.android.launcher3.LauncherState.ALL_APPS_HEADER_EXTRA; +import static com.android.launcher3.anim.AnimatorSetBuilder.ANIM_VERTICAL_PROGRESS; import static com.android.launcher3.anim.Interpolators.FAST_OUT_SLOW_IN; import static com.android.launcher3.anim.Interpolators.LINEAR; import static com.android.launcher3.anim.PropertySetter.NO_ANIM_PROPERTY_SETTER; @@ -55,8 +56,6 @@ public class AllAppsTransitionController } }; - public static final float PARALLAX_COEFFICIENT = .125f; - private AllAppsContainerView mAppsView; private final Launcher mLauncher; @@ -169,7 +168,7 @@ public class AllAppsTransitionController ObjectAnimator anim = ObjectAnimator.ofFloat(this, ALL_APPS_PROGRESS, mProgress, targetProgress); anim.setDuration(config.duration); - anim.setInterpolator(interpolator); + anim.setInterpolator(builder.getInterpolator(ANIM_VERTICAL_PROGRESS, interpolator)); anim.addListener(getProgressAnimatorListener()); builder.play(anim); diff --git a/src/com/android/launcher3/anim/AnimatorSetBuilder.java b/src/com/android/launcher3/anim/AnimatorSetBuilder.java index 7cd96512d..919104886 100644 --- a/src/com/android/launcher3/anim/AnimatorSetBuilder.java +++ b/src/com/android/launcher3/anim/AnimatorSetBuilder.java @@ -17,6 +17,8 @@ package com.android.launcher3.anim; import android.animation.Animator; import android.animation.AnimatorSet; +import android.util.SparseArray; +import android.view.animation.Interpolator; import com.android.launcher3.LauncherAnimUtils; @@ -27,7 +29,12 @@ import java.util.ArrayList; */ public class AnimatorSetBuilder { + public static final int ANIM_VERTICAL_PROGRESS = 0; + public static final int ANIM_OVERVIEW_TRANSLATION = 1; + protected final ArrayList<Animator> mAnims = new ArrayList<>(); + + private final SparseArray<Interpolator> mInterpolators = new SparseArray<>(); private long mStartDelay = 0; /** @@ -49,4 +56,12 @@ public class AnimatorSetBuilder { anim.setStartDelay(mStartDelay); return anim; } + + public Interpolator getInterpolator(int animId, Interpolator fallback) { + return mInterpolators.get(animId, fallback); + } + + public void setInterpolator(int animId, Interpolator interpolator) { + mInterpolators.put(animId, interpolator); + } } diff --git a/src/com/android/launcher3/touch/AbstractStateChangeTouchController.java b/src/com/android/launcher3/touch/AbstractStateChangeTouchController.java index db5363436..a22f450e3 100644 --- a/src/com/android/launcher3/touch/AbstractStateChangeTouchController.java +++ b/src/com/android/launcher3/touch/AbstractStateChangeTouchController.java @@ -19,6 +19,7 @@ import static com.android.launcher3.anim.Interpolators.scrollInterpolatorForVelo import android.animation.Animator; import android.animation.AnimatorListenerAdapter; +import android.animation.TimeInterpolator; import android.animation.ValueAnimator; import android.util.Log; import android.view.MotionEvent; @@ -140,10 +141,14 @@ public abstract class AbstractStateChangeTouchController extends AnimatorListene @Override public boolean onDrag(float displacement, float velocity) { float deltaProgress = mProgressMultiplier * displacement; - mCurrentAnimation.setPlayFraction(deltaProgress + mStartProgress); + updateProgress(deltaProgress + mStartProgress); return true; } + protected void updateProgress(float fraction) { + mCurrentAnimation.setPlayFraction(fraction); + } + @Override public void onDragEnd(float velocity, boolean fling) { final int logAction; @@ -173,7 +178,7 @@ public abstract class AbstractStateChangeTouchController extends AnimatorListene startProgress = 1; } else { startProgress = Utilities.boundToRange( - progress + velocity * SINGLE_FRAME_MS / getShiftRange(), 0f, 1f); + progress + velocity * SINGLE_FRAME_MS * mProgressMultiplier, 0f, 1f); duration = SwipeDetector.calculateDuration(velocity, endProgress - Math.max(progress, 0)); } @@ -184,7 +189,7 @@ public abstract class AbstractStateChangeTouchController extends AnimatorListene startProgress = 0; } else { startProgress = Utilities.boundToRange( - progress + velocity * SINGLE_FRAME_MS / getShiftRange(), 0f, 1f); + progress + velocity * SINGLE_FRAME_MS * mProgressMultiplier, 0f, 1f); duration = SwipeDetector.calculateDuration(velocity, Math.min(progress, 1) - endProgress); } @@ -193,10 +198,16 @@ public abstract class AbstractStateChangeTouchController extends AnimatorListene mCurrentAnimation.setEndAction(() -> onSwipeInteractionCompleted(targetState, logAction)); ValueAnimator anim = mCurrentAnimation.getAnimationPlayer(); anim.setFloatValues(startProgress, endProgress); - anim.setDuration(duration).setInterpolator(scrollInterpolatorForVelocity(velocity)); + updateSwipeCompleteAnimation(anim, duration, targetState, velocity, fling); anim.start(); } + protected void updateSwipeCompleteAnimation(ValueAnimator animator, long expectedDuration, + LauncherState targetState, float velocity, boolean isFling) { + animator.setDuration(expectedDuration) + .setInterpolator(scrollInterpolatorForVelocity(velocity)); + } + protected int getDirectionForLog() { return mToState.ordinal > mFromState.ordinal ? Direction.UP : Direction.DOWN; } diff --git a/src_ui_overrides/com/android/launcher3/uioverrides/AllAppsState.java b/src_ui_overrides/com/android/launcher3/uioverrides/AllAppsState.java index c05d30ccd..121f13e7b 100644 --- a/src_ui_overrides/com/android/launcher3/uioverrides/AllAppsState.java +++ b/src_ui_overrides/com/android/launcher3/uioverrides/AllAppsState.java @@ -25,7 +25,6 @@ import com.android.launcher3.AbstractFloatingView; import com.android.launcher3.Launcher; import com.android.launcher3.LauncherState; import com.android.launcher3.R; -import com.android.launcher3.allapps.AllAppsTransitionController; import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType; /** @@ -33,6 +32,8 @@ import com.android.launcher3.userevent.nano.LauncherLogProto.ContainerType; */ public class AllAppsState extends LauncherState { + private static final float PARALLAX_COEFFICIENT = .125f; + private static final int STATE_FLAGS = FLAG_DISABLE_ACCESSIBILITY | FLAG_SHOW_SCRIM | FLAG_ALL_APPS_SCRIM; @@ -75,8 +76,7 @@ public class AllAppsState extends LauncherState { @Override public float[] getWorkspaceScaleAndTranslation(Launcher launcher) { return new float[] { 1f, 0, - -launcher.getAllAppsController().getShiftRange() - * AllAppsTransitionController.PARALLAX_COEFFICIENT}; + -launcher.getAllAppsController().getShiftRange() * PARALLAX_COEFFICIENT}; } @Override |