Frage

I found this nice code snippet: Android, Make an image at a URL equal to ImageView's image

and tried to implement it on a little "screen slider" app that I'm trying to create. When it tries to create the bitmap, it throws an exception saying that I can't make a network call on the same thread. I then tried creating a new thread to fill my imageview and now it says only the original thread that created a view hierarchy can touch its views.

I'm not sure where to turn next. This is inside a class that extends Fragment so there is no "direct access" to the ViewGroup.

This is the code with the new thread:

public class MyThread implements Runnable {

    ViewGroup vg;
   public MyThread(ViewGroup parameter) {
       this.vg = parameter;
   }

   public void run() {
       try {                      
              Bitmap bitmap = BitmapFactory.decodeStream((InputStream)new URL("http://static.adzerk.net/Advertisers/11239ce559004d9a8e16fe2790630628.png").getContent());
              ImageView i = (ImageView)vg.findViewById(R.id.image);
              i.setImageBitmap(bitmap); 
            } catch (MalformedURLException e) {
              e.printStackTrace();
            } catch (IOException e) {
              e.printStackTrace();
            }
   }
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {
    // Inflate the layout containing a title and body text.
    ViewGroup rootView = (ViewGroup) inflater
            .inflate(R.layout.fragment_screen_slide_page, container, false);

    // Set the title view to show the page number.
    ((TextView) rootView.findViewById(android.R.id.text1)).setText(
            getString(R.string.title_template_step, mPageNumber + 1));

    Runnable r = new MyThread(rootView);
    new Thread(r).start();

    return rootView;
}

can anyone provide some suggestions of how I can get that bitmap object filled in a new thread and then passed back to my UI thread to fill my imageview?

TIA.

War es hilfreich?

Lösung

I ended up using an asynctask to make this work:

class BitmapWorkerTask extends AsyncTask<Integer, Void, Bitmap> {
    private final WeakReference<ImageView> imageViewReference;
    private int data = 0;

    public BitmapWorkerTask(ImageView imageView) {
        // Use a WeakReference to ensure the ImageView can be garbage collected
        imageViewReference = new WeakReference<ImageView>(imageView);
    }

    // Decode image in background.
    @Override
    protected Bitmap doInBackground(Integer... params) {
        data = params[0];
        Bitmap bitmap = null;
        try {                     
              bitmap = BitmapFactory.decodeStream((InputStream)new URL("http://static.adzerk.net/Advertisers/11239ce559004d9a8e16fe2790630628.png").getContent());
            } catch (MalformedURLException e) {
              e.printStackTrace();
            } catch (IOException e) {
              e.printStackTrace();
            }
        return bitmap;
    }

    // Once complete, see if ImageView is still around and set bitmap.
    @Override
    protected void onPostExecute(Bitmap bitmap) {
        if (imageViewReference != null && bitmap != null) {
            final ImageView imageView = imageViewReference.get();
            if (imageView != null) {
                imageView.setImageBitmap(bitmap);
            }
        }
    }
}
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top