简体   繁体   中英

Android wait AsyncTask to finish

I have a function, AppHelper.isOnline(Context context) , I call in various parts of my application to check that a session didn't timeout before making an HTTP request.

public void onClick(View v) {
        Intent intent = null;
        switch (v.getId()) {

        case R.id.buttonPagamenti:
            if (AppHelper.isOnline(this))
            {
                //here AppHelper.isOnline should have finished it's async task
                intent = new Intent(this, OrdineCreaActivity.class);
                this.startActivityForResult(intent, R.id.buttonPagamenti);
            }
            break;
...

Inside AppHelper.isOnline() , I am executing an AsyncTask that logs in, thus making a network request, which can't be run on UI because otherwise I get an exception. I need to wait for it to finish BEFORE resuming with the code inside the if. How can I do this ?

Problem is the activity starts firsts, then the AsyncTask executes, so when the activity expects a valid logged in session, it breaks.

You have two options:

Either use the AsyncTask 's method get(long timeout, TimeUnit unit) like that:

task.get(1000, TimeUnit.MILLISECONDS);

This will make your main thread wait for the result of the AsyncTask at most 1000 milliseconds (as per @user1028741 comment: actually there is also infinetly waiting method - AsyncTask#get() which might also do the work for you in some cases).

Alternatively you can show a progress dialog in the async task until it finishes. See this thread (No need for me to copy past the code). Basically a progress dialog is shown while the async task runs and is hidden when it finishes.

You have even third option:" if Thread is sufficient for your needs you can just use its join method. However, if the task is taking a long while you will still need to show a progress dialog, otherwise you will get an exception because of the main thread being inactive for too long.

try using

if (AppHelper.isOnline(this))
        {
            while(!task.isCancelled()){
               // waiting until finished protected String[] doInBackground(Void... params)          
              } 
            intent = new Intent(this, OrdineCreaActivity.class);
            this.startActivityForResult(intent, R.id.buttonPagamenti);
        }    

For more information read http://developer.android.com/reference/android/os/AsyncTask.html

Rafiq's response did not work for me - the app hung. I think the reason has to do with the nature of isCancelled(): "Returns true if this task was cancelled before it completed normally." If the task completes normally (ie is not cancelled) then while(!task.isCancelled()) { } will loop forever.

To solve this create a Boolean flag that you instatiate to false and then flip to true in task.onPostExecute() . Then do while(!flag) { } before switching Activities. Additionally, if you'd like to give the main thread a 'break' to let the AsyncTask process a little faster, you can do try this:

while (!flag) {
    try { Thread.sleep(100); }
    catch (InterruptedException e) { e.printStackTrace(); }
}

It seems to be working well for me.

intent = new Intent(this, OrdineCreaActivity.class);
context.startActivityForResult(intent, R.id.buttonPagamenti);

Write the above lines in onPostExecute() of you AysncTask. Because if we are using AsyncTask it wont wait there until the task complete.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM