Question

I'm using a runnable in my Android app to update a countdown timer, as shown in the code below. It appears to work but I noticed my timer takes a few seconds longer than expected. For example, if it's supposed to count down 3 minutes, it takes 3 minutes and 5 seconds. I tried using a timer in a service to manage the countdown display in the main activity. The timer/service worked as expected.

Why doesn't runnable/postDelayed() run for the correct amount of time? Is postDelayed() timing reliable? The runnable decrements a variable then uses it to update an EditText with setText(). Does setText() take too long (a small fraction of a second), so the runnable really runs every 1.x seconds?

Handler handler = new Handler();
Runnable r = new Runnable() {
   public void run() {
      // decrement the time remaining and update the display
      handler.postDelayed(this, 1000);
   }
};
...
// start the runnable
handler.postDelayed(r, 1000);
Was it helpful?

Solution

Your code is kinda sorta designed to be inaccurate because you are not accounting for the time taken by the guts of the runnable. You might get improved results by doing something like

public void run(){  
    startTime = System.currentTimeMillis();  
    // compare expectedTime to startTime and compensate  
    // <guts of runnable goes here>
    // now wrap it up...
        delay = 1000 - (System.currentTimeMillis() - startTime);  
    if (delay < 0)  
        delay = 0;
    expectedTime = System.currentTimeMillies() + delay;
    handler.postDelayed(this, delay);  
}

OTHER TIPS

What about using CountDownTimer? I used this for same tasks several times and haven’t met this kind of problem.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top