0

我有我的列表視圖自定義適配器刷新圖像,在ListView它設置每個圖像的AsyncTask從背景中的web服務加載圖像,然後顯示它。但圖像不斷刷新,有時會在一段時間後加載錯誤的圖像(第一次加載它顯示正確的圖像)LogoLoader是asynctask。我的列表視圖保持與LogoLoader的AsyncTask

適配器類:

public class SearchResultAdapter extends ArrayAdapter<SearchResultRowItem> { 

Context context; 
private MainActivity main; 

public SearchResultAdapter(Context context, int resourceId, List<SearchResultRowItem> items,MainActivity main) { 
    super(context, resourceId, items); 
    this.context = context; 
    this.main = main; 
} 

/*private view holder class*/ 
private class ViewHolder { 
    ImageView imageView; 
    TextView txtTitle; 
    TextView txtDesc; 
    TextView txtAdres; 
    TextView txtAfstand; 
} 

public View getView(int position, View convertView, ViewGroup parent) { 
    ViewHolder holder = null; 
    SearchResultRowItem rowItem = getItem(position); 

    LayoutInflater mInflater = (LayoutInflater) context 
      .getSystemService(Activity.LAYOUT_INFLATER_SERVICE); 
    if (convertView == null) { 
     convertView = mInflater.inflate(R.layout.listitem, null); 
     holder = new ViewHolder(); 
     holder.txtDesc = (TextView) convertView.findViewById(R.id.desc); 
     holder.txtTitle = (TextView) convertView.findViewById(R.id.title); 
     holder.txtAdres = (TextView) convertView.findViewById(R.id.adres); 
     holder.txtAfstand = (TextView) convertView.findViewById(R.id.afstand); 
     holder.imageView = (ImageView) convertView.findViewById(R.id.logo); 
     convertView.setTag(holder); 
    } else { 
     holder = (ViewHolder) convertView.getTag(); 
    } 


    holder.txtDesc.setText(Html.fromHtml(rowItem.getDesc())); 
    holder.txtTitle.setText(rowItem.getTitle()); 
    holder.txtAdres.setText(rowItem.getAdres()); 
    holder.txtAfstand.setText(rowItem.getAfstand()); 

    if (holder.imageView != null && rowItem.hasLogo()) { 
     holder.imageView.setImageResource(R.drawable.loader); 
     LogoLoader logoLoader = new LogoLoader(holder.imageView, rowItem.getOrganisatieId(), 100, 100, main); 
     logoLoader.execute(); 
    } 

    convertView.setBackgroundColor(position % 2 == 0 ? Color.WHITE : Color.parseColor("#F8F8F8")); 
    return convertView; 
} 

}

LogoLoader類:

public class LogoLoader extends AsyncTask<Void, Void, String> { 

private ImageView imageView; 
private UUID OrganisationGuid; 
private int maxWidth; 
private int maxHeight; 

private MainActivity main; 

public LogoLoader(ImageView imageView, UUID OrganisationGuid, int maxHeight, int maxWidth,MainActivity main) { 
    this.imageView = imageView; 
    this.OrganisationGuid = OrganisationGuid; 
    this.maxHeight = maxHeight; 
    this.maxWidth = maxWidth; 
    this.main = main; 
} 

@Override 
protected String doInBackground(Void... params) { 
    WebserviceAdapter task = new WebserviceAdapter(
      "api/Logo/GetLogos?ids="+OrganisationGuid.toString()+ 
      "&maxWidth="+Integer.toString(maxWidth)+ 
      "&maxHeight="+Integer.toString(maxHeight)); 
    return task.result; 
} 

@Override 
protected void onPostExecute(String result){ 
    try { 
     JSONObject json = new JSONObject(result); 

     JSONArray jsonArray = json.getJSONArray("Results"); 
     JSONObject imageObject = jsonArray.getJSONObject(0); 

     byte[] imageData = Base64.decode(imageObject.getString("Data").getBytes(), Base64.DEFAULT); 
     Drawable logoDrawable = null; 
     if (imageData != null) { 
      Bitmap logoBitmap = BitmapFactory.decodeByteArray(imageData, 0, 
        imageData.length); 
      logoDrawable = new BitmapDrawable(main.getResources(), logoBitmap); 
     } 
     imageView.setImageDrawable(logoDrawable); 
    } catch (JSONException e) { 
     imageView.setImageDrawable(null); 
    } 

} 

}

回答

1

重複加載是由於listview的getView方法被定期多次調用,並且加載錯誤的圖像是由於重新調用視圖的功能。 ListView嘗試重用項目視圖以節省內存並提高效率。第一個問題的解決方案是隻加載一次圖像並將其保存在某處(如果圖像是縮略圖,則存儲在內存中,如果圖像大於SD卡)。並解決了第二個問題是使用

holder.imageView.setImageBitmap(null); 

if (holder.imageView != null && rowItem.hasLogo()) {之前,使得每當一個視圖獲取呈現,它具有裝載沒有先前圖像。 我希望你明白我的觀點。也可以使用Universal Image Loader庫來加載圖像。我已經使用它,它像一個魅力。

+0

謝謝你爲我做的伎倆,我會稍後做緩存! –

0

,我可以推薦不同的方式來加載圖像和工程就像一個魅力:Android查詢。

你可以從這裏下載jar文件:http://code.google.com/p/android-query/downloads/list

AQuery androidAQuery=new AQuery(this); 

舉個例子:

androidAQuery.id(YOUR IMAGEVIEW).image(YOUR IMAGE TO LOAD, true, true, getDeviceWidth(), ANY DEFAULT IMAGE YOU WANT TO SHOW); 

這是非常快速和準確,並使用此你可以找到更多的功能,如動畫時裝載;獲取位圖,如果需要的話;等

+0

我很欣賞你的時間回答,但我想知道我做錯了什麼,所以我可以從中吸取教訓。 –

+0

你的通話是在後臺運行的,所以它將會是一項單獨的任務,並且你膨脹你的數據是另一項任務,所以兩者都沒有並行運行。我已經給出了一個完美的解決方案,你可以從你的應用程序中保存一個asynctask,android查詢將像魅力一樣工作。去嘗試一下。 –