2013-01-12 119 views
1

我有一個屬性動畫,但它不光滑,即我在動畫中跳轉。我嘗試使用動畫器的參數,例如插值器,持續時間和幀延遲,但無法獲得平滑的效果。有沒有人有一些技巧/例子?這裏是我當前的代碼來設置動畫:製作流暢的動畫

rotationAnimator=new ObjectAnimator(); 
rotationAnimator.setTarget(rotationController); 
rotationAnimator.setPropertyName("mapRotation"); 
rotationAnimator.setInterpolator(new LinearInterpolator()); 
ValueAnimator.setFrameDelay(24); 
rotationAnimator.setDuration(ROTATION_DURATION); 
rotationAnimator.setRepeatCount(ValueAnimator.INFINITE); 
rotationAnimator.setRepeatMode(ValueAnimator.RESTART); 

(還有以setFloatValues一個電話,但在後面的代碼來了,我纔開始動畫)

編輯:有人問我要顯示什麼我的動畫,所以在這裏它是:

這是從動畫得到值的setter函數:

public void setMapRotation(float rotationDegrees) 
{ 
    if ((rotationAnimator!=null)&&(rotationAnimator.isRunning())) 
     rotationAnimator.cancel(); 
    rotationDegrees%=360; 
    if (rotationDegrees<0) rotationDegrees+=360; 
    rotationView.setRotationDegrees(rotationDegrees); 
    if (rotationDegrees!=oldRotationDegrees) 
    { 
     notifyRotationListeners(); 
     oldRotationDegrees=rotationDegrees; 
    } 
} 

如果你在看代碼,你會看到有這麼得到另一個函數調用(setRotationDegrees),所以在這裏它是:

public void setRotationDegrees(float rotationDegrees) 
{ 
    this.rotationDegrees=rotationDegrees%360; 
    if (this.rotationDegrees<0) this.rotationDegrees+=360; 
    Log.i("MapView","View degrees: " + this.rotationDegrees); 
    invalidate(); 
} 

這就是失效後會發生什麼:

@Override protected void dispatchDraw(Canvas canvas) 
{ 
    Log.i("MapView","Redrawing"); 
    int saveCount=canvas.save(Canvas.MATRIX_SAVE_FLAG); 
    canvas.rotate(rotationDegrees,getWidth()/2,getHeight()/2); 
    canvas.setDrawFilter(drawFilter); 
    canvas.getMatrix(rotationMatrix); 
    super.dispatchDraw(canvas); 
    canvas.restoreToCount(saveCount); 
} 

我不知道是否有什麼特別沉重這裏,但我可能是錯的...

回答

0

在動畫中間跳轉更可能是由rotateController類中的某個東西引起的,即接收動畫值「mapRotation」。或者它可能與您的佈局有關。

我會想象有一些相當激烈的,內存或CPU明智的,這是造成的動盪。

如果您的動畫有很多佈局,那麼這可能是原因。如果在你的代碼中有很多的findViewByID會因爲你的動畫而被調用,那麼這會導致速度減慢。

如果你只是動畫一個簡單的圖像,那麼我不完全確定問題會是什麼。

就我個人而言,我認爲你的代碼看起來不錯,或許會顯示/描述你的動畫。與畫布動畫的知識

[編輯] 我有限的,所以我剛剛看了一下你是如何使用canvas.save()和canvas.restoreToCount(),我從來沒有見過的。

這一切看起來不錯,雖然我發現奇怪的是,幾個教程旋轉畫布而不是球形圖像來創建旋轉。儘管如此,我發現改善動畫效果的唯一參考是以下link中的一條評論,建議使用postInvalidateOnAnimation()。不知道在哪裏,也許而不是invalidate()。

+0

謝謝,請參閱我上面的編輯。 – user940016

+0

我個人不喜歡旋轉方法,我的直覺說它過度。不知道它是否適用於您,但我可能會以某種方式查看使用精靈,例如http://p-xr.com/android-tutorial-2d-canvas-graphics/不同之處在於您調整精靈而不是繪製在圖形中的畫布。 – Emile

1

定義一個AnimatorSet並設置插值它可以幫助您解決問題:

rotationAnimator=new ObjectAnimator(); 
rotationAnimator.setTarget(rotationController); 
rotationAnimator.setPropertyName("mapRotation"); 
ValueAnimator.setFrameDelay(24); 
rotationAnimator.setDuration(ROTATION_DURATION); 
rotationAnimator.setRepeatCount(ValueAnimator.INFINITE); 
rotationAnimator.setRepeatMode(ValueAnimator.RESTART); 

AnimatorSet animatorSet = new AnimatorSet(); 
animatorSet.getChildAnimations().add(rotationAnimator); 
animatorSet.setInterpolator(new LinearInterpolator()); 
... 
animatorSet.start(); 
+1

你能解釋一下AnimatorSet如何讓動畫更流暢嗎?據我所知,它只是用於將幾個動畫分組和同步在一起,但我只有一個動畫... – user940016

+0

事實上,你只有一個動畫,但我希望你的AnimatorSet的性能會有所提高,因爲你正在重複動畫永遠。 (你試過了嗎?你有同樣的結果嗎?) – ben75

1

我直接添加硬件加速到我的動畫視圖,視圖容器解決(myViewContainer - 在我的情況下的RelativeLayout) :

if(!myViewContainer.isHardwareAccelerated()) 
{ 
    myViewContainer.setLayerType(View.LAYER_TYPE_HARDWARE, null); 
    myAnimatedView1.setLayerType(View.LAYER_TYPE_HARDWARE, null); 
    myAnimatedView2.setLayerType(View.LAYER_TYPE_HARDWARE, null); 
}