在Android中获取动画的变换矩阵

时间:2010-04-01 23:54:02

标签: android animation matrix transformation

我想获取动画的变换矩阵来计算动画视图的位置。

似乎Animation类有一个名为getTransformation的方法,可用于获取应用于视图的转换。

但是,如果我在开始动画之前使用getTransformation,我会获得单位矩阵。如果我这样使用它:

public void onAnimationEnd(Animation animation) {
    Transformation t = new Transformation();
    animation.getTransformation(animation.getDuration(), t);
}

程序进入infite循环,因为getTransformation似乎触发onAnimationEnd(为什么?)。

我应该如何使用getTransformation来获取动画的变换矩阵?还有另一种方法吗?

2 个答案:

答案 0 :(得分:0)

因为某些原因,这就是getTransformation的编码方式。

http://www.netmite.com/android/mydroid/1.5/frameworks/base/core/java/android/view/animation/Animation.java

看起来您可以检查hasEnded()以查看动画是否完整。尝试这样的事情:

public void onAnimationEnd(Animation animation)
{
   if ( animation.hasEnded() )
       return;

   Transformation t= new Transformation();
   animation.getTransformation(animation.getDuration(), t);
}

答案 1 :(得分:0)

当我想在上一个动画完成后为下一个动画获取getTransformation()时,我也遇到了这个问题,然后无限循环导致stackoverflow。

我从GrepCode分析了Android源代码的问题,代码低于getTransformation(),我从未发现任何会导致无限循环的问题,因为只调用onAnimationEnd(),它将mEnded设置为true。下次致电getTransformation()时,它应被if(!mEnded)屏蔽,但事实并非如此。

    if (expired) {
        if (mRepeatCount == mRepeated) {
            if (!mEnded) {
                mEnded = true;   //this is not real!!!
                if (mListener != null) {
                    mListener.onAnimationEnd(this);
                }
            }
        } else {
            if (mRepeatCount > 0) {
                mRepeated++;
            }

            if (mRepeatMode == REVERSE) {
                mCycleFlip = !mCycleFlip;
            }

            mStartTime = -1;
            mMore = true;

            if (mListener != null) {
                mListener.onAnimationRepeat(this);
            }
        }
    }

这段代码的接缝grepcode不正确。事实是eEnded = trueonAnimationEnd()之后被设置为:

    if (!mEnded) {
            if (mListener != null) {
                mListener.onAnimationEnd(this);
            }
            //it happen after onAnimationEnd(). cancel() is also does as this
            mEnded = true; 
        }

这应该解释为什么会发生无限循环。即使您检查animation.hasEnded()也无济于事,因为无法将mEnded设置为true。

我解决这个问题的方法是:
在监听器中设置标志以防范:

boolean needBlock = false;
public void onAnimationEnd(Animation animation)
{
   if ( needBlock ) return;

   needBlock = true;
   Transformation t= new Transformation();
   animation.getTransformation(animation.getDuration(), t);
}

清除AnimationListner。如果需要,我们可以在

之后退回
public void onAnimationEnd(Animation animation)
{
   animation.setAnimationListener(null);
   Transformation t= new Transformation();
   animation.getTransformation(animation.getDuration(), t);
   animation.setAnimationListener(this);
}