Android LayoutAnimation

LayoutAnimation:顾名思义,组件内动画,这里参考apidemo中的例子做学习记录。

用处

viewgroup添加或者删除子view时的过度动画,避免子view显示的生硬。

用例参考

com.example.android.apis.animation.LayoutAnimations

用法及注意事项

-API10 以上使用

1.简单用法
使用系统默认的animation
<GridLayout
    android:columnCount="4"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:id="@+id/gridContainer"
    android:animateLayoutChanges="true"
    />`
只要在你需要加上一个属性android:animateLayoutChanges="true",则此layout子view有变化时会有默认的过度动画,一般情况都可以满足我们的需求。

2.自定义animation:如果我们不想用系统默认的动画,那句需要自己来定义了。
    - 首先介绍使用方法:
    - 所有的动画属性都是针对LayoutTransition,llAnimContent.setLayoutTransition(transition)即可
  • LayoutTransition介绍:
    -This class enables automatic animations on layout changes in ViewGroup objects. To enable transitions for a layout container, create a LayoutTransition object and set it on any ViewGroup by calling setLayoutTransition(LayoutTransition). This will cause default animations to run whenever items are added to or removed from that container. To specify custom animations, use the setAnimator() method.
    详细了解:LayoutTransition

  • 四种场景

  • 一共四种类型的动画
    APPEARING ————- View本身的出现动画
    CHANGE_APPEARING ———– 由于新增了其他View而需要改变位置的动画
    DISAPPEARING ———– 消失动画
    CHANGE_DISAPPEARING ———– 由于移除了其他View而需要改变位置的动画
    例如:
    ObjectAnimator customAppearingAnim = ObjectAnimator.ofFloat(null, "translationX", -700, 0). setDuration(transition.getDuration(LayoutTransition.APPEARING));
    transition.setAnimator(LayoutTransition.APPEARING, customAppearingAnim);

    • 上段代码的就是设置了APPEARING—即layout addview时被添加view的动画,
      这里我设置了从左到有淡入。
    • 需要注意的是如果layout种本来就有其他的view 这时addview会出发CHANGE_APPEARING ,这里你只需要再定义相应的动画transition.setAnimator(LayoutTransition.CHANGE_APPEARING,anim)就OK了,当然,如果不想设置的话,也可以使用系统默认的偏移动画
  • 实战

    • 现在我有一个LinnerLayout,我需要每次addview时,view从左边底部进 来,removeview时 列表顶部的view淡出,有点类似直播聊天室的例子。
    • 针对LinnerLayout设置APPEARING ,DISAPPEARING 动画即可,随之发生的CHANGE_APPEARING ,CHANGE_DISAPPEARING 我们使用的默认的就好。
//  add
  transition = new LayoutTransition();
        transition.setDuration(1000);
        llAnimContent.setLayoutTransition(transition);
        ObjectAnimator customAppearingAnim = ObjectAnimator.ofFloat(null, "translationX", -700, 0).
                setDuration(transition.getDuration(LayoutTransition.APPEARING));
  transition.setAnimator(LayoutTransition.APPEARING, customAppearingAnim);
// Removing
   customDisappearingAnim = ObjectAnimator.ofFloat(null, "alpha", 1.0f, 0.0f).
         setDuration(transition.getDuration(LayoutTransition.DISAPPEARING));
   transition.setAnimator(LayoutTransition.DISAPPEARING, customDisappearingAnim);
  • 这里我实际的需求是当itemview 充满布局后,每次add 先让顶部的view消失,再由底部addview进来,所以对APPEARING 做了监听,针对firstItemView 做特殊的淡出动画
这 customAppearingAnim.addListener(new AnimatorListenerAdapter() {

            @Override
            public void onAnimationStart(Animator animation) {
                if (llAnimContent.getChildCount() >= itemMaxCount) {
                    llAnimContent.post(new Runnable() {
                        @Override
                        public void run() {
                            //第一条淡出动画
                            View firstItemView = llAnimContent.getChildAt(0);
                            if(firstItemView == null){
                                return;
                            }
                            //这里为了排除外层layout remove动画对本身动画的影响 先清空 DISAPPEARING 动作的动画
                            transition.setAnimator(LayoutTransition.DISAPPEARING, null);
                            ObjectAnimator alphaAnimator = ObjectAnimator.ofFloat(firstItemView, "alpha", 1.0f, 0.0f).
                                    setDuration(transition.getDuration(LayoutTransition.DISAPPEARING));
                            alphaAnimator.start();
                            alphaAnimator.addListener(new AnimatorListenerAdapter() {

                                @Override
                                public void onAnimationStart(Animator animation) {
                                }

                                @Override
                                public void onAnimationEnd(Animator animation) {
                                    llAnimContent.removeViewAt(0);
                                    transition.setAnimator(LayoutTransition.DISAPPEARING, customDisappearingAnim);
                                }

                                @Override
                                public void onAnimationCancel(Animator animation) {
                                    transition.setAnimator(LayoutTransition.DISAPPEARING, customDisappearingAnim);
                                }
                            });
                        }
                    });
                }
            }

            public void onAnimationEnd(Animator anim) {
                Log.i(TAG, "APPEARING...childcount: " + llAnimContent.getChildCount());
                View view = (View) ((ObjectAnimator) anim).getTarget();
                view.setTranslationX(0);
            }
        });
  • 另外有一点要写一下,APIDemos 提供的参考类中使用了
  • ` PropertyValuesHolder pvhLeft =
    PropertyValuesHolder.ofInt(“left”, 0, 1);
    PropertyValuesHolder pvhTop =
    PropertyValuesHolder.ofInt(“top”, 0, 1);
    PropertyValuesHolder pvhRight =
    PropertyValuesHolder.ofInt(“right”, 0, 1);
    PropertyValuesHolder pvhBottom =

    • 注:PropertyValuesHolder 是一个animation集合类,用于将多种动画柔和在一起。PropertyValuesHolder

    经个人测试,这四个属性括号内的值是像数(pix),动画执行的结果是改变自身getLeft,getRight,getTop,getBottom 的值,这几个属性容易改变view的大小,不推荐使用。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值