我正在使用BaseAdapter来定制我的listview
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View view, ViewGroup parent) {
if (view == null) {
LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
view = inflater.inflate(R.layout.products_item, null);
}
FileBean file = (FileBean) ((ExtendedList) (Object) categories.get(groupPosition)).getItem(childPosition);
CheckBox checkBox = (CheckBox) view.findViewById(R.id.fileCheckBox);
if(checkBox != null){
if(mCheckBoxListener != null){
checkBox.setOnCheckedChangeListener(mCheckBoxListener);
}
checkBox.setChecked(file.isChecked());
Log.d("getcview", String.valueOf(file.isChecked() + " " + file.getName()
+ " " + groupPosition + " " + childPosition));
}
setProductDetails(file, view);
ViewHolder holder = new ViewHolder();
holder.groupPosition = groupPosition;
holder.childPosition = childPosition;
Log.d("exadapter", "Child " + file.getName());
view.setTag(holder);
return view;
}
您的问题与滚动列表视图时视图被回收有关。你必须每次重置正确的值为你的复选框(选中或未选中)。
你正在这样做,但是你的顺序是错误的,你的OnCheckListener被触发每次你重置复选框已选中/未选中的值(你先设置侦听器,然后你改变复选框的值)。
- 删除OnCheckListener
- 设置复选框值
- 再次添加监听器
正确顺序:
checkBox.setOnCheckedChangeListener(null);
checkBox.setChecked(file.isChecked());
checkBox.setOnCheckedChangeListener(mCheckBoxListener)
在baseadapter类中重写这两个方法:
@Override
public int getViewTypeCount() {
if (getCount() != 0)
return getCount();
return 1;
}
@Override
public int getItemViewType(int position) {
return position;
}
看看它是否有效。
我看到两个问题,
1 -将你的LayoutInflater移出getView方法,你在那里创建了很多垃圾。相反,应该创建一个实例变量来存储LayoutInflater,并在适配器的构造函数中创建它。(顺便说一句,这与混合无关)。
private LayoutInflater mInflater; //instance variable
public CustomAdapter(Context context, List<Item> items) {
//some code
mInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
2 -每次调用getView()时,都在上创建ViewHolder实例。移动这段代码:
ViewHolder holder = new ViewHolder();
holder.groupPosition = groupPosition;
holder.childPosition = childPosition;
Log.d("exadapter", "Child " + file.getName());
view.setTag(holder);
在converview的空检查中。您只希望在converView为null时(仅在新视图上)创建一个新的ViewHolder。
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View view, ViewGroup parent) {
//First, get the Tag from the converView
ViewHolder mHolder = (ViewHolder) view.getTag();
//Now check if the holder is null, rather than checking if the convertView is null.
if (mHolder == null) {
//init the holder code
view.setTag(mHolder); //only set the Tag if it's a new view.
}
同样,你以错误的方式使用ViewHolder模式,你应该使用ViewHolder来存储CheckBox,例如,所以你不必在每个getView调用上调用findViewById(R.id.fileCheckBox);
。
希望有帮助。