列表查看项目回收

时间:2013-11-23 06:31:16

标签: android android-listview android-viewpager

我有一个包含14行的列表视图,每个项目都是View Pager。这是我的getView()方法:

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder = null;
        FindMyBeerPager findMyBeerPager;
        if(convertView==null){
            holder = new ViewHolder();
            LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = inflater.inflate(R.layout.beer_list_item, parent,false);

            findMyBeerPager = new FindMyBeerPager(context, findBeerDataList.get(position));
            holder.beerPager = (ViewPager)convertView.findViewById(R.id.mypager);
            holder.beerPager.setAdapter(findMyBeerPager);

            System.out.println("Recycling view position"+position);
            holder.beerPager.setTag(findMyBeerPager);

            convertView.setTag(holder);
        }
        else{
            holder = (ViewHolder) convertView.getTag();
            System.out.println("Recycled"+position);
        }

        return convertView; 
    }
}

class ViewHolder{
    ViewPager beerPager;
}

问题:我面临的问题是,当我向下滚动列表视图时,我没有得到更多的行值,即列表视图与之前的值一起回收。我不知道为什么会这样。我必须发送View Pager(每个位置的数据项)。在向下滚动之前,一切正常。

3 个答案:

答案 0 :(得分:3)

将getView更改为

 @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder = null;
        FindMyBeerPager findMyBeerPager;
        if(convertView==null){
            holder = new ViewHolder();
            LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = inflater.inflate(R.layout.beer_list_item, parent,false);
            holder.beerPager = (ViewPager)convertView.findViewById(R.id.mypager);
            convertView.setTag(holder);
        }
        else{
            holder = (ViewHolder) convertView.getTag();
            }

         findMyBeerPager = new FindMyBeerPager(context, findBeerDataList.get(position));
             holder.beerPager.setTag(findMyBeerPager);
             holder.beerPager.setAdapter(findMyBeerPager);
        return convertView; 
    }
}

您可以将LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);移动到适配器类的构造函数。

还使用Log进行日志记录而不是System.out.println

How ListView's recycling mechanism works

ViewPager and OnItemClickListener in ListView

在上面的链接中查看Dianne Hackborn的答案。

答案 1 :(得分:1)

您可以尝试在esle块中设置适配器吗?

  @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewHolder holder = null;
        FindMyBeerPager findMyBeerPager;
        if(convertView==null){
            holder = new ViewHolder();
            LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
            convertView = inflater.inflate(R.layout.beer_list_item, parent,false);

            holder.beerPager = (ViewPager)convertView.findViewById(R.id.mypager);

            System.out.println("Recycling view position"+position);
            holder.beerPager.setTag(findMyBeerPager);

            convertView.setTag(holder);
        }
        else{
            holder = (ViewHolder) convertView.getTag();
            System.out.println("Recycled"+position);
            findMyBeerPager = new FindMyBeerPager(context, findBeerDataList.get(position));
            holder.beerPager.setAdapter(findMyBeerPager);
        }

        return convertView; 
    }
}

答案 2 :(得分:1)

它可以在不设置每个getView()的参数的情况下工作,但为此你需要扩展BaseAdapter并重载以下方法:

@Override
public boolean hasStableIds() {
    return true;
}

@Override
public int getCount() {
    return items.size();
}

@Override
public long getItemId(int position) {
    return position;
}

@Override
public int getItemViewType(int position) {
    return position;
}

@Override
public int getViewTypeCount() {
    return MAXIMUM_NUMBER_OF_ITEMS_IN_LIST_VIEW;
}

通过这种方式,BaseAdapter将为每个元素保留在回收器的单独视图中。对于每个项目都有自定义视图的短列表,这是一个很好的解决方案。 (但是当膨胀的观点相同时也可以工作)

请注意,getViewTypeCount()仅在构造函数上调用一次,因此BaseAdapter必须知道您的列表将包含多少项。

这个想法的关键是getItemViewType()为每个项目返回不同的值。多亏了getView()将获得每个列表项的唯一convertView。

然后你可以完全跳过条件(convertView!= null)并将所有代码放入(convertView == null){}