2011-04-21 14 views

Respuesta

25

Agregaría algo al controlador onTick para guardar el progreso del temporizador en su clase (queda el número de milisegundos).

En el método onPause() para la actividad call cancel() en el temporizador.

En el método onResume() para la actividad, cree un nuevo temporizador con el número de milisegundos guardado restante.

+0

De su análisis de la fuente countDownTimer, esta es la mejor sugerencia. Siempre que su intervalo active el onTick() con la frecuencia suficiente, podrá hacerlo con una cantidad mínima de tiempo extra una vez reiniciado. – Maximus

+0

¡Gracias, acabo de probarlo y parece funcionar bastante bien! – sfrider0

+0

hola, ¿dónde escribiste el método onpause() y onresume()? – RaagaSudha

16

No es necesario crear un nuevo temporizador, simplemente configure millisUntilFinished = total. Por ejemplo

private CountDownTimer cdTimer; 
private long total = 30000; 

     ... 
     toggleButton.setOnClickListener(new View.OnClickListener() { 
      public void onClick(View view){ 
       if(toggleButton.isChecked()) { 
        startCountDownTimer(); 
       }else{ 
        cdTimer.cancel(); 
       } 
      } 
     }); 
     ... 

    private void startCountDownTimer() { 
     cdTimer = new CountDownTimer(total, 1000) { 
      public void onTick(long millisUntilFinished) { 
       //update total with the remaining time left 
       total = millisUntilFinished; 
       nTimeLabel.setText("seconds remaining: " + millisUntilFinished/ 1000); 
      } 
      public void onFinish() { 
       nTimeLabel.setText("done!"); 
      } 
     }.start(); 
    } 
+6

Su línea 'cdTimer = new CountDownTimer (total, 1000) {' en realidad está creando un nuevo temporizador:/ –

25

Puede utilizar pause() para ponerlo en pausa y luego iniciar o reanudar la countDownTimer llamando start().

/** 
* This class uses the native CountDownTimer to 
* create a timer which could be paused and then 
* started again from the previous point. You can 
* provide implementation for onTick() and onFinish() 
* then use it in your projects. 
*/ 
public abstract class CountDownTimerPausable { 
    long millisInFuture = 0; 
    long countDownInterval = 0; 
    long millisRemaining = 0; 

    CountDownTimer countDownTimer = null; 

    boolean isPaused = true; 

    public CountDownTimerPausable(long millisInFuture, long countDownInterval) { 
     super(); 
     this.millisInFuture = millisInFuture; 
     this.countDownInterval = countDownInterval; 
     this.millisRemaining = this.millisInFuture; 
    } 
    private void createCountDownTimer(){ 
     countDownTimer = new CountDownTimer(millisRemaining,countDownInterval) { 

      @Override 
      public void onTick(long millisUntilFinished) { 
       millisRemaining = millisUntilFinished; 
       CountDownTimerPausable.this.onTick(millisUntilFinished); 

      } 

      @Override 
      public void onFinish() { 
       CountDownTimerPausable.this.onFinish(); 

      } 
     }; 
    } 
    /** 
    * Callback fired on regular interval. 
    * 
    * @param millisUntilFinished The amount of time until finished. 
    */ 
    public abstract void onTick(long millisUntilFinished); 
    /** 
    * Callback fired when the time is up. 
    */ 
    public abstract void onFinish(); 
    /** 
    * Cancel the countdown. 
    */ 
    public final void cancel(){ 
     if(countDownTimer!=null){ 
      countDownTimer.cancel(); 
     } 
     this.millisRemaining = 0; 
    } 
    /** 
    * Start or Resume the countdown. 
    * @return CountDownTimerPausable current instance 
    */ 
    public synchronized final CountDownTimerPausable start(){ 
     if(isPaused){ 
      createCountDownTimer(); 
      countDownTimer.start(); 
      isPaused = false; 
     } 
     return this; 
    } 
    /** 
    * Pauses the CountDownTimerPausable, so it could be resumed(start) 
    * later from the same point where it was paused. 
    */ 
    public void pause()throws IllegalStateException{ 
     if(isPaused==false){ 
      countDownTimer.cancel(); 
     } else{ 
      throw new IllegalStateException("CountDownTimerPausable is already in pause state, start counter before pausing it."); 
     } 
     isPaused = true; 
    } 
    public boolean isPaused() { 
     return isPaused; 
    } 
} 
+0

Clase fina, pero el temporizador no llama a 'onTick' si permanece tiempo menor que Intervalo pero aún no 0 –

1

Esto debe ser exactamente lo que estás buscando. Fuente es this Gist.

package alt.android.os; 

import android.os.Handler; 
import android.os.SystemClock; 
import android.os.Message; 

public abstract class CountDownTimer { 

/** 
* Millis since epoch when alarm should stop. 
*/ 
private final long mMillisInFuture; 

/** 
* The interval in millis that the user receives callbacks 
*/ 
private final long mCountdownInterval; 

private long mStopTimeInFuture; 

private long mPauseTime; 

private boolean mCancelled = false; 

private boolean mPaused = false; 

/** 
* @param millisInFuture The number of millis in the future from the call 
* to {@link #start()} until the countdown is done and {@link #onFinish()} 
* is called. 
* @param countDownInterval The interval along the way to receive 
* {@link #onTick(long)} callbacks. 
*/ 
public CountDownTimer(long millisInFuture, long countDownInterval) { 
    mMillisInFuture = millisInFuture; 
    mCountdownInterval = countDownInterval; 
} 

/** 
* Cancel the countdown. 
* 
* Do not call it from inside CountDownTimer threads 
*/ 
public final void cancel() { 
    mHandler.removeMessages(MSG); 
    mCancelled = true; 
} 

/** 
* Start the countdown. 
*/ 
public synchronized final CountDownTimer start() { 
    if (mMillisInFuture <= 0) { 
     onFinish(); 
     return this; 
    } 
    mStopTimeInFuture = SystemClock.elapsedRealtime() + mMillisInFuture; 
    mHandler.sendMessage(mHandler.obtainMessage(MSG)); 
    mCancelled = false; 
    mPaused = false; 
    return this; 
} 

/** 
* Pause the countdown. 
*/ 
public long pause() { 
    mPauseTime = mStopTimeInFuture - SystemClock.elapsedRealtime(); 
    mPaused = true; 
    return mPauseTime; 
} 

/** 
* Resume the countdown. 
*/ 
public long resume() { 
    mStopTimeInFuture = mPauseTime + SystemClock.elapsedRealtime(); 
    mPaused = false; 
    mHandler.sendMessage(mHandler.obtainMessage(MSG)); 
    return mPauseTime; 
} 

/** 
* Callback fired on regular interval. 
* @param millisUntilFinished The amount of time until finished. 
*/ 
public abstract void onTick(long millisUntilFinished); 

/** 
* Callback fired when the time is up. 
*/ 
public abstract void onFinish(); 


private static final int MSG = 1; 


// handles counting down 
private Handler mHandler = new Handler() { 

    @Override 
    public void handleMessage(Message msg) { 

     synchronized (CountDownTimer.this) { 
      if (!mPaused) { 
       final long millisLeft = mStopTimeInFuture - SystemClock.elapsedRealtime(); 

       if (millisLeft <= 0) { 
        onFinish(); 
       } else if (millisLeft < mCountdownInterval) { 
        // no tick, just delay until done 
        sendMessageDelayed(obtainMessage(MSG), millisLeft); 
       } else { 
        long lastTickStart = SystemClock.elapsedRealtime(); 
        onTick(millisLeft); 

        // take into account user's onTick taking time to execute 
        long delay = lastTickStart + mCountdownInterval - SystemClock.elapsedRealtime(); 

        // special case: user's onTick took more than interval to 
        // complete, skip to next interval 
        while (delay < 0) delay += mCountdownInterval; 

        if (!mCancelled) { 
         sendMessageDelayed(obtainMessage(MSG), delay); 
        } 
       } 
      } 
     } 
    } 
}; 
} 
0

puede probar a usar Hourglass

Hourglass hourglass = new Hourglass(50000, 1000) { 
     @Override 
     public void onTimerTick(long timeRemaining) { 
      // Update UI 
      Toast.show(MainActivity.this, String.valueOf(timeRemaining), Toast.LENGTH_SHORT).show(); 
     } 

     @Override 
     public void onTimerFinish() { 
      // Timer finished 
      Toast.show(MainActivity.this, "Timer finished", Toast.LENGTH_SHORT).show(); 


     } 
    }; 

Uso hourglass.startTimer(); para iniciar el temporizador.

Tiene métodos de ayuda que permiten pausar y reanudar el temporizador.

hourglass.pauseTimer(); 

Y

hourglass.resumeTimer(); 
Cuestiones relacionadas