Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Passing arguments to AsyncTask, and returning results

I have an application that does some long calculations, and I would like to show a progress dialog while this is done. So far I have found that I could do this with threads/handlers, but didn't work, and then I found out about the AsyncTask.

In my application I use maps with markers on it, and I have implemented the onTap function to call a method that I have defined. The method creates a dialog with Yes/No buttons, and I would like to call an AsyncTask if Yes is clicked. My question is how to pass an ArrayList<String> to the AsyncTask (and work with it there), and how to get back a new ArrayList<String> like a result from the AsyncTask?

The code of the method looks like this:

String curloc = current.toString(); String itemdesc = item.mDescription;  ArrayList<String> passing = new ArrayList<String>(); passing.add(itemdesc); passing.add(curloc);  ArrayList<String> result = new ArrayList<String>();  new calc_stanica().execute(passing,result);  String minim = result.get(0); int min = Integer.parseInt(minim);  String glons = result.get(1); String glats = result.get(2);  double glon = Double.parseDouble(glons); double glat = Double.parseDouble(glats);  GeoPoint g = new GeoPoint(glon, glat); String korisni_linii = result.get(3); 

So, as you see, I would like to send the string array list "passing" to the AsyncTask, and to get the "result" string array list back from it. And the calc_stanica AssycTask class looks like this:

public class calc_stanica extends AsyncTask<ArrayList<String>, Void, ArrayList<String>> {     ProgressDialog dialog;      @Override     protected void onPreExecute() {         dialog = new ProgressDialog(baraj_mapa.this);         dialog.setTitle("Calculating...");         dialog.setMessage("Please wait...");         dialog.setIndeterminate(true);         dialog.show();     }      protected ArrayList<String> doInBackground(ArrayList<String>... passing) {          //Some calculations...          return something; //???     }      protected void onPostExecute(Void unused) {         dialog.dismiss();     } 

So my question is how to get the elements of the "passing" array list in the AsyncTask doInBackground method (and use them there), and how to return an array list to use in the main method (the "result" array list)?

like image 706
Bojan Ilievski Avatar asked Nov 16 '10 15:11

Bojan Ilievski


People also ask

Why did AsyncTask get deprecated?

This class was deprecated in API level 30. AsyncTask was intended to enable proper and easy use of the UI thread. However, the most common use case was for integrating into UI, and that would cause Context leaks, missed callbacks, or crashes on configuration changes.

What happens to AsyncTask if activity is destroyed?

If you start an AsyncTask inside an Activity and you rotate the device, the Activity will be destroyed and a new instance will be created. But the AsyncTask will not die. It will go on living until it completes. And when it completes, the AsyncTask won't update the UI of the new Activity.

How many times an instance of AsyncTask can be executed?

AsyncTask instances can only be used one time.


2 Answers

Change your method to look like this:

String curloc = current.toString(); String itemdesc = item.mDescription; ArrayList<String> passing = new ArrayList<String>(); passing.add(itemdesc); passing.add(curloc); new calc_stanica().execute(passing); //no need to pass in result list 

And change your async task implementation

public class calc_stanica extends AsyncTask<ArrayList<String>, Void, ArrayList<String>> { ProgressDialog dialog;      @Override     protected void onPreExecute() {         dialog = new ProgressDialog(baraj_mapa.this);         dialog.setTitle("Calculating...");         dialog.setMessage("Please wait...");         dialog.setIndeterminate(true);         dialog.show();     }      protected ArrayList<String> doInBackground(ArrayList<String>... passing) {         ArrayList<String> result = new ArrayList<String>();         ArrayList<String> passed = passing[0]; //get passed arraylist          //Some calculations...          return result; //return result     }      protected void onPostExecute(ArrayList<String> result) {         dialog.dismiss();         String minim = result.get(0);         int min = Integer.parseInt(minim);         String glons = result.get(1);         String glats = result.get(2);         double glon = Double.parseDouble(glons);         double glat = Double.parseDouble(glats);         GeoPoint g = new GeoPoint(glon, glat);         String korisni_linii = result.get(3);     } 

UPD:

If you want to have access to the task starting context, the easiest way would be to override onPostExecute in place:

new calc_stanica() {     protected void onPostExecute(ArrayList<String> result) {       // here you have access to the context in which execute was called in first place.        // You'll have to mark all the local variables final though..      } }.execute(passing); 
like image 135
Konstantin Burov Avatar answered Sep 23 '22 16:09

Konstantin Burov


Why would you pass an ArrayList?? It should be possible to just call execute with the params directly:

String curloc = current.toString(); String itemdesc = item.mDescription; new calc_stanica().execute(itemdesc, curloc) 

That how varrargs work, right? Making an ArrayList to pass the variable is double work.

like image 26
Leander Avatar answered Sep 22 '22 16:09

Leander