2012-09-06 79 views
0

我使用Google图表API在我的应用程序中构建图表。AsyncTask下载图片错误

在我的情况下,我需要下载每个图表上的图像。我为此使用AsyncTask。

要监视下载过程,我使用进度对话框。但是在这个AsyncTask类中出现错误。

执行的AsyncTask的:

new loadChart(ChartAct.this,img).execute(); 

和的AsyncTask代码:

public class loadChart extends AsyncTask<Void, Void, Void> { 
    private ImageView img; 
    private Context con; 
    private ProgressDialog dialog; 

    public loadChart(Context context, ImageView img1) { 
     this.img = img1; 
     this.con = context; 
    } 

    @Override 
    protected void onPreExecute() { 
     dialog = ProgressDialog.show(con, "Connecting:", 
       "Loading. Please wait...", true); 
     super.onPreExecute(); 
    } 

    @Override 
    protected Void doInBackground(Void... params) { 
     final Bitmap bitmap = DownloadImage(); 
     img.setImageBitmap(bitmap); 
     return null; 
    } 

    @Override 
    protected void onPostExecute(Void result) { 
     dialog.dismiss(); 
     super.onPostExecute(result); 
    } 

    private static InputStream OpenHttpConnection(String urlString) 
      throws IOException { 

     Log.d("palval", "OpenHttpConnection"); 
     InputStream in = null; 
     int response = -1; 

     URL url = new URL(urlString); 
     URLConnection conn = url.openConnection(); 

     if (!(conn instanceof HttpURLConnection)) 
      throw new IOException("Not an HTTP connection"); 

     try { 
      HttpURLConnection httpConn = (HttpURLConnection) conn; 
      httpConn.setAllowUserInteraction(false); 
      httpConn.setInstanceFollowRedirects(true); 
      httpConn.setRequestMethod("GET"); 
      httpConn.connect(); 

      response = httpConn.getResponseCode(); 

      if (response == HttpURLConnection.HTTP_OK) { 
       in = httpConn.getInputStream(); 
      } 

      String res = Integer.toString(response); 
     } catch (Exception ex) { 
      throw new IOException("Error connecting"); 
     } 
     return in; 
    } 

    public static Bitmap DownloadImage() { 
     Log.d("palval", "DownloadImage"); 
     Bitmap bitmap = null; 
     InputStream in = null; 
     try { 

      in = OpenHttpConnection("https://chart.googleapis.com/chart?chs=440x220&chd=t:60,40&cht=p3&chl=Hello|World"); 
      bitmap = BitmapFactory.decodeStream(in); 
      in.close(); 
     } catch (IOException e1) { 
      // TODO Auto-generated catch block 
      e1.printStackTrace(); 
     } 
     return bitmap; 
    } 

} 

错误:

09-06 18:35:35.574: E/AndroidRuntime(2502): FATAL EXCEPTION: AsyncTask #1 
09-06 18:35:35.574: E/AndroidRuntime(2502): java.lang.RuntimeException: An error occured while executing doInBackground() 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.os.AsyncTask$3.done(AsyncTask.java:278) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.FutureTask.setException(FutureTask.java:124) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.FutureTask.run(FutureTask.java:137) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:208) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1076) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:569) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.lang.Thread.run(Thread.java:864) 
09-06 18:35:35.574: E/AndroidRuntime(2502): Caused by: android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views. 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.ViewRootImpl.checkThread(ViewRootImpl.java:4132) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.ViewRootImpl.requestLayout(ViewRootImpl.java:723) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.View.requestLayout(View.java:12957) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.View.requestLayout(View.java:12957) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.View.requestLayout(View.java:12957) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.View.requestLayout(View.java:12957) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.view.View.requestLayout(View.java:12957) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.widget.ImageView.setImageDrawable(ImageView.java:362) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.widget.ImageView.setImageBitmap(ImageView.java:377) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at com.example.headache.loadChart.doInBackground(loadChart.java:37) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at com.example.headache.loadChart.doInBackground(loadChart.java:1) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at android.os.AsyncTask$2.call(AsyncTask.java:264) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305) 
09-06 18:35:35.574: E/AndroidRuntime(2502):  ... 5 more 
09-06 18:35:36.055: E/WindowManager(2502): Activity com.example.headache.ChartAct has leaked window [email protected] that was originally added here 
09-06 18:35:36.055: E/WindowManager(2502): android.view.WindowLeaked: Activity com.example.headache.ChartAct has leaked window [email protected] that was originally added here 
09-06 18:35:36.055: E/WindowManager(2502): at android.view.ViewRootImpl.<init>(ViewRootImpl.java:352) 
09-06 18:35:36.055: E/WindowManager(2502): at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:373) 
09-06 18:35:36.055: E/WindowManager(2502): at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:321) 
09-06 18:35:36.055: E/WindowManager(2502): at android.view.WindowManagerImpl$CompatModeWrapper.addView(WindowManagerImpl.java:152) 
09-06 18:35:36.055: E/WindowManager(2502): at android.view.Window$LocalWindowManager.addView(Window.java:541) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.Dialog.show(Dialog.java:301) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ProgressDialog.show(ProgressDialog.java:116) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ProgressDialog.show(ProgressDialog.java:99) 
09-06 18:35:36.055: E/WindowManager(2502): at com.example.headache.loadChart.onPreExecute(loadChart.java:29) 
09-06 18:35:36.055: E/WindowManager(2502): at android.os.AsyncTask.executeOnExecutor(AsyncTask.java:561) 
09-06 18:35:36.055: E/WindowManager(2502): at android.os.AsyncTask.execute(AsyncTask.java:511) 
09-06 18:35:36.055: E/WindowManager(2502): at com.example.headache.ChartAct.onCreate(ChartAct.java:31) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.Activity.performCreate(Activity.java:4531) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1071) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2150) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2229) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ActivityThread.access$600(ActivityThread.java:139) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1261) 
09-06 18:35:36.055: E/WindowManager(2502): at android.os.Handler.dispatchMessage(Handler.java:99) 
09-06 18:35:36.055: E/WindowManager(2502): at android.os.Looper.loop(Looper.java:154) 
09-06 18:35:36.055: E/WindowManager(2502): at android.app.ActivityThread.main(ActivityThread.java:4945) 
09-06 18:35:36.055: E/WindowManager(2502): at java.lang.reflect.Method.invokeNative(Native Method) 
09-06 18:35:36.055: E/WindowManager(2502): at java.lang.reflect.Method.invoke(Method.java:511) 
09-06 18:35:36.055: E/WindowManager(2502): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:784) 
09-06 18:35:36.055: E/WindowManager(2502): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:551) 
09-06 18:35:36.055: E/WindowManager(2502): at dalvik.system.NativeStart.main(Native Method) 

回答

1

您不能设置在doInBackground()图像使其返回一个位图,并将其设置在onPostExecute()

public class loadChart extends AsyncTask<Void, Void, Bitmap> { 
    private ImageView img; 
    private Context con; 
    private ProgressDialog dialog; 

    public loadChart(Context context, ImageView img1) { 
     this.img = img1; 
     this.con = context; 
    } 

    @Override 
    protected void onPreExecute() { 
     dialog = ProgressDialog.show(con, "Connecting:", 
       "Loading. Please wait...", true); 
     super.onPreExecute(); 
    } 

    @Override 
    protected Bitmap doInBackground(Void... params) { 
     final Bitmap bitmap = DownloadImage(); 
     return bitmap; 
    } 

    @Override 
    protected void onPostExecute(Bitmap result) { 
     dialog.dismiss(); 
     img.setImageBitmap(result); 
    } 
0

不能从doInBackground()访问UI,这是你通过设置做什么与您的img.setImageBitmap(bitmap);位图。如果您在使用runOnUiThread()进行背景活动时需要这样做,请将您的UI访问代码移至onPostExecute(),即将对象中的位图存储,但将其分配给onProgressUpdate()中的UI元素。一般来看看AsyncTask documentation

+0

我能做到这一点的postExecute? – Val

+0

是的,您应该在'doInBackground()'中返回您的位图,并将其设置在'onPostExecute()' – tolgap

+0

@ p.Valery中。请参阅编辑答案 –

0

您无法从doInBackground()修改UI元素。

尝试使用您的活动的方法runOnUIThread()或将UI更改为onPostExecute()方法的方法。

阅读this answer了解更多详情。