Handler cannot cancel asynctask in higher api - android

In my app I am using an asynctask for an operation.But I am also using a handler to cancel my task in case of time-out.
this is my handler operation
Handler mHandler = new android.os.Handler() {
#Override
public void handleMessage(Message msg) {
task.cancel(true);
}
};
Message msg = new Message();
msg.arg1 = 0;
mHandler.sendMessageDelayed(msg, 1000);
and this is my asynctask start
final findIpTask task = new findIpTask(1, 2);
task.execute();
and in my asynctask I have
protected void onCancelled() {
running = false;
dialog.dismiss();
//some alert dialog for time-out
in 2.33 emulator it is working fine.but when I run my app on a 4.0 emulator it doesn't stop.does anybody know why and have a solution.

Your AsyncTask doesn't stopped due to not stopping or cancel of Handler Thread.
Instead of using handler use timer thread, you can stop your thread and asyncTask, as shown in snippet below.
Timer myTimer = new Timer();
myTimer.schedule(new TimerTask() {
#Override
public void run() {
//Your Stuffs
}
}, 0, 1000); // put your delay here
if(ButtonStopped == true){
myTimer .cancel();
myTimer .purge();
//your stuffs
task.cancle();// call here for stopping your asyncTask
}else{
//your stuffs
}
For more info go to this Android Developer link.

Related

a good way to check if timer already run repeatedly

I'm working on React Native and i want to create a never ending service that run every (n) seconds on Native Modules (on this topic is android).
I've create a simple service like this
public void startTimer() {
timer = new Timer();
timer.scheduleAtFixedRate(new TimerTask() {
public void run() {
Log.v(TAG, "SERVICE RUN");
try{
if(haveNetworkConnection()){
db.openDB();
if(db.countRowNewStructure()>0){
//send data to server
} else{
Log.v(TAG, "No data should be send to server");
}
} else {
Log.v(TAG, "Ga ada sinyal");
}
} catch (JSONException e){
e.printStackTrace();
}
}
}, 0, 1000);
}
above code run every second to check, but i'm facing the problem when i re-run the service from React Native, the log showing me those code every 0.5 seconds
the simulation may be like :
0----------------1 //seconds
startTimer()
re-run startTimer() conscious
0----------------1 //seconds
startTimer()
//now i have two startTimer() that will run every 1 sec on different interval
I want to keep my startTimer() just running once even I trigger startService() every 0.5 sec.
how can i do that? is it possible?
this may help you. Timmer to perform the certain action in android after the particular time.
final Handler handler = new Handler();
Timer timer = new Timer();
TimerTask timertaskforsynctime = new TimerTask() {
#Override
public void run() {
handler.post(new Runnable() {
#Override
public void run() {
// your action here
}
});
}
};
timer.schedule(timertaskforsynctime,5000,10000);// decide the time when it will start and after how much time it will run continusly.
}`
for one time
new Handler().postDelayed(new Runnable(){
#Override
public void run() {
// your code that will run after 1 sec
}
}, 1000);
You could make use of the cancel method to cancel the previous Timer.
public class YourModule extends ReactContextBaseJavaModule {
Timer tim = new Timer();
public void startTimer() {
tim.cancel();
tim = new Timer();
tim.scheduleAtFixedRate(
new TimerTask() {
public void run() {
// Run tasks
}
},
0,
1000);
}
}

TimerTask / Handler with Delay getting called Multiple times

I need a delay for around 5 seconds. I have tried using Timer using below code :
Timer myTimer = new Timer();
myTimer.schedule(new TimerTask() {
#Override
public void run() {
Log.d(TAG,"Timer");
}
}, 4000, 5000);
When i check logs, the Timer is getting printed thrice. If I change time, sometimes it gets printed in log 4 times as well.
I have tried using Handler as well like below :
final Handler mHandler = new Handler();
new Thread(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
while (true) {
try {
Thread.sleep(10000);
mHandler.post(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
Log.d(Utility.TAG,"Sleep::");
}
});
} catch (Exception e) {
// TODO: handle exception
}
}
}
}).start();
But again the log is printing multiple times. I just want to call my method once not multiple times. How can I achieve it ?
EDIT
used handler without thread as well like below :
final Handler h = new Handler();
final int delay = 3000; //milliseconds
h.postDelayed(new Runnable(){
public void run(){
//do something
h.postDelayed(this, delay);
Log.d(Utility.TAG,"Sleep ::");
}
}, delay);
But again, Log is getting printed thrice
Your third approach (no Timer, no Thread) is the closest to being correct. It's printing multiple times because the Runnable is re-posting itself every time it runs. If you only want it to run once, remove this line from the run() method:
h.postDelayed(this, delay);

[ANDROID]Implementing Delay in Message in HandlerThread

i want to do some stuff on every few seconds in my app, for that purpose , i have implemented HandlerThread & handler via following code
handlerThread = new HandlerThread(getClass().getSimpleName());
handlerThread.start();
handler = new Handler(handlerThread.getLooper(), new Callback() {
#Override
public boolean handleMessage(Message msg) {
//my code here
return l.this.handleMessage(msg);
}
});
I initiate this handler by sending message from onCreate()
I handle the message as follows :
private boolean handleMessage(Message msg) {
switch (msg.what) {
default:
return false;
case MY_MESSAGE:
if(handler_stop==0)
{
checkLauncher();
sendMessage(MY_MESSAGE); // I Send the message from here to make //this continuous
}
}
return true;
}
It's Working fine but it Sends message too fast , i mean constantly , instead i want this message to be sent after 2 or 3 seconds , In Short , i want to repeat task every 2-3 seconds.
How can i do this on above code ? please some one help
First declare one global varialbe for Handler to update the UI control from Thread, like below:
Handler mHandler = new Handler();
Now create one Thread and use while loop to periodically perform the task using the sleep method of the thread.
new Thread(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
while (true) {
try {
Thread.sleep(10000);// change the time according to your need
mHandler.post(new Runnable() {
#Override
public void run() {
// TODO Auto-generated method stub
// Write your code here to update the UI.
}
});
} catch (Exception e) {
// TODO: handle exception
}
}
}
}).start();
Else just add this in your code:
handler.postDelayed(new Runnable(){
public void run() {
// do something
}}, 20000);
Why not to use Handler.sendMessageDelayed? It allows you to schedule your message to be delivered to the Handler with delay that you specify. So your code will look like this:
private boolean handleMessage(Message msg) {
switch (msg.what) {
default:
return false;
case MY_MESSAGE:
if(handler_stop == 0) {
checkLauncher();
sendMessageDelayed(MY_MESSAGE, 2000); // Send message everytime with 2 seconds delay
}
}
return true;
}
hi i have an simple way for doing this
try this
Runnable runnable;
final Handler handler = new Handler();
runnable = new Runnable() {
public void run() {
// HERE I AM CHANGING BACKGROUND YOU CAN DO WHATEVER YOU WANT
_images[i].setBackgroundResource(imageArray[0]);
i++;
handler.postDelayed(this, 1000); // for interval...
}
};
handler.postDelayed(runnable, 1000); // for initial delay..
worked for me hope you will also find it working
thanks
Vote Up if find usefull.

How to quit HandlerThread's looper safely

I have a HandlerThread, to which I keep posting a runnable every 5 seconds. Something like this:
HandlerThread thread = new HandlerThread("MyThread");
thread.start();
Handler handler = new Handler(thread.getLooper());
handler.post(new Runnable() {
public void run() {
//...
handler.postDelayed(this, 5000);
}
});
I need to quit the looper at some point, after 60 seconds or something like that.. so I write:
mainHandler = new Handler(Looper.myLooper()); //main thread's
mainHandler.postDelayed(new Runnable() {
#Override
public void run() {
thread.getLooper().quit();
}
}, 60000);
I think this causes the looper to quit abruptly, so I start getting this "warning" messages:
W/MessageQueue(3726): java.lang.RuntimeException: Handler
(android.os.Handler) {4823dbf8} sending message to a Handler on a dead
thread
I want to avoid this error msg, I thought that I could solve it by using the Looper.quitSafely() method.. but I checked the API and it's no longer available.
Does anyone know what happened to it? (It's not deprecated like some other methods).
Is there some way I can quit the looper safely? Thanks!
You could try to use a boolean to know if the code should be executed. Something like this:
private boolean runHandler = true;
...
HandlerThread thread = new HandlerThread("MyThread");
thread.start();
Handler handler = new Handler(thread.getLooper());
handler.post(new Runnable() {
public void run() {
if(runHandler){
//...
handler.postDelayed(this, 5000);
}
}
});
mainHandler = new Handler(Looper.myLooper()); //main thread's
mainHandler.postDelayed(new Runnable() {
#Override
public void run() {
runHandler = false;
}
}, 60000);
Im not Thread Guru, but this way can give you direction:
...
_thread.setRunning(true);
_thread.start();
..
public void stopThread(){
boolean retry = true;
_thread.setRunning(false);
while (retry) {
try {
_thread.join();
retry = false;
Log.e("test", "thread stopped");
} catch (InterruptedException e) {
Log.e("test", "can't stop thread, retrying...");
// we will try it again and again...
}
}
}
In your thread:
while (isRunning) {
//...
}
1st all you implement run method in loop (while(isRunnig){}).
On finish, you switch flag to false and "wait" for join.

Several setMessage updates (ProgressBar)

new Thread() {
public void run() {
try {
Progress.setMessage("Scanning Apps ...");
int CurrentNumber = 0;
while (CurrentNumber <= 99) {
Progress.setProgress(CurrentNumber);
Progress.setMessage(CurrentNumber + "");
sleep(100);
CurrentNumber ++;
} catch (Exception e) {
}
}
}.start();
So.. this code is not working :(
What am I doing wrong?
Without Progress.setMessage(CurrentNumber + ""); it is working perfectly...
write handler
e.g.
private Handler handler = new Handler() {
#Override
public void handleMessage(Message msg) {
//set message here
}
};
Try looking at AsyncTask which handles progress updates, giving you a chance to set your progress message on the UI thread.
I'm assuming that Progress is an instance of ProgressDialog. You can only update the UI on the UI (main) thread. Read about threading and the UI on the dev site.

Categories

Resources