Android CountDownTimer - android

When writing :
CountDownTimer timer = new CountDownTimer(1000, 100)
{
#Override
public void onTick(long l)
{
}
#Override
public void onFinish()
{
};
}.start();
are we actually starting a new thread that handles ticks? If not, what is really happening?

CountDownTimer's implementation uses Handler and sendMessageDelayed(), so no background thread is needed. This does mean that the timer will not update if you are tying up the main application thread elsewhere in your code.

Definition from multiple publications, tried and tested:
"Another timer is provided with the built-in class CountDownTimer.This encapsulates the creation of a background thread and the handler queuing into a convenient class call..."

Related

How can i handle my Looper in an OnClick method to run a function with delay?

I would like to be able to run my specific method in background through a looper in an on click event, is this the right way to do this?
myThread = new LooperThread();
myThread.start();
upload.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
}
});
stop.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
myThread.handler.post(new Runnable() {
#Override
public void run() {
//my methods
}
});
}
});
And my Looper Class:
class LooperThread extends Thread {
Handler handler;
public void run() {
Looper.prepare();
handler = new Handler();
Looper.loop();
}
}
If it is,
the problem is that in this way, i don't understand why the system don't recognize "handler" while i typing: "myThread.handler.post.." and run the methods.
Otherwise, can you help me on making this?
I am sorry if i made mistakes while making the question, but it's my first time here :)``
Welcome to Stack Overflow.
I would like to be able to run my specific method in background through a looper in an on click event, is this the right way to do this?
Your code works, but I couldn't say it's the right way to do it. Like #tynn mentioned, a HandlerThread might be a better option.
If it is, the problem is that in this way, i don't understand why the system don't recognize "handler" while i typing: "myThread.handler.post.." and run the methods.
Otherwise, can you help me on making this?
If I understood your problem, it's an access issue. Your handler seems unaccessible since it's declared as package-private. You could make your handler visible this way:
// Should this class be public or package-private?
public class LooperThread extends Thread {
private Handler handler;
public Handler getHandler() {
return handler;
}
// ...
}
And you will be able to reference the handler like this:
myThread.getHandler().post(...);
UPDATE
You can delay a Runnable execution this way:
// Delay execution of a Runnable task by 5000 milliseconds.
myThread.getHandler().postDelayed(myDelayedRunnable, 5000);

Handler.postDelayed(Runnable) vs CountdownTimer

Sometimes we need to delay a code before it runs.
This is doable by the Handler.postDelayed(Runnable) or CountdownTimer.
Which one is better in terms of performance?
See the sample code below
Handler
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
//DO SOMETHING
}
}, 1000);
CountDownTimer
new CountDownTimer(1000, 1000) {
public void onFinish() {
//DO SOMETHING
}
public void onTick(long millisUntilFinished) {}
}.start();
The Handler should offer you better performances as CountDownTimer contains itself a Handler as you can see here.
I agree that Handler is offering a better performance. But on a side note, you should keep in mind that CountDownTimer object will be destroyed after completed. A Handler will continue to exist after finished. If you only need a temporary timer then CountDownTimer is preferable. Otherwise, use a Handler.
Use Handler,Android Handler is Good.
See Here, What Others say About Handler

Taking a picture with 2 secs of delay

Is there a way to take a picture two seconds after the Camera.takePicture method is invoked? For some reason, I do not want to use handler/timer to schedule the invocation of takePicture.
Precisely, I would like to use a different solution than the following one:
final Handler handler = new Handler();
Timer t = new Timer();
t.schedule(new TimerTask() {
public void run() {
handler.post(new Runnable() {
public void run() {
<here takePicture is invoked>
}
});
}
}, 2000);
You could use AlarmManager with a PendingIntent and handle taking the camera capture in your Activity.onNewIntent method, but it is a very confusing solution for what you are trying to solve (a much better use of AlarmManager is to schedule tasks so that they are performed even if the user exits your application). This solution also requires more code and is less precise/reliable and less efficient than using a Handler.
EDIT: You can also use a ScheduledThreadPoolExecutor along with a Runnable.
(Personal opinion following) If you are exploring the APIs available in Android for performing timed tasks, that is ok, but I wouldn't use AlarmManager to schedule timed tasks within an Activity that's already running.
If you just want to have the code a bit more organised, you can make an inner class that implements Runnable and schedule your action like this:
class MyCameraActivity extends Activity
{
class TakePictureTask implements Runnable
{
public void run()
{
MyCameraActivity.this.takePicture();
}
}
void scheduleCameraShot()
{
(new Handler(this.getMainLooper())).postDelayed(new TakePictureTask(), 2000);
}
}

android timer makes the app crash

I'm trying to create a Timer that does something after 5 seconds.
Now in my main activity ( I only got 1 ) I wrote this class:
class Reminder {
Timer timer;
public Reminder(int seconds) {
timer = new Timer();
timer.schedule(new RemindTask(), seconds*1000);
}
class RemindTask extends TimerTask {
public void run() {
textFeedback.setText("test");
timer.cancel();
}
}
}
In a function (and also in my mainactivity) I create a timer as new Reminder(5).
After 5 seconds the application crashes.
I don't see whats wrong, because I do it in normal java apps like this.
Not sure where you have initialized textFeedback.
textFeedback.setText("test"); cannot update ui from a timer task. Timer task runs on a non ui thread. Ui can be updated only on ui thread.
Your options use a Handler or runOnUiThread.
Note runOnUiThread is a method of Activity class. Requires Activity Context
More info
Android Thread for a timer
Thanks.
Solved it like this:
new CountDownTimer(5000, 1000) {
public void onTick(long millisUntilFinished) {
//textFeedback.setText("seconds remaining: " + millisUntilFinished / 1000);
}
public void onFinish() {
textFeedback.setText("");
}
}.start();
when the class Remainder is istatiate not know the var textFeedback , becaouse you nees to pass the owmer of the textFeedback

Android Async, Handler or Timer?

Every 5 seconds, I want to call my webservice and get text (not images), then display it in my ImageAdapter. What would be the best way to accomplish this?
final Handler handler = new Handler();
final Runnable r = new Runnable()
{
public void run()
{
callWebservice();
}
};
handler.postDelayed(r, 5000);
It depends if you want to use a different thread or not. Do you want the user to be able to interact with the application on the UI Thread while the images are downloading? If so, then I would definitely use an AsyncTask with a small ProgressBar (style="#android:style/Widget.ProgressBar.Small")
If you don't care about threading then what #inazaruk said.
Edit: the truth is most modern apps that retrieve data from a web service will use an AsyncTask with a discreet little loader in the corner just to let the user know it's updating.
Edit 2: here's an example of using a TimerTask to run something every 5 seconds. The key is the runOnUiThread(). There may be better ways to tie all the elements together but this accurately portrays all the pieces.
myTimer = new Timer();
myTimer.schedule(new TimerTask() {
#Override
public void run() {
CallWebService();
}
}, 0, 1000);
}
private void CallWebService()
{
this.runOnUiThread(fetchData);
}
private Runnable fetchData = new Runnable() {
public void run() {
asyncTask.execute();
}
};
You should call asynctask inside the application main thread. Asynctask can't be called in a background thread.

Categories

Resources