blob: 3eda3204d7a374943a59045d1762f5f4fad3165f [file] [log] [blame]
Jorim Jaggiecc798e2014-05-26 18:14:37 +02001/*
2 * Copyright (C) 2014 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License
15 */
16
17package com.android.systemui.statusbar.phone;
18
19import android.animation.Animator;
20import android.animation.AnimatorListenerAdapter;
Selim Cinekaac93252015-04-14 20:04:12 -070021import android.animation.PropertyValuesHolder;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020022import android.animation.ValueAnimator;
John Spurlockd06aa572014-09-10 10:40:49 -040023import android.content.Context;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020024import android.graphics.Color;
Selim Cinek6811d722016-01-19 17:53:12 -080025import android.graphics.Rect;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020026import android.view.View;
27import android.view.ViewTreeObserver;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020028import android.view.animation.DecelerateInterpolator;
29import android.view.animation.Interpolator;
Jorim Jaggi0d210f62015-07-10 14:24:44 -070030import android.view.animation.PathInterpolator;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020031
John Spurlockbf370992014-06-17 13:58:31 -040032import com.android.systemui.R;
Selim Cinekaac93252015-04-14 20:04:12 -070033import com.android.systemui.statusbar.ExpandableNotificationRow;
34import com.android.systemui.statusbar.NotificationData;
Selim Cineka0fad3b2014-09-19 17:20:05 +020035import com.android.systemui.statusbar.ScrimView;
Selim Cinekaac93252015-04-14 20:04:12 -070036import com.android.systemui.statusbar.policy.HeadsUpManager;
37import com.android.systemui.statusbar.stack.StackStateAnimator;
John Spurlockbf370992014-06-17 13:58:31 -040038
Jorim Jaggiecc798e2014-05-26 18:14:37 +020039/**
40 * Controls both the scrim behind the notifications and in front of the notifications (when a
41 * security method gets shown).
42 */
Selim Cinekaac93252015-04-14 20:04:12 -070043public class ScrimController implements ViewTreeObserver.OnPreDrawListener,
44 HeadsUpManager.OnHeadsUpChangedListener {
John Spurlock8b12f222014-09-09 11:54:11 -040045 public static final long ANIMATION_DURATION = 220;
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -070046 public static final Interpolator KEYGUARD_FADE_OUT_INTERPOLATOR
47 = new PathInterpolator(0f, 0, 0.7f, 1f);
Jorim Jaggiecc798e2014-05-26 18:14:37 +020048 private static final float SCRIM_BEHIND_ALPHA = 0.62f;
Jorim Jaggie5716222015-05-14 14:13:20 -070049 private static final float SCRIM_BEHIND_ALPHA_KEYGUARD = 0.45f;
Jorim Jaggi76a16232014-08-08 17:00:47 +020050 private static final float SCRIM_BEHIND_ALPHA_UNLOCKING = 0.2f;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020051 private static final float SCRIM_IN_FRONT_ALPHA = 0.75f;
John Spurlockbf370992014-06-17 13:58:31 -040052 private static final int TAG_KEY_ANIM = R.id.scrim;
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -070053 private static final int TAG_KEY_ANIM_TARGET = R.id.scrim_target;
Selim Cinek5104a6d2015-12-18 18:38:31 -080054 private static final int TAG_START_ALPHA = R.id.scrim_alpha_start;
55 private static final int TAG_END_ALPHA = R.id.scrim_alpha_end;
John Spurlockbf370992014-06-17 13:58:31 -040056
Xiaohui Chen5da71352016-02-22 10:04:41 -080057 protected final ScrimView mScrimBehind;
Selim Cineka0fad3b2014-09-19 17:20:05 +020058 private final ScrimView mScrimInFront;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020059 private final UnlockMethodCache mUnlockMethodCache;
Selim Cinekaac93252015-04-14 20:04:12 -070060 private final View mHeadsUpScrim;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020061
Xiaohui Chen4dab4b52016-03-07 12:31:14 -080062 private float mScrimBehindAlpha = SCRIM_BEHIND_ALPHA;
63 private float mScrimBehindAlphaKeyguard = SCRIM_BEHIND_ALPHA_KEYGUARD;
64 private float mScrimBehindAlphaUnlocking = SCRIM_BEHIND_ALPHA_UNLOCKING;
65
Xiaohui Chen5da71352016-02-22 10:04:41 -080066 protected boolean mKeyguardShowing;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020067 private float mFraction;
68
69 private boolean mDarkenWhileDragging;
Xiaohui Chen5da71352016-02-22 10:04:41 -080070 protected boolean mBouncerShowing;
Jorim Jaggi0d210f62015-07-10 14:24:44 -070071 private boolean mWakeAndUnlocking;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020072 private boolean mAnimateChange;
73 private boolean mUpdatePending;
Jorim Jaggi2fbad7b2014-05-26 22:38:00 +020074 private boolean mExpanding;
Jorim Jaggie29b2db2014-05-30 23:17:03 +020075 private boolean mAnimateKeyguardFadingOut;
76 private long mDurationOverride = -1;
77 private long mAnimationDelay;
78 private Runnable mOnAnimationFinished;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020079 private final Interpolator mInterpolator = new DecelerateInterpolator();
Jorim Jaggi048af1f2014-11-11 22:51:10 +010080 private boolean mDozing;
81 private float mDozeInFrontAlpha;
82 private float mDozeBehindAlpha;
83 private float mCurrentInFrontAlpha;
84 private float mCurrentBehindAlpha;
Selim Cinekaac93252015-04-14 20:04:12 -070085 private float mCurrentHeadsUpAlpha = 1;
Selim Cinek684a4422015-04-15 16:18:39 -070086 private int mPinnedHeadsUpCount;
Selim Cinekaac93252015-04-14 20:04:12 -070087 private float mTopHeadsUpDragAmount;
88 private View mDraggedHeadsUpView;
Selim Cinek37c110f2015-05-22 12:38:44 -070089 private boolean mForceHideScrims;
Jorim Jaggiab45a212015-08-20 16:59:44 -070090 private boolean mSkipFirstFrame;
Selim Cinek372d1bd2015-08-14 13:19:37 -070091 private boolean mDontAnimateBouncerChanges;
Adrian Roos5f72c922016-03-08 15:54:26 -080092 private boolean mKeyguardFadingOutInProgress;
Jorim Jaggiecc798e2014-05-26 18:14:37 +020093
Selim Cinek25503252016-03-03 15:31:43 -080094 public ScrimController(ScrimView scrimBehind, ScrimView scrimInFront, View headsUpScrim) {
Jorim Jaggiecc798e2014-05-26 18:14:37 +020095 mScrimBehind = scrimBehind;
96 mScrimInFront = scrimInFront;
Selim Cinekaac93252015-04-14 20:04:12 -070097 mHeadsUpScrim = headsUpScrim;
John Spurlockd06aa572014-09-10 10:40:49 -040098 final Context context = scrimBehind.getContext();
99 mUnlockMethodCache = UnlockMethodCache.getInstance(context);
Selim Cinekaac93252015-04-14 20:04:12 -0700100 updateHeadsUpScrim(false);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200101 }
102
103 public void setKeyguardShowing(boolean showing) {
104 mKeyguardShowing = showing;
105 scheduleUpdate();
106 }
107
Xiaohui Chen4dab4b52016-03-07 12:31:14 -0800108 public void setShowScrimBehind(boolean show) {
109 if (show) {
110 mScrimBehindAlpha = SCRIM_BEHIND_ALPHA;
111 mScrimBehindAlphaKeyguard = SCRIM_BEHIND_ALPHA_KEYGUARD;
112 mScrimBehindAlphaUnlocking = SCRIM_BEHIND_ALPHA_UNLOCKING;
113 } else {
114 mScrimBehindAlpha = 0;
115 mScrimBehindAlphaKeyguard = 0;
116 mScrimBehindAlphaUnlocking = 0;
117 }
118 scheduleUpdate();
119 }
120
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200121 public void onTrackingStarted() {
Jorim Jaggi2fbad7b2014-05-26 22:38:00 +0200122 mExpanding = true;
Selim Cineke8bae622015-07-15 13:24:06 -0700123 mDarkenWhileDragging = !mUnlockMethodCache.canSkipBouncer();
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200124 }
125
Jorim Jaggi2fbad7b2014-05-26 22:38:00 +0200126 public void onExpandingFinished() {
127 mExpanding = false;
128 }
129
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200130 public void setPanelExpansion(float fraction) {
Jorim Jaggi93439da2014-06-30 23:53:39 +0200131 if (mFraction != fraction) {
132 mFraction = fraction;
133 scheduleUpdate();
Selim Cinek131c1e22015-05-11 19:04:49 -0700134 if (mPinnedHeadsUpCount != 0) {
135 updateHeadsUpScrim(false);
136 }
Jorim Jaggi93439da2014-06-30 23:53:39 +0200137 }
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200138 }
139
140 public void setBouncerShowing(boolean showing) {
141 mBouncerShowing = showing;
Selim Cinek372d1bd2015-08-14 13:19:37 -0700142 mAnimateChange = !mExpanding && !mDontAnimateBouncerChanges;
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200143 scheduleUpdate();
144 }
145
Jorim Jaggi0d210f62015-07-10 14:24:44 -0700146 public void setWakeAndUnlocking() {
147 mWakeAndUnlocking = true;
148 scheduleUpdate();
149 }
150
Jorim Jaggiab45a212015-08-20 16:59:44 -0700151 public void animateKeyguardFadingOut(long delay, long duration, Runnable onAnimationFinished,
152 boolean skipFirstFrame) {
Jorim Jaggi0d210f62015-07-10 14:24:44 -0700153 mWakeAndUnlocking = false;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200154 mAnimateKeyguardFadingOut = true;
155 mDurationOverride = duration;
156 mAnimationDelay = delay;
157 mAnimateChange = true;
Jorim Jaggiab45a212015-08-20 16:59:44 -0700158 mSkipFirstFrame = skipFirstFrame;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200159 mOnAnimationFinished = onAnimationFinished;
160 scheduleUpdate();
Jorim Jaggiab45a212015-08-20 16:59:44 -0700161
162 // No need to wait for the next frame to be drawn for this case - onPreDraw will execute
163 // the changes we just scheduled.
164 onPreDraw();
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200165 }
166
Selim Cinekedd32b82015-06-23 22:05:58 -0400167 public void abortKeyguardFadingOut() {
168 if (mAnimateKeyguardFadingOut) {
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700169 endAnimateKeyguardFadingOut(true /* force */);
Selim Cinekedd32b82015-06-23 22:05:58 -0400170 }
171 }
172
Jorim Jaggidbc3dce2014-08-01 01:16:36 +0200173 public void animateGoingToFullShade(long delay, long duration) {
174 mDurationOverride = duration;
175 mAnimationDelay = delay;
176 mAnimateChange = true;
177 scheduleUpdate();
178 }
179
Selim Cinek5104a6d2015-12-18 18:38:31 -0800180 public void animateNextChange() {
181 mAnimateChange = true;
182 }
183
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100184 public void setDozing(boolean dozing) {
Jorim Jaggi0d210f62015-07-10 14:24:44 -0700185 if (mDozing != dozing) {
186 mDozing = dozing;
187 scheduleUpdate();
188 }
John Spurlockbf370992014-06-17 13:58:31 -0400189 }
190
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100191 public void setDozeInFrontAlpha(float alpha) {
192 mDozeInFrontAlpha = alpha;
193 updateScrimColor(mScrimInFront);
John Spurlockd06aa572014-09-10 10:40:49 -0400194 }
195
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100196 public void setDozeBehindAlpha(float alpha) {
197 mDozeBehindAlpha = alpha;
198 updateScrimColor(mScrimBehind);
John Spurlockbf370992014-06-17 13:58:31 -0400199 }
200
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100201 public float getDozeBehindAlpha() {
202 return mDozeBehindAlpha;
Jeff Brown4d69e222014-09-18 15:27:50 -0700203 }
204
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100205 public float getDozeInFrontAlpha() {
206 return mDozeInFrontAlpha;
John Spurlockbf370992014-06-17 13:58:31 -0400207 }
208
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200209 private void scheduleUpdate() {
210 if (mUpdatePending) return;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200211
212 // Make sure that a frame gets scheduled.
213 mScrimBehind.invalidate();
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200214 mScrimBehind.getViewTreeObserver().addOnPreDrawListener(this);
215 mUpdatePending = true;
216 }
217
Xiaohui Chen5da71352016-02-22 10:04:41 -0800218 protected void updateScrims() {
Selim Cinek37c110f2015-05-22 12:38:44 -0700219 if (mAnimateKeyguardFadingOut || mForceHideScrims) {
Selim Cinekbaa23272014-07-08 18:01:07 +0200220 setScrimInFrontColor(0f);
221 setScrimBehindColor(0f);
Jorim Jaggi0d210f62015-07-10 14:24:44 -0700222 } else if (mWakeAndUnlocking) {
223
224 // During wake and unlock, we first hide everything behind a black scrim, which then
225 // gets faded out from animateKeyguardFadingOut.
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700226 if (mDozing) {
227 setScrimInFrontColor(0f);
228 setScrimBehindColor(1f);
229 } else {
230 setScrimInFrontColor(1f);
231 setScrimBehindColor(0f);
232 }
John Spurlock8b12f222014-09-09 11:54:11 -0400233 } else if (!mKeyguardShowing && !mBouncerShowing) {
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200234 updateScrimNormal();
235 setScrimInFrontColor(0);
236 } else {
237 updateScrimKeyguard();
238 }
239 mAnimateChange = false;
240 }
241
242 private void updateScrimKeyguard() {
Jorim Jaggi2fbad7b2014-05-26 22:38:00 +0200243 if (mExpanding && mDarkenWhileDragging) {
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200244 float behindFraction = Math.max(0, Math.min(mFraction, 1));
245 float fraction = 1 - behindFraction;
Jorim Jaggi76a16232014-08-08 17:00:47 +0200246 fraction = (float) Math.pow(fraction, 0.8f);
247 behindFraction = (float) Math.pow(behindFraction, 0.8f);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200248 setScrimInFrontColor(fraction * SCRIM_IN_FRONT_ALPHA);
Xiaohui Chen4dab4b52016-03-07 12:31:14 -0800249 setScrimBehindColor(behindFraction * mScrimBehindAlphaKeyguard);
Jorim Jaggi2fbad7b2014-05-26 22:38:00 +0200250 } else if (mBouncerShowing) {
251 setScrimInFrontColor(SCRIM_IN_FRONT_ALPHA);
252 setScrimBehindColor(0f);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200253 } else {
Jorim Jaggi76a16232014-08-08 17:00:47 +0200254 float fraction = Math.max(0, Math.min(mFraction, 1));
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200255 setScrimInFrontColor(0f);
Jorim Jaggi76a16232014-08-08 17:00:47 +0200256 setScrimBehindColor(fraction
Xiaohui Chen4dab4b52016-03-07 12:31:14 -0800257 * (mScrimBehindAlphaKeyguard - mScrimBehindAlphaUnlocking)
258 + mScrimBehindAlphaUnlocking);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200259 }
260 }
261
262 private void updateScrimNormal() {
263 float frac = mFraction;
264 // let's start this 20% of the way down the screen
265 frac = frac * 1.2f - 0.2f;
266 if (frac <= 0) {
267 setScrimBehindColor(0);
268 } else {
269 // woo, special effects
270 final float k = (float)(1f-0.5f*(1f-Math.cos(3.14159f * Math.pow(1f-frac, 2f))));
Xiaohui Chen4dab4b52016-03-07 12:31:14 -0800271 setScrimBehindColor(k * mScrimBehindAlpha);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200272 }
273 }
274
275 private void setScrimBehindColor(float alpha) {
276 setScrimColor(mScrimBehind, alpha);
277 }
278
279 private void setScrimInFrontColor(float alpha) {
280 setScrimColor(mScrimInFront, alpha);
281 if (alpha == 0f) {
282 mScrimInFront.setClickable(false);
283 } else {
284
John Spurlock8b12f222014-09-09 11:54:11 -0400285 // Eat touch events (unless dozing).
286 mScrimInFront.setClickable(!mDozing);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200287 }
288 }
289
Selim Cinekaac93252015-04-14 20:04:12 -0700290 private void setScrimColor(View scrim, float alpha) {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800291 updateScrim(mAnimateChange, scrim, alpha, getCurrentScrimAlpha(scrim));
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200292 }
293
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100294 private float getDozeAlpha(View scrim) {
295 return scrim == mScrimBehind ? mDozeBehindAlpha : mDozeInFrontAlpha;
296 }
297
298 private float getCurrentScrimAlpha(View scrim) {
Selim Cinekaac93252015-04-14 20:04:12 -0700299 return scrim == mScrimBehind ? mCurrentBehindAlpha
300 : scrim == mScrimInFront ? mCurrentInFrontAlpha
301 : mCurrentHeadsUpAlpha;
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100302 }
303
304 private void setCurrentScrimAlpha(View scrim, float alpha) {
305 if (scrim == mScrimBehind) {
306 mCurrentBehindAlpha = alpha;
Selim Cinekaac93252015-04-14 20:04:12 -0700307 } else if (scrim == mScrimInFront) {
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100308 mCurrentInFrontAlpha = alpha;
Selim Cinekaac93252015-04-14 20:04:12 -0700309 } else {
310 alpha = Math.max(0.0f, Math.min(1.0f, alpha));
311 mCurrentHeadsUpAlpha = alpha;
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200312 }
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100313 }
314
Selim Cinekaac93252015-04-14 20:04:12 -0700315 private void updateScrimColor(View scrim) {
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100316 float alpha1 = getCurrentScrimAlpha(scrim);
Selim Cinekaac93252015-04-14 20:04:12 -0700317 if (scrim instanceof ScrimView) {
318 float alpha2 = getDozeAlpha(scrim);
319 float alpha = 1 - (1 - alpha1) * (1 - alpha2);
320 ((ScrimView) scrim).setScrimColor(Color.argb((int) (alpha * 255), 0, 0, 0));
321 } else {
322 scrim.setAlpha(alpha1);
323 }
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100324 }
325
Selim Cinekaac93252015-04-14 20:04:12 -0700326 private void startScrimAnimation(final View scrim, float target) {
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100327 float current = getCurrentScrimAlpha(scrim);
328 ValueAnimator anim = ValueAnimator.ofFloat(current, target);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200329 anim.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
330 @Override
331 public void onAnimationUpdate(ValueAnimator animation) {
Jorim Jaggi048af1f2014-11-11 22:51:10 +0100332 float alpha = (float) animation.getAnimatedValue();
333 setCurrentScrimAlpha(scrim, alpha);
334 updateScrimColor(scrim);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200335 }
336 });
Jorim Jaggi16423aa2014-10-28 11:42:58 +0100337 anim.setInterpolator(getInterpolator());
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200338 anim.setStartDelay(mAnimationDelay);
339 anim.setDuration(mDurationOverride != -1 ? mDurationOverride : ANIMATION_DURATION);
340 anim.addListener(new AnimatorListenerAdapter() {
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200341 @Override
342 public void onAnimationEnd(Animator animation) {
343 if (mOnAnimationFinished != null) {
344 mOnAnimationFinished.run();
345 mOnAnimationFinished = null;
Adrian Roos5f72c922016-03-08 15:54:26 -0800346 mKeyguardFadingOutInProgress = false;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200347 }
John Spurlockbf370992014-06-17 13:58:31 -0400348 scrim.setTag(TAG_KEY_ANIM, null);
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700349 scrim.setTag(TAG_KEY_ANIM_TARGET, null);
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200350 }
351 });
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200352 anim.start();
Adrian Roos5f72c922016-03-08 15:54:26 -0800353 if (mAnimateKeyguardFadingOut) {
354 mKeyguardFadingOutInProgress = true;
355 }
Jorim Jaggiab45a212015-08-20 16:59:44 -0700356 if (mSkipFirstFrame) {
357 anim.setCurrentPlayTime(16);
358 }
John Spurlockbf370992014-06-17 13:58:31 -0400359 scrim.setTag(TAG_KEY_ANIM, anim);
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700360 scrim.setTag(TAG_KEY_ANIM_TARGET, target);
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200361 }
362
Jorim Jaggi16423aa2014-10-28 11:42:58 +0100363 private Interpolator getInterpolator() {
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700364 return mAnimateKeyguardFadingOut ? KEYGUARD_FADE_OUT_INTERPOLATOR : mInterpolator;
Jorim Jaggi16423aa2014-10-28 11:42:58 +0100365 }
366
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200367 @Override
368 public boolean onPreDraw() {
369 mScrimBehind.getViewTreeObserver().removeOnPreDrawListener(this);
370 mUpdatePending = false;
Selim Cinek372d1bd2015-08-14 13:19:37 -0700371 if (mDontAnimateBouncerChanges) {
372 mDontAnimateBouncerChanges = false;
373 }
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200374 updateScrims();
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200375 mDurationOverride = -1;
376 mAnimationDelay = 0;
Jorim Jaggiab45a212015-08-20 16:59:44 -0700377 mSkipFirstFrame = false;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200378
379 // Make sure that we always call the listener even if we didn't start an animation.
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700380 endAnimateKeyguardFadingOut(false /* force */);
Selim Cinekedd32b82015-06-23 22:05:58 -0400381 return true;
382 }
383
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700384 private void endAnimateKeyguardFadingOut(boolean force) {
Selim Cinekedd32b82015-06-23 22:05:58 -0400385 mAnimateKeyguardFadingOut = false;
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700386 if ((force || (!isAnimating(mScrimInFront) && !isAnimating(mScrimBehind)))
387 && mOnAnimationFinished != null) {
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200388 mOnAnimationFinished.run();
389 mOnAnimationFinished = null;
Adrian Roos5f72c922016-03-08 15:54:26 -0800390 mKeyguardFadingOutInProgress = false;
Jorim Jaggie29b2db2014-05-30 23:17:03 +0200391 }
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200392 }
John Spurlockbf370992014-06-17 13:58:31 -0400393
Jorim Jaggi83eb6bb2015-08-17 17:38:58 -0700394 private boolean isAnimating(View scrim) {
395 return scrim.getTag(TAG_KEY_ANIM) != null;
396 }
397
Selim Cinek25503252016-03-03 15:31:43 -0800398 public void setDrawBehindAsSrc(boolean asSrc) {
Selim Cineka0fad3b2014-09-19 17:20:05 +0200399 mScrimBehind.setDrawAsSrc(asSrc);
400 }
Selim Cinekaac93252015-04-14 20:04:12 -0700401
402 @Override
John Spurlockb349af572015-04-29 12:24:19 -0400403 public void onHeadsUpPinnedModeChanged(boolean inPinnedMode) {
Selim Cinekaac93252015-04-14 20:04:12 -0700404 }
405
406 @Override
Selim Cinek684a4422015-04-15 16:18:39 -0700407 public void onHeadsUpPinned(ExpandableNotificationRow headsUp) {
408 mPinnedHeadsUpCount++;
409 updateHeadsUpScrim(true);
410 }
411
412 @Override
413 public void onHeadsUpUnPinned(ExpandableNotificationRow headsUp) {
414 mPinnedHeadsUpCount--;
415 if (headsUp == mDraggedHeadsUpView) {
416 mDraggedHeadsUpView = null;
417 mTopHeadsUpDragAmount = 0.0f;
Selim Cinekaac93252015-04-14 20:04:12 -0700418 }
419 updateHeadsUpScrim(true);
420 }
421
422 @Override
Selim Cinek684a4422015-04-15 16:18:39 -0700423 public void onHeadsUpStateChanged(NotificationData.Entry entry, boolean isHeadsUp) {
Selim Cinekaac93252015-04-14 20:04:12 -0700424 }
425
426 private void updateHeadsUpScrim(boolean animate) {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800427 updateScrim(animate, mHeadsUpScrim, calculateHeadsUpAlpha(), mCurrentHeadsUpAlpha);
428 }
429
430 private void updateScrim(boolean animate, View scrim, float alpha, float currentAlpha) {
Adrian Roos5f72c922016-03-08 15:54:26 -0800431 if (mKeyguardFadingOutInProgress) {
432 return;
433 }
434
Selim Cinek5104a6d2015-12-18 18:38:31 -0800435 ValueAnimator previousAnimator = StackStateAnimator.getChildTag(scrim,
Selim Cinekaac93252015-04-14 20:04:12 -0700436 TAG_KEY_ANIM);
437 float animEndValue = -1;
438 if (previousAnimator != null) {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800439 if (animate || alpha == currentAlpha) {
Selim Cinekaac93252015-04-14 20:04:12 -0700440 previousAnimator.cancel();
Selim Cinek737bff32015-05-08 16:08:35 -0700441 } else {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800442 animEndValue = StackStateAnimator.getChildTag(scrim, TAG_END_ALPHA);
Selim Cinekaac93252015-04-14 20:04:12 -0700443 }
Selim Cinekaac93252015-04-14 20:04:12 -0700444 }
Selim Cinek5104a6d2015-12-18 18:38:31 -0800445 if (alpha != currentAlpha && alpha != animEndValue) {
Selim Cinekaac93252015-04-14 20:04:12 -0700446 if (animate) {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800447 startScrimAnimation(scrim, alpha);
448 scrim.setTag(TAG_START_ALPHA, currentAlpha);
449 scrim.setTag(TAG_END_ALPHA, alpha);
Selim Cinekaac93252015-04-14 20:04:12 -0700450 } else {
451 if (previousAnimator != null) {
Selim Cinek5104a6d2015-12-18 18:38:31 -0800452 float previousStartValue = StackStateAnimator.getChildTag(scrim,
453 TAG_START_ALPHA);
454 float previousEndValue = StackStateAnimator.getChildTag(scrim,
455 TAG_END_ALPHA);
Selim Cinekaac93252015-04-14 20:04:12 -0700456 // we need to increase all animation keyframes of the previous animator by the
457 // relative change to the end value
458 PropertyValuesHolder[] values = previousAnimator.getValues();
459 float relativeDiff = alpha - previousEndValue;
460 float newStartValue = previousStartValue + relativeDiff;
461 values[0].setFloatValues(newStartValue, alpha);
Selim Cinek5104a6d2015-12-18 18:38:31 -0800462 scrim.setTag(TAG_START_ALPHA, newStartValue);
463 scrim.setTag(TAG_END_ALPHA, alpha);
Selim Cinekaac93252015-04-14 20:04:12 -0700464 previousAnimator.setCurrentPlayTime(previousAnimator.getCurrentPlayTime());
465 } else {
466 // update the alpha directly
Selim Cinek5104a6d2015-12-18 18:38:31 -0800467 setCurrentScrimAlpha(scrim, alpha);
468 updateScrimColor(scrim);
Selim Cinekaac93252015-04-14 20:04:12 -0700469 }
470 }
471 }
472 }
473
Selim Cinek684a4422015-04-15 16:18:39 -0700474 /**
475 * Set the amount the current top heads up view is dragged. The range is from 0 to 1 and 0 means
476 * the heads up is in its resting space and 1 means it's fully dragged out.
477 *
478 * @param draggedHeadsUpView the dragged view
479 * @param topHeadsUpDragAmount how far is it dragged
480 */
Selim Cinekaac93252015-04-14 20:04:12 -0700481 public void setTopHeadsUpDragAmount(View draggedHeadsUpView, float topHeadsUpDragAmount) {
482 mTopHeadsUpDragAmount = topHeadsUpDragAmount;
483 mDraggedHeadsUpView = draggedHeadsUpView;
484 updateHeadsUpScrim(false);
485 }
486
487 private float calculateHeadsUpAlpha() {
Selim Cinek131c1e22015-05-11 19:04:49 -0700488 float alpha;
Selim Cinek684a4422015-04-15 16:18:39 -0700489 if (mPinnedHeadsUpCount >= 2) {
Selim Cinek131c1e22015-05-11 19:04:49 -0700490 alpha = 1.0f;
Selim Cinek684a4422015-04-15 16:18:39 -0700491 } else if (mPinnedHeadsUpCount == 0) {
Selim Cinek131c1e22015-05-11 19:04:49 -0700492 alpha = 0.0f;
Selim Cinekaac93252015-04-14 20:04:12 -0700493 } else {
Selim Cinek131c1e22015-05-11 19:04:49 -0700494 alpha = 1.0f - mTopHeadsUpDragAmount;
Selim Cinekaac93252015-04-14 20:04:12 -0700495 }
Selim Cinek131c1e22015-05-11 19:04:49 -0700496 float expandFactor = (1.0f - mFraction);
497 expandFactor = Math.max(expandFactor, 0.0f);
498 return alpha * expandFactor;
Selim Cinekaac93252015-04-14 20:04:12 -0700499 }
Selim Cinek37c110f2015-05-22 12:38:44 -0700500
501 public void forceHideScrims(boolean hide) {
502 mForceHideScrims = hide;
503 mAnimateChange = false;
504 scheduleUpdate();
505 }
Selim Cinek372d1bd2015-08-14 13:19:37 -0700506
507 public void dontAnimateBouncerChangesUntilNextFrame() {
508 mDontAnimateBouncerChanges = true;
509 }
Selim Cinek6811d722016-01-19 17:53:12 -0800510
511 public void setExcludedBackgroundArea(Rect area) {
512 mScrimBehind.setExcludedArea(area);
513 }
Selim Cinekd35c2792016-01-21 13:20:57 -0800514
515 public int getScrimBehindColor() {
516 return mScrimBehind.getScrimColorWithAlpha();
517 }
518
519 public void setScrimBehindChangeRunnable(Runnable changeRunnable) {
520 mScrimBehind.setChangeRunnable(changeRunnable);
521 }
Jorim Jaggiecc798e2014-05-26 18:14:37 +0200522}