2016-02-14 34 views
-1

這是代碼,圖像確實下載了,但問題是,我無法顯示,因爲沒有beeing能夠解決方法findViewByIdAndroid的 - 異步下載圖像,並將其顯示

public class ImageDownloader 
    extends AsyncTask<String, Integer, Bitmap> { 

protected void onPreExecute(){ 
    //Setup is done here 
} 
@Override 
protected Bitmap doInBackground(String... params) { 
    //this where i get the image using HttpURLConnection 
} 
protected void onProgressUpdate(Integer... params){ 
    //Update a progress bar here, or ignore it, it's up to you 
} 
protected void onPostExecute(Bitmap img){ 
    //here is the problem with findViewById beeing undefined 
    ImageView image_view = (ImageView) findViewById(R.id.remote_image); 

    if(image_view!=null && img!=null){ 
     image_view.setImageBitmap(img); 
    } 
} 

在我的主呢活動我叫裏面的OnCreate的ImageDownloader這樣的:

ImageDownloader download = new ImageDownloader(); 
download.execute("http://wanderingoak.net/bridge.png"); 

`

+0

是'remote_image'圖像視圖的ID在你的** **當前佈局? –

+0

明顯asynctask沒有這樣的方法...顯然你必須通過imageview引用或使你的asynctask實現內部非靜態類的類有這樣的方法...看起來像缺乏Java的基礎知識(不與android所有) – Selvin

+0

是的,它是位於content_main.xml裏面的ImageView名稱 – Akis

回答

3

的Android開發者頁面提供了許多有用的例子:http://developer.android.com/training/displaying-bitmaps/load-bitmap.html

我假設你正在處理多個下載圖像。但如果是這樣,那麼你的asyncTask應該檢查是否存在對imageView的引用。 你應該往這個方向:

public class ImageDownloader extends AsyncTask<String, Integer, Bitmap> { 

     private final WeakReference<ImageView> imageViewReference; 

     public ImageDownloader(ImageView imageView) { 
      imageViewReference = new WeakReference<ImageView>(imageView); 
     } 

     protected void onPreExecute() { 
      //Setup is done here 
     } 

     @Override 
     protected Bitmap doInBackground(String... params) { 
      //this where i get the image using HttpURLConnection 
     } 

     protected void onProgressUpdate(Integer... params) { 
      //Update a progress bar here, or ignore it, it's up to you 
     } 

     protected void onPostExecute(Bitmap bitmap) { 

      if (imageViewReference != null && bitmap != null) { 
       final ImageView imageView = imageViewReference.get(); 
       if (imageView != null) { 
        imageView.setImageBitmap(bitmap); 
       } 
      } 
     } 
    } 

然後調用例如:

@Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     ImageView iv = (ImageView) findViewById(R.id.myImageView); 
     new ImageDownloader(iv).execute("http://wanderingoak.net/bridge.png"); 
    } 
+0

這肯定會起作用並幫助我很多。如果我想在圖像下載時顯示Loader,該怎麼辦? – Akis

+1

@Akis_Tfs,只需使用[Picasso](http://square.github.io/picasso/),使用起來更簡單,並讓您輕鬆完成。 – JonasCz

3

要訪問findViewById你需要一個實際的看法。您只能在ActivityFragmentView類中使用該方法。

傳入參考,不要做的事情你的類不應該做的:

// add the constructor 
public ImageDownloader(ImageView image) { 
    mImage = image; 
} 

然後調用構造函數:

ImageDownloader download = new ImageDownloader((ImageView) findViewById(R.id.remote_image)); 

乾淨解決方案應另外使用一個WeakReference<ImageView>而不是一個ImageView,因爲在長時間運行的任務中保持引用會導致內存泄漏。

使用AsyncTask作爲非靜態內部類將而不是防止相同的問題,因爲它也將保持對活動的引用,導致所述內存泄漏。

+0

OP還必須小心,在試圖設置其圖像之前,ImageView不會被破壞。 –

+0

@ Code-Apprentice最糟糕的情況就是泄露活動?你是對的,一個'WeakReference'將會是一條路,但我不想超越OP。 –

+0

我並不是100%確定這裏的生命週期問題。如果「AsyncTask」啓動,用戶導航到另一個活動/片段,最後「AsyncTask」完成並設置「ImageView」的圖像,會發生什麼? 「ImageDownloader」中的引用是否有效? –

1

您必須聲明你imageview作爲一個字段在您的活動

在初始化它創建

private ImageView image_view; 

@Override 
public void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.main); 
    image_view = (ImageView) findViewById(R.id.remote_image); 
    ImageDownloader download = new ImageDownloader(); 
    download.execute("http://wanderingoak.net/bridge.png"); 
} 

你的異步任務:

public class ImageDownloader 
    extends AsyncTask<String, Integer, Bitmap> { 

    protected void onPreExecute(){ 
     //Setup is done here 
    } 

    @Override 
    protected Bitmap doInBackground(String... params) { 
     //this where i get the image using HttpURLConnection 
    } 

    protected void onProgressUpdate(Integer... params){ 
     //Update a progress bar here, or ignore it, it's up to you 
    } 

    protected void onPostExecute(Bitmap img){ 
     if(image_view!=null && img!=null){ 
      image_view.setImageBitmap(img); 
     } 
    } 
+0

你應該包含封閉的類聲明以使你的答案更清楚。 –

+0

@ Code-Apprentice是什麼類似這樣的? – meda

+0

哪個類包含'onCreate()'?那麼'ImageDownloader'如何訪問'image_view'? –