Listview的BaseAdapter没有为索引9

时间:2017-08-05 22:22:40

标签: android listview android-fragments

我正在尝试在Android中创建一个listview,就像你可以在whatsapp中看到你的聊天一样。我的片段中有一个列表视图,我从Firebase获取数据以放入列表中。前10个项目非常好,但在这10个项目之后,不再调用getview()函数。我得到了错误文本的按钮(来自其他组的名称),但是如果我点击它们,就会在其中显示正确的名称。

代码段:
片段:

rowItems = new ArrayList<RowItem>();

final CustomAdapter adapter = new CustomAdapter(getContext(), rowItems);
mylistview = (ListView) rootView.findViewById(R.id.LVGroups);
mylistview.setAdapter(adapter);
mylistview.setOnItemClickListener(this);  
        ValueEventListener valueEventListener = new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                String name = dataSnapshot.child("name").getValue(String.class);
                Log.d("TAG", "name: " + name);
                //Create new item in the rowItems arraylist to add to the listview
                RowItem item = new RowItem(name, R.mipmap.ic_challenger_black, "placeholder");
                rowItems.add(item);
                adapter.notifyDataSetChanged();
            }

            @Override
            public void onCancelled(DatabaseError databaseError) {}
        };  

RowItem:

public class RowItem {

    private String member_name;
    private int profile_pic_id;
    private String status;

    public RowItem(String member_name, int profile_pic_id, String status) {
        this.member_name = member_name;
        Log.d("TAG", "member_name: " + this.member_name);
        this.profile_pic_id = profile_pic_id;
        this.status = status;
    }

    public String getMember_name() {
        return this.member_name;
    }

    public void setMember_name(String member_name) {
        this.member_name = member_name;
    }

    public int getProfile_pic_id() {
        return profile_pic_id;
    }

    public void setProfile_pic_id(int profile_pic_id) {
        this.profile_pic_id = profile_pic_id;
    }

    public String getStatus() {
        return status;
    }

    public void setStatus(String status) {
        this.status = status;
    }
} 

CustomAdapter:

public class CustomAdapter extends BaseAdapter {
    Context context;
    List<RowItem> rowItems;

    CustomAdapter(Context context, List<RowItem> rowItems) {
        this.context = context;
        this.rowItems = rowItems;
    }

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

    @Override
    public Object getItem(int position) {
        return rowItems.get(position);
    }

    @Override
    public long getItemId(int position) {
        return rowItems.indexOf(getItem(position));
    }

    /* private view holder class */
    private class ViewHolder {
        ImageView profile_pic;
        TextView member_name;
        TextView status;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {

        ViewHolder holder = null;

        LayoutInflater mInflater = (LayoutInflater) context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);


        if (convertView == null) {

            convertView = mInflater.inflate(R.layout.list_item_groups, null);
            holder = new ViewHolder();

            holder.member_name = (TextView) convertView
                    .findViewById(R.id.name);
            holder.profile_pic = (ImageView) convertView
                    .findViewById(R.id.pic);
            holder.status = (TextView) convertView.findViewById(R.id.sta);

            RowItem row_pos = rowItems.get(position);

            holder.profile_pic.setImageResource(row_pos.getProfile_pic_id());
            holder.member_name.setText(row_pos.getMember_name());
            Log.d("TAG", "holder.member_name: " + row_pos.getMember_name() + " " + position);
            holder.status.setText(row_pos.getStatus());

            convertView.setTag(holder);
        } else {
            holder = (ViewHolder) convertView.getTag();
        }

        return convertView;
    }
}

customadapter中的打印件打印到第10个元素(索引9)。对于最后2,它没有被调用。

1 个答案:

答案 0 :(得分:2)

您需要在if else语句中设置textView文本和imageView源。您只在视图初始化中设置它们。滚动后它们不会更改,因为convertView在滚动后不为null。您的适配器将使用过去的convertViews和过去的值。您只需要设置视图内容。

@Override
public View getView(int position, View convertView, ViewGroup parent) {

    ViewHolder holder = null;

    LayoutInflater mInflater = (LayoutInflater) context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);


    if (convertView == null) {

        convertView = mInflater.inflate(R.layout.list_item_groups, null);
        holder = new ViewHolder();

        holder.member_name = (TextView) convertView
                .findViewById(R.id.name);
        holder.profile_pic = (ImageView) convertView
                .findViewById(R.id.pic);
        holder.status = (TextView) convertView.findViewById(R.id.sta);

        convertView.setTag(holder);
    } else {
        holder = (ViewHolder) convertView.getTag();
    }

RowItem row_pos = rowItems.get(position);

        holder.profile_pic.setImageResource(row_pos.getProfile_pic_id());
        holder.member_name.setText(row_pos.getMember_name());
        Log.d("TAG", "holder.member_name: " + row_pos.getMember_name() + " " + position);
        holder.status.setText(row_pos.getStatus());

    return convertView;
}

编辑:还有一个建议。在您的班级中定义此变量:

LayoutInflater mInflater;

在自定义适配器的构造函数中调用它:

mInflater = (LayoutInflater) context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);

并在getView方法中删除inflater的初始化。 ListView是如此重要的类。不要厌倦你的getView方法,因为每个列表项都在屏幕上调用。

查看以下链接。这就是ListView回收的工作原理:

How ListView's recycling mechanism works