1 /* 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 17 package com.android.dialer.animation; 18 19 import android.animation.Animator; 20 import android.animation.AnimatorListenerAdapter; 21 import android.animation.ValueAnimator; 22 import android.view.View; 23 import android.view.ViewPropertyAnimator; 24 import android.view.animation.Interpolator; 25 import android.view.animation.PathInterpolator; 26 27 public class AnimUtils { 28 29 public static final int DEFAULT_DURATION = -1; 30 public static final int NO_DELAY = 0; 31 32 public static final Interpolator EASE_IN = new PathInterpolator(0.0f, 0.0f, 0.2f, 1.0f); 33 public static final Interpolator EASE_OUT = new PathInterpolator(0.4f, 0.0f, 1.0f, 1.0f); 34 public static final Interpolator EASE_OUT_EASE_IN = new PathInterpolator(0.4f, 0, 0.2f, 1); 35 crossFadeViews(View fadeIn, View fadeOut, int duration)36 public static void crossFadeViews(View fadeIn, View fadeOut, int duration) { 37 fadeIn(fadeIn, duration); 38 fadeOut(fadeOut, duration); 39 } 40 fadeOut(View fadeOut, int duration)41 public static void fadeOut(View fadeOut, int duration) { 42 fadeOut(fadeOut, duration, null); 43 } 44 fadeOut(final View fadeOut, int durationMs, final AnimationCallback callback)45 public static void fadeOut(final View fadeOut, int durationMs, final AnimationCallback callback) { 46 fadeOut.setAlpha(1); 47 final ViewPropertyAnimator animator = fadeOut.animate(); 48 animator.cancel(); 49 animator 50 .alpha(0) 51 .withLayer() 52 .setListener( 53 new AnimatorListenerAdapter() { 54 @Override 55 public void onAnimationEnd(Animator animation) { 56 fadeOut.setVisibility(View.GONE); 57 if (callback != null) { 58 callback.onAnimationEnd(); 59 } 60 } 61 62 @Override 63 public void onAnimationCancel(Animator animation) { 64 fadeOut.setVisibility(View.GONE); 65 fadeOut.setAlpha(0); 66 if (callback != null) { 67 callback.onAnimationCancel(); 68 } 69 } 70 }); 71 if (durationMs != DEFAULT_DURATION) { 72 animator.setDuration(durationMs); 73 } 74 animator.start(); 75 } 76 fadeIn(View fadeIn, int durationMs)77 public static void fadeIn(View fadeIn, int durationMs) { 78 fadeIn(fadeIn, durationMs, NO_DELAY, null); 79 } 80 fadeIn( final View fadeIn, int durationMs, int delay, final AnimationCallback callback)81 public static void fadeIn( 82 final View fadeIn, int durationMs, int delay, final AnimationCallback callback) { 83 fadeIn.setAlpha(0); 84 final ViewPropertyAnimator animator = fadeIn.animate(); 85 animator.cancel(); 86 87 animator.setStartDelay(delay); 88 animator 89 .alpha(1) 90 .withLayer() 91 .setListener( 92 new AnimatorListenerAdapter() { 93 @Override 94 public void onAnimationStart(Animator animation) { 95 fadeIn.setVisibility(View.VISIBLE); 96 } 97 98 @Override 99 public void onAnimationCancel(Animator animation) { 100 fadeIn.setAlpha(1); 101 if (callback != null) { 102 callback.onAnimationCancel(); 103 } 104 } 105 106 @Override 107 public void onAnimationEnd(Animator animation) { 108 if (callback != null) { 109 callback.onAnimationEnd(); 110 } 111 } 112 }); 113 if (durationMs != DEFAULT_DURATION) { 114 animator.setDuration(durationMs); 115 } 116 animator.start(); 117 } 118 119 /** 120 * Scales in the view from scale of 0 to actual dimensions. 121 * 122 * @param view The view to scale. 123 * @param durationMs The duration of the scaling in milliseconds. 124 * @param startDelayMs The delay to applying the scaling in milliseconds. 125 */ scaleIn(final View view, int durationMs, int startDelayMs)126 public static void scaleIn(final View view, int durationMs, int startDelayMs) { 127 AnimatorListenerAdapter listener = 128 (new AnimatorListenerAdapter() { 129 @Override 130 public void onAnimationStart(Animator animation) { 131 view.setVisibility(View.VISIBLE); 132 } 133 134 @Override 135 public void onAnimationCancel(Animator animation) { 136 view.setScaleX(1); 137 view.setScaleY(1); 138 } 139 }); 140 scaleInternal( 141 view, 142 0 /* startScaleValue */, 143 1 /* endScaleValue */, 144 durationMs, 145 startDelayMs, 146 listener, 147 EASE_IN); 148 } 149 150 /** 151 * Scales out the view from actual dimensions to 0. 152 * 153 * @param view The view to scale. 154 * @param durationMs The duration of the scaling in milliseconds. 155 */ scaleOut(final View view, int durationMs)156 public static void scaleOut(final View view, int durationMs) { 157 AnimatorListenerAdapter listener = 158 new AnimatorListenerAdapter() { 159 @Override 160 public void onAnimationEnd(Animator animation) { 161 view.setVisibility(View.GONE); 162 } 163 164 @Override 165 public void onAnimationCancel(Animator animation) { 166 view.setVisibility(View.GONE); 167 view.setScaleX(0); 168 view.setScaleY(0); 169 } 170 }; 171 172 scaleInternal( 173 view, 174 1 /* startScaleValue */, 175 0 /* endScaleValue */, 176 durationMs, 177 NO_DELAY, 178 listener, 179 EASE_OUT); 180 } 181 scaleInternal( final View view, int startScaleValue, int endScaleValue, int durationMs, int startDelay, AnimatorListenerAdapter listener, Interpolator interpolator)182 private static void scaleInternal( 183 final View view, 184 int startScaleValue, 185 int endScaleValue, 186 int durationMs, 187 int startDelay, 188 AnimatorListenerAdapter listener, 189 Interpolator interpolator) { 190 view.setScaleX(startScaleValue); 191 view.setScaleY(startScaleValue); 192 193 final ViewPropertyAnimator animator = view.animate(); 194 animator.cancel(); 195 196 animator 197 .setInterpolator(interpolator) 198 .scaleX(endScaleValue) 199 .scaleY(endScaleValue) 200 .setListener(listener) 201 .withLayer(); 202 203 if (durationMs != DEFAULT_DURATION) { 204 animator.setDuration(durationMs); 205 } 206 animator.setStartDelay(startDelay); 207 208 animator.start(); 209 } 210 211 /** 212 * Animates a view to the new specified dimensions. 213 * 214 * @param view The view to change the dimensions of. 215 * @param newWidth The new width of the view. 216 * @param newHeight The new height of the view. 217 */ changeDimensions(final View view, final int newWidth, final int newHeight)218 public static void changeDimensions(final View view, final int newWidth, final int newHeight) { 219 ValueAnimator animator = ValueAnimator.ofFloat(0f, 1f); 220 221 final int oldWidth = view.getWidth(); 222 final int oldHeight = view.getHeight(); 223 final int deltaWidth = newWidth - oldWidth; 224 final int deltaHeight = newHeight - oldHeight; 225 226 animator.addUpdateListener( 227 new ValueAnimator.AnimatorUpdateListener() { 228 @Override 229 public void onAnimationUpdate(ValueAnimator animator) { 230 Float value = (Float) animator.getAnimatedValue(); 231 232 view.getLayoutParams().width = (int) (value * deltaWidth + oldWidth); 233 view.getLayoutParams().height = (int) (value * deltaHeight + oldHeight); 234 view.requestLayout(); 235 } 236 }); 237 animator.start(); 238 } 239 240 public static class AnimationCallback { 241 onAnimationEnd()242 public void onAnimationEnd() {} 243 onAnimationCancel()244 public void onAnimationCancel() {} 245 } 246 } 247