Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Best way to handle multiple getView calls from inside an Adapter

I have a ListView with custom ArrayAdapter. Each of the row in this ListView has an icon and some text. These icons are downloaded in background,cached and then using a callback, substituted in their respective ImageViews. The logic to get a thumbnail from cache or download is triggered every time getView() runs.

Now, according to Romain Guy:

"there is absolutely no guarantee on the order in which getView() will be called nor how many times."

I have seen this happen, for a row of size two getView() was being called six times!

How do I change my code to avoid duplicate thumbnail-fetch-requests and also handle view recycling?

Thanks.

like image 746
Samuh Avatar asked May 20 '10 10:05

Samuh


2 Answers

My understanding is that you need to use the ViewHolder design pattern here. Just using a returned convertView can lead to reuse of a previous view (with some other image assigned in this case).

public class ImageAdapter extends ArrayAdapter<String> {

  // Image adapter code goes here.

  private ViewHolder {
    public ImageView imageView;
    public String url;
  }

  @Override
  public View getView(final int position, View convertView, ViewGroup parent) {
    View view = null;
    ViewHolder viewHolder;
    String url = getUrl(position);
    if (convertView == null) {
      // There was no view to recycle. Create a new view.
      view = inflator.inflate(R.layout.image_layout, parent, false);
      viewHolder = new ViewHolder();
      viewHolder.imageView = (ImageView) view.findViewById(R.id.image_view);
      viewHolder.url = url;
      view.setTag(viewHolder);
    } else {
      // We got a view that can be recycled.
        view = convertView;
        viewHolder = ((ViewHolder) view.getTag());
        if (viewHolder.url.equals(url)) {
          // Nothing to do, we have the view with the correct info already.
          return view;
        }
    }

    // Do work to set your imageView which can be accessed by viewHolder.imageView

    return view;
  }
}
like image 54
wislo Avatar answered Oct 21 '22 11:10

wislo


I m experiancing the same issue i change the layout_height of listView to match_parent resolve my issue.

like image 26
Muhammad Aamir Ali Avatar answered Oct 21 '22 13:10

Muhammad Aamir Ali