开发者

Trying to get downloading file size, but get an error

private class DownloadLargeFileTask extends AsyncTask<Void, Void, Void> 
{
    private final ProgressDialog dialog;

    public DownloadLargeFileTask(ProgressDialog dialog) {
         this.dialog = dialog;
    }

    protected void onPreExecute() {
        dialog.show();
    }


    protected void onPostExecute(Void unused) {
        dialog.dismiss();
    }

    @Override
    protected Void doInBackground(Void... arg0) {
        download();
        return null;
    }
}

private void download ()
{
    try 
    {
        long startTime = System.currentTimeMillis();

        URL u = new URL("http://mds.podfm.ru/188/download/040_Sergejj_Palijj_-_Karantin_CHast_2.mp3");
        HttpURLConnection c = (HttpURLConnection) u.openConnection();

        c.setRequestMethod("GET");
        c.setDoOutput(true);
        c.connect();
        FileOutputStream f = new FileOutputStream(new File("/sdcard/","my.mp3"));

        InputStream in = c.getInputStream();

        byte[] buffer = new byte[1024];
        int len1 = 0;
        int downloadedSize = 0;
        while ( (len1 = in.read(buffer)) != -1 ) 
        {
          f.write(buffer,0, len1);
          downloadedSize += len1; 
     开发者_C百科     ReturnDownloadedBytes(downloadedSize);
        }
        f.close();
        Log.d("ImageManager", "download ready in" + ((System.currentTimeMillis() - startTime) / 1000) + " sec");
    }
    catch (IOException e)
    {
        Log.d("ImageManager", "Error" + ((System.currentTimeMillis()) / 1000) + e + " sec");
    }
}

private void ReturnDownloadedBytes(int size)
{
    text.setText(String.valueOf(size));

}

Error says: Only the original thread that created a view hierarchy can touch its views. i think this means that i create textview from one therad and trying to get access from another one (AsyncTask) but how to get it? Thanks

EDIT

here is the all code. but even if i send in publishProgress(downloadedSize) int value = 10 it alwys outputs in text.setText(String.valueOf(progress)); different values like [Ljava.lang.float;@43ed62f78

public class list extends Activity {

private TextView text;



@Override
public void onCreate(Bundle icicle)
{
    super.onCreate(icicle);
    setContentView(R.layout.main);

    text = (TextView)findViewById(R.id.result);
}

public void selfDestruct(View view) {

    ProgressDialog dialog = new ProgressDialog(this);
    dialog.setMessage("????????. ?????...");
    new DownloadLargeFileTask(dialog).execute();

}


private class DownloadLargeFileTask extends AsyncTask<Void, Integer, Void> 
{
    private final ProgressDialog dialog;

    public DownloadLargeFileTask(ProgressDialog dialog) {
         this.dialog = dialog;
    }

    protected void onPreExecute() {
        dialog.show();
    }


    protected void onPostExecute(Void unused) {
        dialog.dismiss();
    }

    protected void onProgressUpdate(Integer...progress) {

        text.setText(String.valueOf(progress));

    }

    @Override
    protected Void doInBackground(Void... arg0) {
        try 
        {
            long startTime = System.currentTimeMillis();

            URL u = new URL("http://mds.podfm.ru/188/download/040_Sergejj_Palijj_-_Karantin_CHast_2.mp3");
            HttpURLConnection c = (HttpURLConnection) u.openConnection();

            c.setRequestMethod("GET");
            c.setDoOutput(true);
            c.connect();
            FileOutputStream f = new FileOutputStream(new File("/sdcard/","my.mp3"));

            InputStream in = c.getInputStream();

            byte[] buffer = new byte[1024];
            int len1 = 0;
            int downloadedSize = 10;
            while ( (len1 = in.read(buffer)) != -1 ) 
            {
              f.write(buffer,0, len1);
              //downloadedSize += len1; 
              **publishProgress(downloadedSize);**
            }
            f.close();
            Log.d("ImageManager", "download ready in" + ((System.currentTimeMillis() - startTime) / 1000) + " sec");
        }
        catch (IOException e)
        {
            Log.d("ImageManager", "Error" + ((System.currentTimeMillis()) / 1000) + e + " sec");
        }
        return null;
    }
}


You are correct in your assessment of the error. I'm assuming that text is a TextView object that is defined in your Activity, and as such it is created in the UI thread. The code that runs within doInBackground() runs in a separate thread. Only the UI thread can perform updates to UI elements, so when you try to call setText you get the error message that you reported.

Abhinav is also correct in how to fix the issue, as AsyncTask has a method that you can call to send updates from the background thread to the UI thread: publishProgress, which calls onProgressUpdate().

Add this method to your AsyncTask:

@Override
protected void onProgressUpdate(Integer... integer){
    text.setText(integer[0].toString());
}

And change the while loop in download():

while ( (len1 = in.read(buffer)) != -1 ) 
{
  f.write(buffer,0, len1);
  downloadedSize += len1; 
  publishProgress(downloadedSize);
}


You can change the UI by publishing the progress to the UI thread. Call publishProgress from doInBackground. This will call onProgressUpdate in your AsyncTask from where you can update the UI.

You will have to define onProgressUpdate in your AsyncTask. http://developer.android.com/reference/android/os/AsyncTask.html#onProgressUpdate(Progress...)

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜