2012-05-25 40 views
0

你好,我試圖暫停動畫繪製,但無法成功。在堆棧溢出的幫助下,我至少得到了animationDrawable end listener的幫助,這裏是它的代碼。是否有任何可能的方式,我可以暫停動畫繪製對象並啓動它從那裏已暫停......AnimationDrawable暫停?

public abstract class CustomAnimationDrawable extends AnimationDrawable{ 

    /** Handles the animation callback. */ 
    Handler mAnimationHandler; 
    Runnable r= new Runnable() { 

     @Override 
     public void run() { 
      // TODO Auto-generated method stub 
       onAnimationFinish(); 
     } 
    }; 

    public CustomAnimationDrawable(AnimationDrawable aniDrawable) { 
     /* Add each frame to our animation drawable */ 
     for (int i = 0; i < aniDrawable.getNumberOfFrames(); i++) { 
      this.addFrame(aniDrawable.getFrame(i), aniDrawable.getDuration(i)); 
     } 
    } 

    @Override 
    public void start() { 
     super.start(); 
     /* 
     * Call super.start() to call the base class start animation method. 
     * Then add a handler to call onAnimationFinish() when the total 
     * duration for the animation has passed 
     */ 
     mAnimationHandler = new Handler(); 
     mAnimationHandler.postDelayed(r, getTotalDuration()); 

    } 

    /** 
    * Gets the total duration of all frames. 
    * 
    * @return The total duration. 
    */ 
    public int getTotalDuration() { 

     int iDuration = 0; 

     for (int i = 0; i < this.getNumberOfFrames(); i++) { 
      iDuration += this.getDuration(i); 
     } 

     return iDuration; 
    } 

    /** 
    * Called when the animation finishes. 
    */ 
    abstract void onAnimationFinish(); 

    public void destroy() 
    { 


     mAnimationHandler.removeCallbacksAndMessages(r); 
     mAnimationHandler.removeCallbacksAndMessages(null); 


    } 

}

請請幫忙有什麼辦法,我可以暫停?

回答

7

我一直在環顧四周,似乎沒有辦法直接做到這一點。所有在AnimationDrawable中設置框架的變量和方法都是私有的。但是,您可以在暫停時獲取動畫所在幀的索引,然後通過從最後一幀播放的索引中迭代原始動畫來創建新動畫(然後重新開始並在動畫中添加其餘動畫是週期性的)。

我從一個基於XML的動畫循環開始,然後再添加一個暫停和恢復。以下是我最終做的事情,到目前爲止它工作得很好,首先列出相關變量。

private ImageView sphere; 
private AnimationDrawable sphereAnimation; 
private AnimationDrawable sphereResume; 
private AnimationDrawable activeAnimation; 
private Drawable currentFrame; 
private Drawable checkFrame; 
private int frameIndex; 

private void pause() 
{ 
    looping = false; 
    sphereResume = new AnimationDrawable(); 
    activeAnimation.stop(); 
    currentFrame = activeAnimation.getCurrent(); 

    frameLoop: 
    for(int i = 0; i < sphereAnimation.getNumberOfFrames(); i++) 
    { 
     checkFrame = activeAnimation.getFrame(i); 

     if(checkFrame == currentFrame) 
     { 
      frameIndex = i; 
      for(int k = frameIndex; k < activeAnimation.getNumberOfFrames(); k++) 
      { 
       Drawable frame = activeAnimation.getFrame(k); 
       sphereResume.addFrame(frame, 50); 
      } 
      for(int k = 0; k < frameIndex; k++) 
      { 
       Drawable frame = activeAnimation.getFrame(k); 
       sphereResume.addFrame(frame, 50); 
      } 
      activeAnimation = sphereResume; 
      sphere.setImageDrawable(activeAnimation); 
      sphere.invalidate(); 
      break frameLoop; 
     } 
    } 
} 

private void play() 
{ 
    looping = false; 
    activeAnimation.setOneShot(true); 
    activeAnimation.start(); 
} 

private void stop() 
{ 
    looping = false; 
    activeAnimation.stop(); 
    activeAnimation = sphereAnimation; 
    sphere.setImageDrawable(activeAnimation); 
} 

private void loop() 
{ 
    looping = true; 
    stopSoundEffect(); 
    activeAnimation.setOneShot(false); 
    activeAnimation.start(); 
} 
+0

完美地工作,非常感謝你! – Gustavo

+0

您可以請發佈完整的代碼,這裏的球體動畫的價值是什麼? –

0

Zorbert Crenshaw的方法很不錯,但它很複雜。

我有另一種解決方案(需要與try/catch環繞,因爲反射是不安全的)。

你可以叫getCurFrameFromAnimationDrawable保存停止動畫當前幀之前,並調用setCurFrameToAnimationDrawable從任意幀開始。

'30L'應該被替換爲你的參數持續時間。

private int getCurFrameFromAnimationDrawable(AnimationDrawable drawable){ 
    try { 
     Field mCurFrame = drawable.getClass().getDeclaredField("mCurFrame"); 
     mCurFrame.setAccessible(true); 
     return mCurFrame.getInt(drawable); 
    }catch (Exception ex){ 
     Log.e(AnimTool.class.getName(), "getCurFrameFromAnimationDrawable: Exception"); 
     return 0; 
    } 
} 

private void setCurFrameToAnimationDrawable(AnimationDrawable drawable, int curFrame){ 
    try { 
     Field mCurFrame = drawable.getClass().getDeclaredField("mCurFrame"); 
     mCurFrame.setAccessible(true); 
     mCurFrame.setInt(drawable, curFrame); 
     Class[] param = new Class[]{Runnable.class, long.class}; 
     Method method = Drawable.class.getDeclaredMethod("scheduleSelf", param); 
     method.setAccessible(true); 
     method.invoke(drawable, drawable, 30L); 
    }catch (Exception ex){ 
     Log.e(AnimTool.class.getName(), "setCurFrameToAnimationDrawable: Exception"); 
    } 
}