视图动画
代码形式:
代码创建并使用方式:
ScaleAnimation sa = new ScaleAnimation(0, 1, 0, 1, Animation.RELATIVE_TO_SELF, 0.5f,
Animation.RELATIVE_TO_SELF, 0.5f);
sa.setInterpolator(new BounceInterpolator());
sa.setDuration(300);
popview.startAnimation(sa);
AlphaAnimation ,RotateAniamtion ,ScaleAniamtion,TranslateAnimation
动画集合:
AnimationSet as.add(~~~~~)
xml形式:
创建xml文件并使用方式:
res/anim/filename.xml 文件
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:shareInterpolator="true">
<alpha
/>
<rotate
/>
<scale
/>
<translate
/>
</set>
使用方式:
Animation animation= AnimationUtils.loadAnimation(this,R.anim.test);
view.startAnimation(animation);
属性动画
弥补类动画变化之后实际属性没变。另外样式不只是4种 ,可对任意属性进行操作
objectAnimatior 创建方式,直接使用工厂类返回一个对象,方法参数,1作用对象,2属性名称。原理是通过了反射机制。
ObjectAnimator:
//相当于 set下的objectAnimator 标签
ObjectAnimator animator=ObjectAnimator.ofFloat(v,"translationX",300);
//属性是可以做的!
animator.setDuration(300);
animator.start();
AnimatorSet:
//动画集合对应xml set的根标签
AnimatorSet set=new AnimatorSet();
set.playTogether(ObjectAnimator.ofFloat(v,"rotationx",0,360),
ObjectAnimator.ofFloat(v,"rotationx",0,360),
ObjectAnimator.ofFloat(v,"translationX",0,90),
ObjectAnimator.ofFloat(v,"scaleX",1,1.5f)
ValuAnimation:
注意这个本身不提供任何动画效果,而是类似于一个插值器。 他不需要属性
//相当于set下的animator标签
ValueAnimator animator=ValueAnimator.ofFloat(0,100);
//和object的区别是动画可以不用作用在属性上,而采用帧监控方法进行处理
animator.setTarget(v);
animator.setDuration(1000).start();
//有点类似于定时监听,更像是一个数值发生器。
animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
button2.setTranslationY((Float) animation.getAnimatedValue());
}
});
XML文件方式:
创建方式:
res/animator/file name.xml
<set xmlns:android="http://schemas.android.com/apk/res/android"
android:ordering="together">
<!-- 顺序还是一起-->
<!--定义一个动画-->
<objectAnimator
android:propertyName="TranslationY"
android:duration="300"
android:valueTo="200"
/>
<!--animator 区别就是 没有属性名-->
</set>
使用方式:
AnimatorSet set= (AnimatorSet) AnimatorInflater.loadAnimator(MainActivity.this,R.animator.property_animator);
set.setTarget(v);
set.start();
封装属性:
(可能某些熟悉不是view自带的例如控件的大小,这时需要get,set方法给这个view对象写一个属性)
//把属性包装起来
private static class WrapperView{
private View mTarget;
public WrapperView(View target){
mTarget=target;
}
public int getWidth(){
return mTarget.getLayoutParams().width;
}
public void setWidth(int width){
mTarget.getLayoutParams().width=width;
mTarget.requestLayout();
}
}
animator监听器:
animator.addListener(new Animator.AnimatorListener() {
@Override
public void onAnimationStart(Animator animation) {
}
@Override
public void onAnimationEnd(Animator animation) {
}
@Override
public void onAnimationCancel(Animator animation) {
}
@Override
public void onAnimationRepeat(Animator animation) {
}
});
插值器:
插值器有多种系统的方式。(也可以自定义,需要矩阵变换,很麻烦!)
插值器,是对属性动画和view动画都起作用的东西。
1.继承Aniamation
2.重写两个方法:initialize 和applyTransformation方法
布局动画:
ViewGroup设置的动画,往往是在添加,和删除时会出现动画
eg:
listview 只需要设置animateLayoutChanges=”true“
就会有系统自带的动画效果
另外也可以通过LayoutAniationController定义子view 的过渡效果。
eg:
淡出
animation = new AlphaAnimation(0f, 1f);
animation.setDuration(500);
controller = new LayoutAnimationController(animation, 1f);
controller.setOrder(LayoutAnimationController.ORDER_NORMAL);
mListView.setLayoutAnimation(controller);
adapter.notifyDataSetInvalidated();
移出
animation = new TranslateAnimation(-50f, 0f, 0f, 0f);
animation.setDuration(500);
//1f为延时
controller = new LayoutAnimationController(animation, 1f);
controller.setOrder(LayoutAnimationController.ORDER_NORMAL);
mListView.setLayoutAnimation(controller);
adapter.notifyDataSetInvalidated();
例子(利用属性动画实现灵动菜单按钮):
准备工作
private boolean mFlag=true;
ArrayList<ImageView> mButtonViews=new ArrayList<>();
ImageView popbutton= (ImageView) findViewById(R.id.popButton);
ImageView popbutton1= (ImageView) findViewById(R.id.pop_botton1);
ImageView popbutton2= (ImageView) findViewById(R.id.pop_botton2);
ImageView popbutton3= (ImageView) findViewById(R.id.pop_botton3);
ImageView popbutton4= (ImageView) findViewById(R.id.pop_botton4);
mButtonViews.add(popbutton);
mButtonViews.add(popbutton1);
mButtonViews.add(popbutton2);
mButtonViews.add(popbutton3);
mButtonViews.add(popbutton4);
popbutton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(mFlag){
startAnim();
}
else {
closeAnim();
}
}
});
两个方法打开,和关闭,主要是依靠这个插值器。实现duang,duang的效果
public void startAnim(){
//设计一个灵动的菜单按钮
ObjectAnimator animator=ObjectAnimator.ofFloat(mButtonViews.get(0),"alpha",1F,0.5F);
ObjectAnimator animator1=ObjectAnimator.ofFloat(mButtonViews.get(1),"translationY",200F);
ObjectAnimator animator2=ObjectAnimator.ofFloat(mButtonViews.get(2),"translationX",200F);
ObjectAnimator animator3=ObjectAnimator.ofFloat(mButtonViews.get(3),"translationY",-200F);
ObjectAnimator animator4=ObjectAnimator.ofFloat(mButtonViews.get(4),"translationX",-200F);
AnimatorSet animatorSet=new AnimatorSet();
animatorSet.setDuration(300);
animatorSet.setInterpolator(new BounceInterpolator());
animatorSet.playTogether(animator,animator1,animator2,animator3,animator4);
animatorSet.start();
mFlag=false;
}
//
private void closeAnim() {
ObjectAnimator animator=ObjectAnimator.ofFloat(mButtonViews.get(0),"alpha",0.5F,1F);
ObjectAnimator animator1=ObjectAnimator.ofFloat(mButtonViews.get(1),"translationY",0);
ObjectAnimator animator2=ObjectAnimator.ofFloat(mButtonViews.get(2),"translationX",0);
ObjectAnimator animator3=ObjectAnimator.ofFloat(mButtonViews.get(3),"translationY",0);
ObjectAnimator animator4=ObjectAnimator.ofFloat(mButtonViews.get(4),"translationX",0);
AnimatorSet animatorSet=new AnimatorSet();
animatorSet.setDuration(300);
animatorSet.setInterpolator(new BounceInterpolator());
animatorSet.playTogether(animator,animator1,animator2,animator3,animator4);
animatorSet.start();
mFlag=true;
}
XML文件,就是把这几个控件通过Framelayout 叠加在一起。注意Framelaytout的大小