简体   繁体   中英

Android App Progress Bar Won't Update When Using Thread and AsyncTask

I have an android app with a class, WifiAudioActivity that extends the Activity class.

In a nutshell, when a button on the app is pressed, a method is run, which uses a progress bar to show the progress of the method.

I show the progress bar and update it using AsyncTasks .

The problem is, in order to get the progress of the method, I have it running on another thread, so a while loop on the AsyncTask thread can constantly as for an updated progress value and display it in the progress bar. However, when I call progessUpdate() , which updates the progress bar, after I set the method on the thread running, it doesn't update the progress bar, it doesn't even jump to the onProgressUpdate() method code.

Interestingly, I can update the progress with dummy values before I run the Thread with the method on.

I presume it is a problem with my threads - can anyone help?

private ProgressDialog downloadAllDialog;
private ProgressDialog usingDialog;

private int totalDownloadSize;

private Download downloadAll;

private int totalBlocksLeft;

private boolean downloadComplete;
private boolean downloadFailed;

public void downloadAllClick(View view)     //When the download all button is clicked
{
    new PerformTask().execute();
}

private class PerformTask extends AsyncTask<Void, Integer, Integer> 
{
    protected void onPreExecute()
    {
        showDialog();
    }

    protected Integer doInBackground(Void... voi) 
    {
        int retryCount = 0;

        downloadComplete = false;   //Assume the download is not complete
        downloadFailed = false;

        totalBlocksLeft = 0;

        progressUpdater.run();       //Running method thread

        publishProgress(20);     //THIS DOES NOT WORK

        while ((retryCount < Consts.RETRY_TOTAL) && (!(downloadComplete)))
        {
            int blocksDownloaded = 0;

            while ((downloadComplete == false) && (downloadFailed == false))   
            {
                 blocksDownloaded = totalDownloadSize - downloadAll.getTotalBlocksLeft();    //GOT FROM THE RUNNING THREAD METHOD

                 publishProgress(blocksDownloaded);   //DOES NOT WORK
            }  

            ...
        }

        return totalBlocksLeft ;
    }

    Thread progressUpdater = new Thread()
    {
        @Override
        public void run() 
        {
            downloadComplete = downloadAll.downloadAudio(totalBlocksLeft);  //Download the audio

            if (!(downloadComplete))
            {
                downloadFailed = true;
            }
        }
    };

    protected void onProgressUpdate(Integer... progress) 
    {
        usingDialog.setProgress(progress[0]);
    }

    protected void onPostExecute(Integer result) 
    {
        removeDialog();
    }
}

protected Dialog onCreateDialog() 
{   
    downloadAllDialog = new ProgressDialog(this);

    downloadAllDialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);

    downloadAllDialog.setMax(totalDownloadSize);

    downloadAllDialog.setProgress(0);

    downloadAllDialog.setMessage("Download All");

    usingDialog = downloadAllDialog;

return downloadAllDialog;
}

}

As it stands, in the key bit of code:

blocksDownloaded = totalDownloadSize - downloadAll.getTotalBlocksLeft();    //GOT FROM THE RUNNING THREAD METHOD

publishProgress(blocksDownloaded);   //DOES NOT WORK

blocksDownloaded, which gets its updated value from the thread running method, is updating with the progress. I'm sure it's not technically right, but having the thread in the AsyncTask does actually run the method whilst getting the progress update in the main method. It is therefore only the updating of the progress bar that doesn't work.

It seems you are not using AsyncTask properly. You seem to be calling the download code on the UI thread, which is probably blocking the progressBar from updating.

I can suggest the following. This will make sure you are using AsyncTask properly. When you use AsyncTask properly the code should get a lot simplified as well.

  1. Do not create any threads and do not use the runOnUIThread method. The AsyncTask provides you the callback methods which run on appropriate threads.
  2. The main download code should be in doInBackground method.
  3. You should call publishProgress at some points somewhere inside the download code.

You need to call

progressUpdater.start(); 

instead of

progressUpdater.run(); 

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