分别在XML文件、Java代码中实现动画效果 Animation(带示例)
1 android?动画
1.1动画结构图
?
Android动画
Animation(2D)
openGL(3D)
Tween
Frame
??
?
?
?
?
?
?
?????
?
?
1.2动画相关类
?????????????????????????????1.2.1 Animation?类及其子类Animation?类及其子类实现了各种动画效果,如平移、缩?放、旋转、改变透明度等。
Animation?是基类,他记录了动画的通用属性和方法。主要的属性包括动画持续时间、重复次、interpolator等。TranslateAnimation、RotateAnimation、AlphaAnimation?等是?Animation?的?子类,分别实现了平移、旋转、改变?Alpha?值等动画。
?????????????????????????????1.2.3?interpolator?类及其子类interpolator?定义了动画的变化速度,可以实现匀速、正加速、负加速、无规则变加速等;
interpolator?是基类,封装了所有?interpolator?的共同方法.LinearInerpolator、AccelerateInterpolator、DecelerateInterpolator、AccelerateDecelerateInterpolator、CycleInterpolator是?Interpolator?的子类,分别实现了匀速、加速、减速、变速、循环等效果。
?????????????????????????????1.2.3?Transformation?类?Transformation?记录了仿射矩阵?Matrix,动画每触发一次,会对原来的矩阵做一次运算,?View?的?Bitmap?与这个矩阵相乘就可实现相应的操作(旋转、平移、缩放等)。
?
?
?
?
?????
2 Tween动画
??????Tween?动画,通过对场景里的对象不断做图像变换(平移、缩放、旋转)产生动画效果。
?
?
Tween?动画
???????
?
?
?
实现方式
动画类型
??
XML
Translate
Alpha
Rotate
Scale
自定义动画
Java Code
??
?
?
?
?
2.1?在XML定义动画
alpha
渐变透明度动画效果
scale
渐变尺寸伸缩动画效果
translate
画面转换位置移动动画效果
rotate
画面转移旋转动画效果
?
定义的alpha从0.1(透明)到1(不透明)渐变,渐变时间为5000毫秒。
<alpha
android:fromAlpha="0.1"
android:toAlpha="1.0"
android:duration="5000"
/>
?
定义了旋转变换,从0度变化到360度(旋转一周),时间为1000毫秒,变换的中心点位控件的中心位置
<rotate
????????android:interpolator="@android:anim/accelerate_decelerate_interpolator"
???????
????????android:fromDegrees="0"
????????android:toDegrees="+360"
???????????????
????????android:pivotX="50%"
????????android:pivotY="50%"????
????????
????????android:duration="1000"
????????android:repeatCount="10000"
????????RepeatMode="1"
/>
?
定义X轴、Y轴从0.1到1逐渐放大(开始高度为正常大小的0.1然后逐渐放大到正常大小)。缩放持续的时间为2000毫秒,缩放的中心点(通过pivotX,pivotY定义)在控件的中间位置。
<scale
??????????android:interpolator="@android:anim/accelerate_decelerate_interpolator"
?????????
??????????android:fromXScale="0.1"
??????????android:toXScale="1.0"
?????????
??????????android:fromYScale="0.1"
??????????android:toYScale="1.0"
?????????
??????????android:pivotX="50%"
??????????android:pivotY="50%"
?????????
??????????android:fillAfter="false"
??????????android:duration="2000"?/>
?
定义了位置变换
<translate
????????android:fromXDelta="10"
????????android:toXDelta="200"
????????android:fromYDelta="10"
????????android:toYDelta="200"
????????android:duration="1000"
/>
?
2.2在Java Code定义动画
AlphaAnimation
渐变透明度动画效果
ScaleAnimation
渐变尺寸伸缩动画效果
TranslateAnimation
画面转换位置移动动画效果
RotateAnimation
画面转移旋转动画效果
//定义变量
private Animation myAnimation_Alpha;
private Animation myAnimation_Scale;
private Animation myAnimation_Translate;
private Animation myAnimation_Rotate;
?
myAnimation_Alpha=new AlphaAnimation(0.1f, 1.0f);
//第一个参数fromAlpha为 动画开始时候透明度
//第二个参数toAlpha为?动画结束时候透明度
?
myAnimation_Scale =new ScaleAnimation(0.0f, 1.4f, 0.0f, 1.4f,?Animation.RELATIVE_TO_SELF, 0.5f, Animation.RELATIVE_TO_SELF, 0.5f);
//第一个参数fromX为动画起始时?X坐标上的伸缩尺寸
//第二个参数toX为动画结束时?X坐标上的伸缩尺寸
//第三个参数fromY为动画起始时Y坐标上的伸缩尺寸
//第四个参数toY为动画结束时Y坐标上的伸缩尺寸
//第五个参数pivotXType为动画在X轴相对于物件位置类型
//第六个参数pivotXValue为动画相对于物件的X坐标的开始位置
//第七个参数pivotXType为动画在Y轴相对于物件位置类型
//第八个参数pivotYValue为动画相对于物件的Y坐标的开始位置
?
myAnimation_Translate=new TranslateAnimation(30.0f, -80.0f, 30.0f, 300.0f);
//第一个参数fromXDelta为动画起始时?X坐标上的移动位置
//第二个参数toXDelta为动画结束时?X坐标上的移动位置
//第三个参数fromYDelta为动画起始时Y坐标上的移动位置
//第四个参数toYDelta为动画结束时Y坐标上的移动位置
?
myAnimation_Rotate=new??RotateAnimation(0.0f,350.0f,Animation.RELATIVE_TO_SELF,0.5f, Animation.RELATIV E_TO_SELF, 0.5f);
//第一个参数fromDegrees为动画起始时的旋转角度
//第二个参数toDegrees为动画旋转到的角度
//第三个参数pivotXType为动画在X轴相对于物件位置类型
//第四个参数pivotXValue为动画相对于物件的X坐标的开始位
//第五个参数pivotXType为动画在Y轴相对于物件位置类型
//第六个参数pivotYValue为动画相对于物件的Y坐标的开始位置
?
2.3自定义动画
????除了以上4类动画外,在代码中继承android.view.animation.Animation类来实现自定义效果。通过重写Animation的applyTransformation(float interpolatedTime, Transformation t)函数来实现自定义动画效果。
?
????在绘制动画的过程中会反复的调用applyTransformation函数,每次调用参数interpolatedTime值都会变化,该参数从0渐?变为1,当该参数为1时表明动画结束。通过参数Transformation?来获取变换的矩阵(matrix),通过改变矩阵就可以实现各种复杂的效果。
?
自定义图片旋转效果动画代码。
class?ViewAnimation?extends?Animation
{??
????int?mCenterX;?
????int?mCenterY;??
????Camera?camera?=?new?Camera();??
????public?ViewAnimation()
????{??
?
????}??
?
@Override?
public?void?initialize(int?width,?int?height,?int?parentWidth,??
???int?parentHeight)
{??
???super.initialize(width, height, parentWidth, parentHeight);??
?
???mCenterX?= width/2;???
???mCenterY?= height/2;??
???setDuration(2500);??
???setFillAfter(true);???
??// setRepeatCount(100);
???setInterpolator(new?LinearInterpolator());??
}??
?
@Override?
protected?void?applyTransformation(float?interpolatedTime,??
??????Transformation t)
{??
???final?Matrix matrix = t.getMatrix();??
???camera.save();??
???camera.translate(0.0f, 0.0f, (1300 - 1300.0f * interpolatedTime));??
???camera.rotateY(360 * interpolatedTime);??
???camera.getMatrix(matrix);??
???matrix.preTranslate(-mCenterX, -mCenterY);??
???matrix.postTranslate(mCenterX,?mCenterY);??
???camera.restore();??
}??
}?
camera.translate(0.0f, 0.0f, (1300 - 1300.0f * interpolatedTime))在第一次调用的时候interpolatedTime值为0,相当于把ImageView在Z轴后移1300像素,?然后逐步的往前移动到0,同时camera.rotateY(360 * interpolatedTime)函数又把ImageView沿Y轴翻转360度
?
?
2.4动画实现
?在代码的一个activity中,将需要动画的控件与已定义的动画关联,开启动画
??????private?Animation?mAnimationXXX = null;//生明动画
???ImageView?mAnimImageX = null;//生明?ImageView控件(或者其它需要有动画的控件)
???mAnimImageX?= (ImageView)?this.findViewById(R.id.anim_imageX);//取得图片资源
???mAnimImageX.startAnimation(mAnimationXXX);//基于xml文件,开启动画
???mAnimImageX.startAnimation(new?ViewAnimation());//基于自定义控件,开启动画。
???
2.5图片旋转Demo
?
public?class?AnimationDemo?extends?Activity {
?????/** Called when the activity is first created. */
????????ImageView?mAnimImage;
???????
????????private?Animation??mAnimationAlpha?????=?null;
????????private?Animation??mAnimationScale?????=?null;
????????private?Animation??mAnimationTranslate?=?null;
????????private?Animation??mAnimationRotate????????=?null;???????
???@Override
?????public?void?onCreate(Bundle savedInstanceState) {
???????super.onCreate(savedInstanceState);
???????setContentView(R.layout.main);
??????
???????mAnimImage?= (ImageView)?this.findViewById(R.id.anim_image1);??
???
???????mAnimationAlpha?=????????????????AnimationUtils.loadAnimation(this,R.anim.alpha_animation);
???????mAnimationScale?=????AnimationUtils.loadAnimation(this,R.anim.scale_animation);
???????mAnimationTranslate?=????AnimationUtils.loadAnimation(this,R.anim.translate_animation);
???????mAnimationRotate?=???AnimationUtils.loadAnimation(this,R.anim.rotate_animation);
?????
???}
??
???public?boolean?onKeyUp(int?keyCode, KeyEvent event)
????{
???switch?( keyCode )
????????{
????????case?KeyEvent.KEYCODE_1:
???????
????????????mAnimImage.startAnimation(mAnimationAlpha);
???????????
????????????break;
????????case?KeyEvent.KEYCODE_2:
?
????????????mAnimImage.startAnimation(mAnimationScale);????
????????????break;
????????case?KeyEvent.KEYCODE_3:
????????????mAnimImage.startAnimation(mAnimationTranslate);
????????????break;
????????case?KeyEvent.KEYCODE_4:
????????????mAnimImage.startAnimation(?mAnimationRotate);
????????????break;
????????case?KeyEvent.KEYCODE_5:??
????????????mAnimImage.startAnimation(new?ViewAnimation());
????????????break;
????????}
????????return?true;
????}
???public?boolean?onKeyDown(int?keyCode, KeyEvent event)
????{
????????if?( keyCode ==??KeyEvent.KEYCODE_BACK)
????????{
????????????this.finish();
????????????return?true;
????????}
????????return?super.onKeyDown(keyCode, event);
????}
}
?
3??Frame动画
?
Frame?动画是顺序播放事先做好的图片。可以在XML Resource定义,也可以使AnimationDrawable中的API定义。
?
3.1Frame动画实现
定义XML文件
<?xml?version="1.0"?encoding="utf-8"?>
<animation-list?xmlns:android="http://schemas.android.com/apk/res/android"
????android:oneshot="false">
?
????<item?android:drawable="@drawable/a1"?android:duration="500"?/>
????<item?android:drawable="@drawable/a2"?android:duration="500"?/>
????<item?android:drawable="@drawable/a3"?android:duration="500"?/>
????<item?android:drawable="@drawable/a4"?android:duration="500"?/>
????<item?android:drawable="@drawable/a5"?android:duration="500"?/>
????<item?android:drawable="@drawable/a6"?android:duration="500"?/>
????<item?android:drawable="@drawable/a7"?android:duration="500"?/>
????<item?android:drawable="@drawable/a8"?android:duration="500"?/>
????<item?android:drawable="@drawable/a9"?android:duration="500"?/>
????<item?android:drawable="@drawable/a10"?android:duration="500"?/>
????<item?android:drawable="@drawable/a11"?android:duration="500"?/>
????<item?android:drawable="@drawable/a12"?android:duration="500"?/>
????<item?android:drawable="@drawable/a13"?android:duration="500"?/>
????<item?android:drawable="@drawable/a14"?android:duration="500"?/>
????<item?android:drawable="@drawable/a15"?android:duration="500"?/>?????
</animation-list>
?
定义动画类
public?class?GameView?extends?View
{
?
????private?AnimationDrawable??frameAnimation??=?null;
????Context?????????????????????mContext????????=?null;
????public?GameView(Context context)
????{
????????super(context);
???????
????????mContext?= context;
?
????????ImageView img =?new?ImageView(mContext);
???????
?
????????img.setBackgroundResource(R.anim.frameanimation);??????
???????
?
????????frameAnimation?= (AnimationDrawable) img.getBackground();
???????
?
????????frameAnimation.setOneShot(?false?);?
?
????????this.setBackgroundDrawable(frameAnimation);
????}
???
????public?void?onDraw(Canvas canvas)
????{
????????super.onDraw(canvas);
????}
???
????public?boolean?onKeyUp(int?keyCode, KeyEvent event)
????{
????????switch?( keyCode )
????????{
????????case?KeyEvent.KEYCODE_DPAD_UP:
?
????????????frameAnimation.start();
????????????break;
????????}
????????return?true;
????}
}
?
开启动画
public?class?Activity01?extends?Activity
{
????private?GameView???mGameView;
????/** Called when the activity is first created. */
????@Override
????public?void?onCreate(Bundle savedInstanceState)
????{
????????super.onCreate(savedInstanceState);
???????
????????mGameView?=?new?GameView(this);
???????
????????setContentView(mGameView);
????}
???
????public?boolean?onKeyUp(int?keyCode, KeyEvent event)
????{
????????if?(?mGameView?==?null?)
????????{
????????????return?false;
????????}
????????mGameView.onKeyUp(keyCode,event);
????????return?true;
????}
????public?boolean?onKeyDown(int?keyCode, KeyEvent event)
????{
????????if?(?mGameView?==?null?)
????????{
????????????return?false;
????????}
????????if?( keyCode ==??KeyEvent.KEYCODE_BACK)
????????{
????????????this.finish();
????????????return?true;
????????}
????????return?super.onKeyDown(keyCode, event);
????}
}