Come creare / Run AsyncTask in servizio senza runOnUiThread ()
-
27-09-2019 - |
Domanda
Ho un Service
che crea AsyncTask
s per il download di file. In attività, creiamo Runnable
s o Thread
s che passiamo a Activity.runOnUiThread()
. Non posso di accesso che il metodo da un servizio, quindi come faccio a utilizzare AsyncTask
correttamente, (fare lavori pesanti senza bloccare il thread UI)?
Soluzione
Se il servizio viene chiamato solo dalla vostra applicazione, e si può fare un Singleton, quindi provare questo:
public class FileDownloaderService extends Service implements FileDownloader {
private static FileDownloaderService instance;
public FileDownloaderService () {
if (instance != null) {
throw new IllegalStateException("This service is supposed to be a singleton");
}
}
public static FileDownloaderService getInstance() {
// TODO: Make sure instance is not null!
return instance;
}
@Override
public void onCreate() {
instance = this;
}
@Override
public IBinder onBind(@SuppressWarnings("unused") Intent intent) {
return null;
}
@Override
public void downloadFile(URL from, File to, ProgressListener progressListener) {
new Thread(new Runnable() {
@Override
public void run() {
// Perform the file download
}
}).start();
}
}
Ora è possibile chiamare direttamente i metodi sul vostro servizio. Quindi basta chiamare downloadFile()
per mettere il servizio al lavoro.
Informazioni sul reale questione di come aggiornare l'interfaccia utente. Si noti che questo metodo riceve un'istanza ProgressListener
. Potrebbe assomigliare a questo:
public interface ProgressListener {
void startDownloading();
void downloadProgress(int progress);
void endOfDownload();
void downloadFailed();
}
Ora basta aggiornare l'interfaccia utente da attività (non dal servizio, che resta a conoscenza di come l'aspetto dell'interfaccia utente piace).