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

Commit 16423aa0 authored by Jorim Jaggi's avatar Jorim Jaggi
Browse files

Improve doze transitions

This change animates the status bar and the bottom area when exiting
doze mode from touch. We also prevent all animations when exiting
from other means, i.e. usually when the power button is pressed, so
we don't have a distracting animation there. In addition, this also
optimizes the scrim animations a bit in terms of interpolation and
duration to make the experience smoother and cleans up some logic.

Bug: 18146441
Bug: 17717584
Change-Id: I495ce480c25de24b6433adebdfe923b637d98f66
parent d3a8c8aa
Loading
Loading
Loading
Loading
+5 −2
Original line number Diff line number Diff line
@@ -224,13 +224,16 @@
    <integer name="doze_pickup_vibration_threshold">2000</integer>

    <!-- Doze: pulse parameter - how long does it take to fade in? -->
    <integer name="doze_pulse_duration_in">1000</integer>
    <integer name="doze_pulse_duration_in">900</integer>

    <!-- Doze: pulse parameter - delay for fading so the screen can wake up before -->
    <integer name="doze_pulse_delay_in">200</integer>

    <!-- Doze: pulse parameter - once faded in, how long does it stay visible? -->
    <integer name="doze_pulse_duration_visible">3000</integer>

    <!-- Doze: pulse parameter - how long does it take to fade out? -->
    <integer name="doze_pulse_duration_out">1000</integer>
    <integer name="doze_pulse_duration_out">600</integer>

    <!-- Doze: alpha to apply to small icons when dozing -->
    <integer name="doze_small_icon_alpha">222</integer><!-- 87% of 0xff -->
+4 −0
Original line number Diff line number Diff line
@@ -72,6 +72,10 @@ public class DozeParameters {
        return getInt("doze.pulse.duration.in", R.integer.doze_pulse_duration_in);
    }

    public int getPulseInDelay() {
        return getInt("doze.pulse.delay.in", R.integer.doze_pulse_delay_in);
    }

    public int getPulseVisibleDuration() {
        return getInt("doze.pulse.duration.visible", R.integer.doze_pulse_duration_visible);
    }
+36 −1
Original line number Diff line number Diff line
@@ -39,6 +39,8 @@ import android.util.TypedValue;
import android.view.View;
import android.view.ViewGroup;
import android.view.accessibility.AccessibilityNodeInfo;
import android.view.animation.AnimationUtils;
import android.view.animation.Interpolator;
import android.widget.FrameLayout;
import android.widget.TextView;

@@ -72,6 +74,8 @@ public class KeyguardBottomAreaView extends FrameLayout implements View.OnClickL
    private static final Intent INSECURE_CAMERA_INTENT =
            new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA);
    private static final Intent PHONE_INTENT = new Intent(Intent.ACTION_DIAL);
    private static final int DOZE_ANIMATION_STAGGER_DELAY = 48;
    private static final int DOZE_ANIMATION_ELEMENT_DURATION = 250;

    private KeyguardAffordanceView mCameraImageView;
    private KeyguardAffordanceView mPhoneImageView;
@@ -92,7 +96,7 @@ public class KeyguardBottomAreaView extends FrameLayout implements View.OnClickL
    private PhoneStatusBar mPhoneStatusBar;

    private final TrustDrawable mTrustDrawable;

    private final Interpolator mLinearOutSlowInInterpolator;
    private int mLastUnlockIconRes = 0;

    public KeyguardBottomAreaView(Context context) {
@@ -111,6 +115,8 @@ public class KeyguardBottomAreaView extends FrameLayout implements View.OnClickL
            int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
        mTrustDrawable = new TrustDrawable(mContext);
        mLinearOutSlowInInterpolator =
                AnimationUtils.loadInterpolator(context, android.R.interpolator.linear_out_slow_in);
    }

    private AccessibilityDelegate mAccessibilityDelegate = new AccessibilityDelegate() {
@@ -450,6 +456,35 @@ public class KeyguardBottomAreaView extends FrameLayout implements View.OnClickL
        }
    }

    public void startFinishDozeAnimation() {
        long delay = 0;
        if (mPhoneImageView.getVisibility() == View.VISIBLE) {
            startFinishDozeAnimationElement(mPhoneImageView, delay);
            delay += DOZE_ANIMATION_STAGGER_DELAY;
        }
        startFinishDozeAnimationElement(mLockIcon, delay);
        delay += DOZE_ANIMATION_STAGGER_DELAY;
        if (mCameraImageView.getVisibility() == View.VISIBLE) {
            startFinishDozeAnimationElement(mCameraImageView, delay);
        }
        mIndicationText.setAlpha(0f);
        mIndicationText.animate()
                .alpha(1f)
                .setInterpolator(mLinearOutSlowInInterpolator)
                .setDuration(NotificationPanelView.DOZE_ANIMATION_DURATION);
    }

    private void startFinishDozeAnimationElement(View element, long delay) {
        element.setAlpha(0f);
        element.setTranslationY(element.getHeight() / 2);
        element.animate()
                .alpha(1f)
                .translationY(0f)
                .setInterpolator(mLinearOutSlowInInterpolator)
                .setStartDelay(delay)
                .setDuration(DOZE_ANIMATION_ELEMENT_DURATION);
    }

    private final BroadcastReceiver mDevicePolicyReceiver = new BroadcastReceiver() {
        public void onReceive(Context context, Intent intent) {
            post(new Runnable() {
+51 −18
Original line number Diff line number Diff line
@@ -64,7 +64,7 @@ public class NotificationPanelView extends PanelView implements

    private static final int DOZE_BACKGROUND_COLOR = 0xff000000;
    private static final int TAG_KEY_ANIM = R.id.scrim;
    private static final long DOZE_BACKGROUND_ANIM_DURATION = ScrimController.ANIMATION_DURATION;
    public static final long DOZE_ANIMATION_DURATION = 700;

    private KeyguardAffordanceHelper mAfforanceHelper;
    private StatusBarHeaderView mHeader;
@@ -132,6 +132,7 @@ public class NotificationPanelView extends PanelView implements

    private Interpolator mFastOutSlowInInterpolator;
    private Interpolator mFastOutLinearInterpolator;
    private Interpolator mDozeAnimationInterpolator;
    private ObjectAnimator mClockAnimator;
    private int mClockAnimationTarget = -1;
    private int mTopPaddingAdjustment;
@@ -167,6 +168,8 @@ public class NotificationPanelView extends PanelView implements
    private boolean mQsTouchAboveFalsingThreshold;
    private int mQsFalsingThreshold;

    private float mKeyguardStatusBarAnimateAlpha = 1f;

    public NotificationPanelView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }
@@ -199,6 +202,8 @@ public class NotificationPanelView extends PanelView implements
                android.R.interpolator.fast_out_slow_in);
        mFastOutLinearInterpolator = AnimationUtils.loadInterpolator(getContext(),
                android.R.interpolator.fast_out_linear_in);
        mDozeAnimationInterpolator = AnimationUtils.loadInterpolator(getContext(),
                android.R.interpolator.linear_out_slow_in);
        mKeyguardBottomArea = (KeyguardBottomAreaView) findViewById(R.id.keyguard_bottom_area);
        mQsNavbarScrim = findViewById(R.id.qs_navbar_scrim);
        mAfforanceHelper = new KeyguardAffordanceHelper(this, getContext());
@@ -909,6 +914,8 @@ public class NotificationPanelView extends PanelView implements
        @Override
        public void run() {
            mKeyguardStatusBar.setVisibility(View.INVISIBLE);
            mKeyguardStatusBar.setAlpha(1f);
            mKeyguardStatusBarAnimateAlpha = 1f;
        }
    };

@@ -918,10 +925,31 @@ public class NotificationPanelView extends PanelView implements
                .setStartDelay(mStatusBar.getKeyguardFadingAwayDelay())
                .setDuration(mStatusBar.getKeyguardFadingAwayDuration()/2)
                .setInterpolator(PhoneStatusBar.ALPHA_OUT)
                .setUpdateListener(mStatusBarAnimateAlphaListener)
                .withEndAction(mAnimateKeyguardStatusBarInvisibleEndRunnable)
                .start();
    }

    private final ValueAnimator.AnimatorUpdateListener mStatusBarAnimateAlphaListener =
            new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator animation) {
            mKeyguardStatusBarAnimateAlpha = mKeyguardStatusBar.getAlpha();
        }
    };

    private void animateKeyguardStatusBarIn() {
        mKeyguardStatusBar.setVisibility(View.VISIBLE);
        mKeyguardStatusBar.setAlpha(0f);
        mKeyguardStatusBar.animate()
                .alpha(1f)
                .setStartDelay(0)
                .setDuration(DOZE_ANIMATION_DURATION)
                .setInterpolator(mDozeAnimationInterpolator)
                .setUpdateListener(mStatusBarAnimateAlphaListener)
                .start();
    }

    private final Runnable mAnimateKeyguardBottomAreaInvisibleEndRunnable = new Runnable() {
        @Override
        public void run() {
@@ -1387,7 +1415,8 @@ public class NotificationPanelView extends PanelView implements
        alphaNotifications = MathUtils.constrain(alphaNotifications, 0, 1);
        alphaNotifications = (float) Math.pow(alphaNotifications, 0.75);
        float alphaQsExpansion = 1 - Math.min(1, getQsExpansionFraction() * 2);
        mKeyguardStatusBar.setAlpha(Math.min(alphaNotifications, alphaQsExpansion));
        mKeyguardStatusBar.setAlpha(Math.min(alphaNotifications, alphaQsExpansion)
                * mKeyguardStatusBarAnimateAlpha);
        mKeyguardBottomArea.setAlpha(Math.min(1 - getQsExpansionFraction(), alphaNotifications));
        setQsTranslation(mQsExpansionHeight);
    }
@@ -1736,19 +1765,22 @@ public class NotificationPanelView extends PanelView implements
        return (1 - t) * start + t * end;
    }

    private void updateKeyguardStatusBarVisibility() {
        mKeyguardStatusBar.setVisibility(mKeyguardShowing && !mDozing ? VISIBLE : INVISIBLE);
    }

    public void setDozing(boolean dozing) {
    public void setDozing(boolean dozing, boolean animate) {
        if (dozing == mDozing) return;
        mDozing = dozing;
        if (mDozing) {
            setBackgroundColorAlpha(this, DOZE_BACKGROUND_COLOR, 0xff, false /*animate*/);
            setBackgroundColorAlpha(DOZE_BACKGROUND_COLOR, 0xff, false /*animate*/);
            mKeyguardStatusBar.setVisibility(View.INVISIBLE);
            mKeyguardBottomArea.setVisibility(View.INVISIBLE);
        } else {
            setBackgroundColorAlpha(this, DOZE_BACKGROUND_COLOR, 0, true /*animate*/);
            setBackgroundColorAlpha(DOZE_BACKGROUND_COLOR, 0, animate);
            mKeyguardBottomArea.setVisibility(View.VISIBLE);
            mKeyguardStatusBar.setVisibility(View.VISIBLE);
            if (animate) {
                animateKeyguardStatusBarIn();
                mKeyguardBottomArea.startFinishDozeAnimation();
            }
        }
        updateKeyguardStatusBarVisibility();
    }

    @Override
@@ -1756,21 +1788,21 @@ public class NotificationPanelView extends PanelView implements
        return mDozing;
    }

    private static void setBackgroundColorAlpha(final View target, int rgb, int targetAlpha,
    private void setBackgroundColorAlpha(int rgb, int targetAlpha,
            boolean animate) {
        int currentAlpha = getBackgroundAlpha(target);
        int currentAlpha = getBackgroundAlpha(this);
        if (currentAlpha == targetAlpha) {
            return;
        }
        final int r = Color.red(rgb);
        final int g = Color.green(rgb);
        final int b = Color.blue(rgb);
        Object runningAnim = target.getTag(TAG_KEY_ANIM);
        Object runningAnim = getTag(TAG_KEY_ANIM);
        if (runningAnim instanceof ValueAnimator) {
            ((ValueAnimator) runningAnim).cancel();
        }
        if (!animate) {
            target.setBackgroundColor(Color.argb(targetAlpha, r, g, b));
            setBackgroundColor(Color.argb(targetAlpha, r, g, b));
            return;
        }
        ValueAnimator anim = ValueAnimator.ofInt(currentAlpha, targetAlpha);
@@ -1778,18 +1810,19 @@ public class NotificationPanelView extends PanelView implements
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                int value = (int) animation.getAnimatedValue();
                target.setBackgroundColor(Color.argb(value, r, g, b));
                setBackgroundColor(Color.argb(value, r, g, b));
            }
        });
        anim.setDuration(DOZE_BACKGROUND_ANIM_DURATION);
        anim.setInterpolator(mDozeAnimationInterpolator);
        anim.setDuration(DOZE_ANIMATION_DURATION);
        anim.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                target.setTag(TAG_KEY_ANIM, null);
                setTag(TAG_KEY_ANIM, null);
            }
        });
        anim.start();
        target.setTag(TAG_KEY_ANIM, anim);
        setTag(TAG_KEY_ANIM, anim);
    }

    private static int getBackgroundAlpha(View view) {
+2 −4
Original line number Diff line number Diff line
@@ -3681,15 +3681,13 @@ public class PhoneStatusBar extends BaseStatusBar implements DemoMode,
        if (mState != StatusBarState.KEYGUARD && !mNotificationPanel.isDozing()) {
            return;
        }
        mNotificationPanel.setDozing(mDozing);
        mNotificationPanel.setDozing(mDozing, mScrimController.isPulsing() /*animate*/);
        if (mDozing) {
            mKeyguardBottomArea.setVisibility(View.INVISIBLE);
            mStackScroller.setDark(true, false /*animate*/);
        } else {
            mKeyguardBottomArea.setVisibility(View.VISIBLE);
            mStackScroller.setDark(false, false /*animate*/);
        }
        mScrimController.setDozing(mDozing);
        mScrimController.setDozing(mDozing, mScrimController.isPulsing() /*animate*/);
    }

    public void updateStackScrollerState(boolean goingToFullShade) {
Loading