我有listview的文字和复选框。滚动列表视图时,该复选框表现得很奇怪。这似乎是一个回收问题。无论如何,我尝试了一些类似帖子中提出的各种选项,但没有一个适合我。我尝试设置并获得其中一个帖子中建议的标记位置,但运气不好。我在我的活动文件中使用自定义适配器作为列表视图。以下是一些代码片段; 活动类:
lv = (ListView) findViewById(R.id.itemdisplay_listview);
lv.setAdapter(new CustomAdapter(this, itemNames, tableNo));
自定义适配器:
private class CustomAdapter extends BaseAdapter {
private List<String> mListItems;
private LayoutInflater mLayoutInflater;
ViewHolder holder;
int a = 1;
public CustomAdapter(Context context, List<String> arrayList,
String table) {
tableNumber = table;
mListItems = arrayList;
// get the layout inflater
mLayoutInflater = (LayoutInflater) context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
}
@Override
public int getCount() {
// TODO Auto-generated method stub
return mListItems.size();
}
@Override
public Object getItem(int position) {
// TODO Auto-generated method stub
return null;
}
@Override
public long getItemId(int arg0) {
// TODO Auto-generated method stub
return 0;
}
private class ViewHolder {
TextView itemName, quantity;
CheckBox checkbox;
ImageButton addBtn, minusBtn;
}
@Override
public View getView(int position, View convertview, ViewGroup viewGroup) {
// create a ViewHolder reference
// check to see if the reused view is null or not, if is not null
// then
// reuse it
if (convertview == null) {
holder = new ViewHolder();
convertview = mLayoutInflater.inflate(
R.layout.itemdisplay_list, null);
holder.itemName = (TextView) convertview
.findViewById(R.id.itemdisplaylist_name);
holder.addBtn = (ImageButton) convertview
.findViewById(R.id.itemdisplaylist_add);
holder.minusBtn = (ImageButton) convertview
.findViewById(R.id.itemdisplaylist_minus);
holder.quantity = (TextView) convertview
.findViewById(R.id.itemdisplaylist_quantity);
holder.checkbox = (CheckBox) convertview
.findViewById(R.id.itemdisplaylist_cbox);
// holder.checkbox.setTag(position);
// the setTag is used to store the data within this view
convertview.setTag(holder);
} else {
// the getTag returns the viewHolder object set as a tag to the
// view
holder = (ViewHolder) convertview.getTag();
}
holder.checkbox.setOnClickListener(checkListener);
doneBtn.setEnabled(true);
holder.minusBtn.setImageResource(R.drawable.minus);
holder.quantity.setText(String.valueOf(a));
holder.addBtn.setImageResource(R.drawable.add);
holder.addBtn.setOnClickListener(addBtnClick);
holder.minusBtn.setOnClickListener(minusBtnClick);
String stringItem = mListItems.get(position);
if (stringItem != null) {
if (holder.itemName != null) {
// set the item name on the TextView
holder.itemName.setText(stringItem);
}
}
// this method must return the view corresponding to the data at the
// specified position.
return convertview;
}
private OnClickListener checkListener = new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
/*doneBtn.setOnClickListener(doneBtnClick);*/
View view = (View) v.getParent();
CheckBox cb = (CheckBox) view
.findViewById(R.id.itemdisplaylist_cbox);
TextView tv = (TextView) view
.findViewById(R.id.itemdisplaylist_name);
TextView tv1 = (TextView) view
.findViewById(R.id.itemdisplaylist_quantity);
if (cb.isChecked()) {
map.put(tv.getText().toString(), tv1.getText().toString());
} else {
for (Iterator<Map.Entry<String, String>> it = map
.entrySet().iterator(); it.hasNext();) {
Map.Entry<String, String> entry = it.next();
String item = entry.getKey();
if ((tv.getText().toString()).equals(item)) {
it.remove();
}
}
}
}
};
我已经挣扎了很长时间。请指教。感谢。
答案 0 :(得分:1)
如果您说 100个CB 的数据,那么您还需要存储他们的checked/unchecked state
。假设一个包含100个元素的布尔数组 CheckedStatus [100] 。在GetView中
if(CheckedStatus[position] == true) {
// check the check box
} else {
// uncheck it
}.
该位置是GetView函数中收到的位置
答案 1 :(得分:1)
在自定义列表视图适配器中调用 setChecked 后调用 setOnCheckedChangeListener 。这样您就可以切断指向回收视图中的老听众。
答案 2 :(得分:0)
将boolean checked
变量添加到ViewHolder
。在checkListener
中更改它。然后在getView
添加holder.checkbox.setChecked(holder.checked)
。
希望它有所帮助。
答案 3 :(得分:0)
您需要使用某种模型对象来保留复选框的状态,然后使用该模型而不是简单的String作为数据结构:
// Oversimplified, but adiquate for our purposes.
public class ItemModel
{
public String text;
public boolean isChecked;
}
然后,不是将一个字符串数组传递给适配器,而是传递一个ItemModels
数组。
您需要的字符串将是text参数,然后您必须将复选框值设置为isChecked
值。
一旦复选框的状态发生变化,剩下的就是更改isChecked
值。
在初始化if(convertView == null)
参数后,在holder.checkbox
块内的getItem方法内执行此操作。另外,请务必在方法参数position
中生成final
变量。
以下是代码:
holder.checkbox.setOnCheckedChangeListener(new CheckBox.OnCheckedChangeListener()
{
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked)
{
mListItems.get(position).isChecked = isChecked;
}
});
希望这会有所帮助:)
答案 4 :(得分:0)
我的猜测是你被循环问题所困扰。
我建议你先使用else语句中的以下内容删除监听器
holder.checkbox.setOnCheckedChangeListener(null);
在您的代码中如下:
} else {
// the getTag returns the viewHolder object set as a tag to the
// view
holder = (ViewHolder) convertview.getTag();
holder.checkbox.setOnCheckedChangeListener(null);
}