java - 交换列表中的项目后,自定义列表适配器和 ViewHolder 模式出现问题

标签 java android android-listview custom-adapter

Item 是一个自定义类,其中包含用于标题的字符串和用于保存复选框状态的枚举。

private final List<Item> mItems = new ArrayList<Item>();

假设我的数组列表中有 3 个项目,我想交换第 2 项和第 3 项的位置。

// Move item down
public void moveDown(int position){
    if ( position < mItems.size() -1 ) {
        Collections.swap(mItems, position, position + 1);
        notifyDataSetChanged();
    }
}

我可以看到,在调试mItems时,项目已正确交换。

接下来,将为每个数组列表项调用 getView 函数。

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

    final Item item = mItems.get(position);

    View myView = convertView;
    if ( null == myView )
    {
        LayoutInflater inflater =  LayoutInflater.from(mContext);
        myView = inflater.inflate(R.layout.item, parent, false);

        ViewHolder  viewHolder  = new ViewHolder();
        viewHolder.title        = (TextView)       myView.findViewById(R.id.titleView);
        viewHolder.statusView   = (CheckBox)       myView.findViewById(R.id.statusCheckBox);

        myView.setTag(viewHolder);
        myView.setLongClickable(true);
    }

    final ViewHolder myHolder = (ViewHolder) myView.getTag() ;

    // Display Title in TextView
    myHolder.title.setText(item.getTitle());

    // Set up Status CheckBox
    if ( item.getStatus() == Status.NOTDONE )
    {
        myHolder.statusView.setChecked(false);
    }
    else
    {
        myHolder.statusView.setChecked(true);
    }

    //  Must also set up an OnCheckedChangeListener, which is called when the user toggles the status checkbox
    myHolder.statusView
            .setOnCheckedChangeListener(new OnCheckedChangeListener() {
                @Override
                public void onCheckedChanged(CompoundButton buttonView, boolean isChecked)
                {
                    if ( isChecked == true ) {
                        item.setStatus(Status.DONE);
                    }
                    else
                    {
                        item.setStatus(Status.NOTDONE);
                    }
                }
            });

    return myView;

}

现在,说一开始,这些是项目

项目:1 |标题 A |复选框状态:未选中
项目: 2 |标题 B |复选框状态:未选中
项目: 3 |标题 C |复选框状态:已选中

交换后,我们得到了这个:

项目:1 |标题 A |复选框状态:未选中
项目: 2 |标题 C |复选框状态:已选中
项目: 3 |标题 B |复选框状态:未选中

第二次 getView 被调用,当复选框状态被选中时,将调用:

myHolder.statusView.setChecked(true);

但奇怪的是:在那之后,我看到了对

的调用
 myHolder.statusView
   .setOnCheckedChangeListener(new OnCheckedChangeListener() {
       @Override
       public void onCheckedChanged(CompoundButton buttonView, boolean isChecked)
       {
           if ( isChecked == true ) {
               item.setStatus(Status.DONE);
           }
           else
           {
               item.setStatus(Status.NOTDONE);
           }
       }
   });

项目指向第三项(标题“B”)和相关复选框,因此我最终错误地将项目3的状态设置为“完成”

在将 onCheckedChanged 监听器设置为检查项目 3 后,我应该如何防止为项目 3 调用 onCheckedChanged 监听器?提前致谢。

最佳答案

你可以尝试在类中而不是在 getview() 中创建 viewholder

关于java - 交换列表中的项目后,自定义列表适配器和 ViewHolder 模式出现问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30078236/

相关文章:

java - 将java小程序转换为java应用程序

android - ListView 适配器使 Activity 崩溃

java - java中的Unicode编码

java - 了解 Spring 事务边界

android - 从 ContentResolver.query() 获取 URI

android - 自定义 Alertdialog 宽度大于布局 xml 中显示的宽度

android - ListView项目背景颜色

android - 我可以使 ListView 项目不可选吗?

java - Mockito、JUnit、Hamcrest、版本控制

android - 在android中的sqlite中使用更新语句