Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 6b2da34c authored by Marzia Favaro's avatar Marzia Favaro
Browse files

Finish animation callback set latest value

Instead of the state on which the animation was started, a cancelled
animation will set the latest state. This ensures that we don't
accidentally end up in an old state if the animation callback is
executed slighly after the next dim state update.

Bug: 357028844
Test: DimmerTests
Flag: EXEMPT change is minor
Change-Id: Ife7eeeee16b0eeb09bf7c3a4eb77f79dc1688414
parent d5846c23
Loading
Loading
Loading
Loading
+27 −27
Original line number Diff line number Diff line
@@ -55,10 +55,11 @@ public class DimmerAnimationHelper {

        Change() {}

        Change(@NonNull Change other) {
        void copyFrom(@NonNull Change other) {
            mAlpha = other.mAlpha;
            mBlurRadius = other.mBlurRadius;
            mDimmingContainer = other.mDimmingContainer;
            mGeometryParent = other.mGeometryParent;
            mRelativeLayer = other.mRelativeLayer;
        }

@@ -83,8 +84,8 @@ public class DimmerAnimationHelper {
        }
    }

    private Change mCurrentProperties = new Change();
    private Change mRequestedProperties = new Change();
    private final Change mCurrentProperties = new Change();
    private final Change mRequestedProperties = new Change();
    private AnimationSpec mAlphaAnimationSpec;

    private final AnimationAdapterFactory mAnimationAdapterFactory;
@@ -128,7 +129,7 @@ public class DimmerAnimationHelper {
                    + "call adjustRelativeLayer?");
            return;
        }
        if (mRequestedProperties.mDimmingContainer.mSurfaceControl == null) {
        if (mRequestedProperties.mDimmingContainer.getSurfaceControl() == null) {
            Log.w(TAG, "container " + mRequestedProperties.mDimmingContainer
                    + "does not have a surface");
            dim.remove(t);
@@ -154,35 +155,35 @@ public class DimmerAnimationHelper {
                        "%s skipping animation and directly setting alpha=%f, blur=%d",
                        dim, mRequestedProperties.mAlpha,
                        mRequestedProperties.mBlurRadius);
                setAlphaBlur(dim.mDimSurface, mRequestedProperties.mAlpha,
                        mRequestedProperties.mBlurRadius, t);
                mCurrentProperties.copyFrom(mRequestedProperties);
                setCurrentAlphaBlur(dim.mDimSurface, t);
                dim.mSkipAnimation = false;
            } else {
                startAnimation(t, dim);
                Change startProperties = mCurrentProperties;
                mCurrentProperties.copyFrom(mRequestedProperties);
                startAnimation(t, dim, startProperties, mRequestedProperties);
            }

        } else if (!dim.isDimming()) {
            // We are not dimming, so we tried the exit animation but the alpha is already 0,
            // therefore, let's just remove this surface
            dim.remove(t);
        }
        mCurrentProperties = new Change(mRequestedProperties);
    }

    private void startAnimation(
            @NonNull SurfaceControl.Transaction t, @NonNull Dimmer.DimState dim) {
            @NonNull SurfaceControl.Transaction t, @NonNull Dimmer.DimState dim,
            @NonNull Change from, @NonNull Change to) {
        ProtoLog.v(WM_DEBUG_DIMMER, "Starting animation on %s", dim);
        mAlphaAnimationSpec = getRequestedAnimationSpec();
        mAlphaAnimationSpec = getRequestedAnimationSpec(from, to);
        mLocalAnimationAdapter = mAnimationAdapterFactory.get(mAlphaAnimationSpec,
                dim.mHostContainer.mWmService.mSurfaceAnimationRunner);

        float targetAlpha = mRequestedProperties.mAlpha;
        int targetBlur = mRequestedProperties.mBlurRadius;
        float targetAlpha = to.mAlpha;

        mLocalAnimationAdapter.startAnimation(dim.mDimSurface, t,
                ANIMATION_TYPE_DIMMER, /* finishCallback */ (type, animator) -> {
                    synchronized (dim.mHostContainer.mWmService.mGlobalLock) {
                        setAlphaBlur(dim.mDimSurface, targetAlpha, targetBlur, t);
                        setCurrentAlphaBlur(dim.mDimSurface, t);
                        if (targetAlpha == 0f && !dim.isDimming()) {
                            dim.remove(t);
                        }
@@ -207,15 +208,15 @@ public class DimmerAnimationHelper {
    }

    @NonNull
    private AnimationSpec getRequestedAnimationSpec() {
        final float startAlpha = Math.max(mCurrentProperties.mAlpha, 0f);
        final int startBlur = Math.max(mCurrentProperties.mBlurRadius, 0);
        long duration = (long) (getDimDuration(mRequestedProperties.mDimmingContainer)
                * Math.abs(mRequestedProperties.mAlpha - startAlpha));
    private static AnimationSpec getRequestedAnimationSpec(Change from, Change to) {
        final float startAlpha = Math.max(from.mAlpha, 0f);
        final int startBlur = Math.max(from.mBlurRadius, 0);
        long duration = (long) (getDimDuration(to.mDimmingContainer)
                * Math.abs(to.mAlpha - startAlpha));

        final AnimationSpec spec =  new AnimationSpec(
                new AnimationSpec.AnimationExtremes<>(startAlpha, mRequestedProperties.mAlpha),
                new AnimationSpec.AnimationExtremes<>(startBlur, mRequestedProperties.mBlurRadius),
                new AnimationSpec.AnimationExtremes<>(startAlpha, to.mAlpha),
                new AnimationSpec.AnimationExtremes<>(startBlur, to.mBlurRadius),
                duration
        );
        ProtoLog.v(WM_DEBUG_DIMMER, "Dim animation requested: %s", spec);
@@ -225,7 +226,7 @@ public class DimmerAnimationHelper {
    /**
     * Change the geometry and relative parent of this dim layer
     */
    void reparent(@NonNull SurfaceControl dimLayer,
    static void reparent(@NonNull SurfaceControl dimLayer,
                  @Nullable SurfaceControl newGeometryParent,
                  @NonNull SurfaceControl relativeParent,
                  int relativePosition,
@@ -240,17 +241,16 @@ public class DimmerAnimationHelper {
        }
    }

    void setAlphaBlur(@NonNull SurfaceControl sc, float alpha, int blur,
                      @NonNull SurfaceControl.Transaction t) {
    void setCurrentAlphaBlur(@NonNull SurfaceControl sc, @NonNull SurfaceControl.Transaction t) {
        try {
            t.setAlpha(sc, alpha);
            t.setBackgroundBlurRadius(sc, blur);
            t.setAlpha(sc, mCurrentProperties.mAlpha);
            t.setBackgroundBlurRadius(sc, mCurrentProperties.mBlurRadius);
        } catch (NullPointerException e) {
            Log.w(TAG , "Tried to change look of dim " + sc + " after remove",  e);
        }
    }

    private long getDimDuration(@NonNull WindowContainer<?> container) {
    private static long getDimDuration(@NonNull WindowContainer<?> container) {
        // Use the same duration as the animation on the WindowContainer
        AnimationAdapter animationAdapter = container.mSurfaceAnimator.getAnimation();
        final float durationScale = container.mWmService.getTransitionAnimationScaleLocked();