2014-03-27 66 views
3

我創建了一個類,它擴展了View,我將在它的佈局中引用它以在屏幕上繪製。自定義視圖中的Android動畫矩形

該類僅僅代表一個矩形,我願把長方形的長一路下降到0

構造:

public CardAnimationNew(Context context, AttributeSet attrs) { 
    super(context, attrs); 
    mPaint = new Paint(Paint.ANTI_ALIAS_FLAG); 
    mPaint.setColor(getResources().getColor(R.color.card_grey_underline)); 
} 

onMeasure:

@Override 
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 
    super.onMeasure(widthMeasureSpec, heightMeasureSpec); 

    if (mRectangle == null) { 
     mWidth = getMeasuredWidth(); 
     mHeight = getMeasuredHeight(); 
     mRectangle = new Rect(0, 0, mWidth, mHeight); 
     animateRectangle(); 
    } 
} 

animateRectangle :

private void animateRectangle() { 
    mObjectAnimator = ObjectAnimator.ofFloat(mRectangle, "width", 5); 
    mObjectAnimator.setDuration(1000); 
    mObjectAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
     @Override 
     public void onAnimationUpdate(ValueAnimator valueAnimator) { 
      invalidate(); 
     } 
    }); 
    mObjectAnimator.start(); 
} 

的onDraw:

@Override 
protected void onDraw(Canvas canvas) { 
    super.onDraw(canvas); 
    canvas.drawRect(mRectangle, mPaint); 
} 

問題是,Rect不是動畫的。它保持相同的長度。我哪裏錯了?

+0

更新的問題,包括缺少的方法(animateRectangle)。 – Subby

+0

發佈您的logcat,因爲Rect對象沒有setWidth方法 – pskink

回答

3

根據documentation該屬性需要在您應用動畫師的課程中使用setter。

該名稱將用於派生setter函數,該函數將被調用來設置動畫值。

的一點是,矩形不具有setWidth()或自動調用setHeight()

而且矩形不具有寬度和高度屬性,順便能夠繪製它的四個座標(topleftrightbottom),並達到你需要的效果。 (只考慮寬度爲Math.abs(left - right),高度爲Math.abs(top - bottom))。

爲了讓它在Rect上工作(或者像下面例子中的RectF - 如果你需要在Rect上使用它,只需使用int setter而不是浮點數),你需要通過添加setter的子類來創建它的子類物業則需要

private class AnimatableRectF extends RectF{ 
     public AnimatableRectF() { 
      super(); 
     } 

     public AnimatableRectF(float left, float top, float right, float bottom) { 
      super(left, top, right, bottom); 
     } 

     public AnimatableRectF(RectF r) { 
      super(r); 
     } 

     public AnimatableRectF(Rect r) { 
      super(r); 
     } 

     public void setTop(float top){ 
      this.top = top; 
     } 
     public void setBottom(float bottom){ 
      this.bottom = bottom; 
     } 
     public void setRight(float right){ 
      this.right = right; 
     } 
     public void setLeft(float left){ 
      this.left = left; 
     } 

    } 

然後你可以設置動畫以正常的方式...這裏的例子動畫稱爲mCurrentRect的AnimatableRectF進行翻譯:

float translateX = 50.0f; 
float translateY = 50.0f; 
ObjectAnimator animateLeft = ObjectAnimator.ofFloat(mCurrentRect, "left", mCurrentRect.left, mCurrentRect.left+translateX); 
ObjectAnimator animateRight = ObjectAnimator.ofFloat(mCurrentRect, "right", mCurrentRect.right, mCurrentRect.right+translateX); 
ObjectAnimator animateTop = ObjectAnimator.ofFloat(mCurrentRect, "top", mCurrentRect.top, mCurrentRect.top+translateY); 
ObjectAnimator animateBottom = ObjectAnimator.ofFloat(mCurrentRect, "bottom", mCurrentRect.bottom, mCurrentRect.bottom+translateY); 
animateBottom.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
         @Override 
         public void onAnimationUpdate(ValueAnimator valueAnimator) { 
          postInvalidate(); 
         } 
        }); 
AnimatorSet rectAnimation = new AnimatorSet(); 
rectAnimation.playTogether(animateLeft, animateRight, animateTop, animateBottom); 
rectAnimation.setDuration(1000).start(); 

我知道這是不是一個複製/粘貼解決方案重刑來解決你的問題,但我希望這段代碼將幫助你瞭解如何解決你的問題!

1

RectEvaluator是這樣做的方法。基本上你可以在Rect上使用一個ObjectAnimator,並給它一個開始和結束rect,它將評估它們之間的步驟。這僅僅是api> = 18。一個體面的寫法是http://cogitolearning.co.uk/?p=1451