• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package com.android.launcher3.anim;
2 
3 import android.animation.Animator;
4 import android.animation.AnimatorListenerAdapter;
5 import android.animation.ValueAnimator;
6 import android.graphics.Outline;
7 import android.graphics.Rect;
8 import android.view.View;
9 import android.view.ViewOutlineProvider;
10 
11 import com.android.launcher3.Utilities;
12 
13 /**
14  * A {@link ViewOutlineProvider} that has helper functions to create reveal animations.
15  * This class should be extended so that subclasses can define the reveal shape as the
16  * animation progresses from 0 to 1.
17  */
18 public abstract class RevealOutlineAnimation extends ViewOutlineProvider {
19     protected Rect mOutline;
20     protected float mOutlineRadius;
21 
RevealOutlineAnimation()22     public RevealOutlineAnimation() {
23         mOutline = new Rect();
24     }
25 
26     /** Returns whether elevation should be removed for the duration of the reveal animation. */
shouldRemoveElevationDuringAnimation()27     abstract boolean shouldRemoveElevationDuringAnimation();
28     /** Sets the progress, from 0 to 1, of the reveal animation. */
setProgress(float progress)29     abstract void setProgress(float progress);
30 
createRevealAnimator(final View revealView, boolean isReversed)31     public ValueAnimator createRevealAnimator(final View revealView, boolean isReversed) {
32         ValueAnimator va =
33                 isReversed ? ValueAnimator.ofFloat(1f, 0f) : ValueAnimator.ofFloat(0f, 1f);
34         final float elevation = revealView.getElevation();
35 
36         va.addListener(new AnimatorListenerAdapter() {
37             private boolean mIsClippedToOutline;
38             private ViewOutlineProvider mOldOutlineProvider;
39 
40             public void onAnimationStart(Animator animation) {
41                 mIsClippedToOutline = revealView.getClipToOutline();
42                 mOldOutlineProvider = revealView.getOutlineProvider();
43 
44                 revealView.setOutlineProvider(RevealOutlineAnimation.this);
45                 revealView.setClipToOutline(true);
46                 if (shouldRemoveElevationDuringAnimation()) {
47                     revealView.setTranslationZ(-elevation);
48                 }
49             }
50 
51             public void onAnimationEnd(Animator animation) {
52                 revealView.setOutlineProvider(mOldOutlineProvider);
53                 revealView.setClipToOutline(mIsClippedToOutline);
54                 if (shouldRemoveElevationDuringAnimation()) {
55                     revealView.setTranslationZ(0);
56                 }
57             }
58 
59         });
60 
61         va.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
62             @Override
63             public void onAnimationUpdate(ValueAnimator arg0) {
64                 float progress = (Float) arg0.getAnimatedValue();
65                 setProgress(progress);
66                 revealView.invalidateOutline();
67                 if (!Utilities.ATLEAST_LOLLIPOP_MR1) {
68                     revealView.invalidate();
69                 }
70             }
71         });
72         return va;
73     }
74 
75     @Override
getOutline(View v, Outline outline)76     public void getOutline(View v, Outline outline) {
77         outline.setRoundRect(mOutline, mOutlineRadius);
78     }
79 
getRadius()80     public float getRadius() {
81         return mOutlineRadius;
82     }
83 
getOutline(Rect out)84     public void getOutline(Rect out) {
85         out.set(mOutline);
86     }
87 }
88