A game I wrote some time ago has a problem with ANRs, and debugging suggests they’re down to HTTP requests taking a long time (and thus causing the ANR).
I’d thought that by assigning the HTTP code into a Runnable called from within a Handler, I’d could avoid the ANR – but it seems this isn’t the case?
The stack dumps suggest the runnable/handler code is still running within the ‘Main’ thread and thus still causes ANRs??
The task it’s doing is asynchronous (uploading highscores and achievements) and so can be started and left to it’s own devices entirely – what is the best way to implement this so that ANRs aren’t going to become a problem?
One topic suggested that the Handler should be created in the Application class and not within the Game’s Activity – but I can’t find any detail on the differences between those cases??
All ideas greatly apprec.
p.s. extending this to ask – I assume an ANR relating to HTTP comes down to the phone being out-of-service/network/WiFi, because I’ve set a SHORT timeout for these requests (they’re non-essential and can be retried later!?)
A
Handlerwill execute code / handle messages per default (any constructor withoutLoopere.g.new Handler()) in the current thread. That is in almost every case the main thread. If you want it to execute in a different thread you have to tell it whichLooperthread it should use.Android has a utility class called
HandlerThreadthat creates aThreadwith aLooper.Short example:
In case your task needs only a some information and does not need to report back, I’d go with an
IntentService. Those don’t go mad if your Activity-lifecycle recreates the Activity.You would create a small
Servicein it’s own fileAdd it to the
AndroidManifest.xmlAnd in your code start it with
IntentService#onHandleIntent()runs on a background thread already so you don’t have to bother about that.