Save Checkbox state in RecyclerView

2020-08-01 06:51发布

I have a list of options with CheckBoxes in RecyclerView. When I tap on checkbox the state is changed, but after scrolling up and down the state of the checkboxes are losts.

How to save state of checkboxes ? I'm trying to change the state in adapter:

private void setAdapter() {
    if (mAdapter == null) {
        mAdapter = new FacetChildAdapter(mValues, getActivity(), query.getSpecValueAsString(mParentValue.getSlug())) {
            @Override
            protected void onCheckBoxRowClicked(CheckboxRow box, Value value, int adapterPosition) {
                if (type == FacetChildType.Brands) {
                    if (box.isChecked()) {
                        query.removeBrand(value);
                    } else {
                        query.addBrand(value);
                    }
                }

                else if (type == FacetChildType.Categories) {
                    if (box.isChecked()) {
                        query.removeCategory(value);
                    } else {
                        query.addCategory(value);
                    }
                }

                else if (type == FacetChildType.Deals) {
                    if (box.isChecked()) {
                        query.removeDealType(value);
                    } else {
                        query.addDealType(value);
                    }
                }

                else if (type == FacetChildType.Specifications) {
                    if (box.isChecked()) {
                        query.removeSpecification(mParentValue.getSlug(), value);
                    } else {
                        query.addSpecification(mParentValue.getSlug(), value);
                    }
                }

                box.setChecked(!box.isChecked());
                mHeading.setBackText(getResources().getString(R.string.apply));
            }

        };
        mRecyclerView.setAdapter(mAdapter);

    } else {
        mAdapter.setSource(query.getSpecValueAsString(mParentValue.getSlug()));
        mAdapter.refresh(mValues);
    }

}

FacetChildAdapter:

public class FacetChildAdapter extends GenericRecycleAdapter<Value, Holders.TextImageHolder> {
private String source;


public FacetChildAdapter(List<Value> list, Context context, String source) {
    super(list, context);
    this.source = source;
}

public void setSource(String source) {
    this.source = source;
}

@Override
protected void onItem(Value s) {

}

public Holders.TextImageHolder getCustomHolder(View v) {
    return new Holders.TextImageHolder(v) {
        @Override
        public void onCheckBoxRowClicked(CheckboxRow v) {
            FacetChildAdapter.this.onCheckBoxRowClicked(v, mList.get(getAdapterPosition()), getAdapterPosition());

        }
    };
}

protected void onCheckBoxRowClicked(CheckboxRow box, Value value, int adapterPosition) {

}

@Override
public int getLayout() {
    return R.layout.facet_child_row;
}

@Override
public void onSet(final Value item,final Holders.TextImageHolder holder) {
    holder.checkboxRow.setTitle(Html.fromHtml(item.getFullName()));
    holder.checkboxRow.setSubText("(" + String.valueOf(item.getCount()) + ")");
    holder.checkboxRow.setChecked(ShowProductsWithId.containsValueInValueStringLine(source, item.getSlug()));
    holder.checkboxRow.setDisabled(!item.isEnabled());

}

}

2条回答
仙女界的扛把子
2楼-- · 2020-08-01 07:17
class TeamNamesAdapter extends RecyclerView.Adapter<TeamNamesAdapter.ViewHolder>
        implements ItemTouchHelperAdapter, View.OnClickListener {

    private ArrayList<Person> people;

    public TeamNamesAdapter(TinyDB db) {
        people = new ArrayList<>();
        try {
            ArrayList<Object> peopleAsObjects = db.getListObject(PEOPLE, Person.class);
            for (Object obj : peopleAsObjects) {
                people.add((Person) obj);
            }

            if (db.getListObject(PEOPLE_ORDER, Person.class) == null) {
                db.putListObject(PEOPLE_ORDER, peopleAsObjects);
            }
        }
        catch (NullPointerException e) {
            return;
        }
    }

    @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.team_names_list_item, null);

        ViewHolder viewHolder = new ViewHolder(view);
        return viewHolder;
    }

    @Override
    public void onBindViewHolder(ViewHolder holder, int position) {
        Person curr = people.get(position);
        holder.name.setText(curr.name);
        holder.name.setChecked(curr.available);
    }

    @Override
    public int getItemCount() {
        return people.size();
    }

    public void addName(String name) {
        if(people.contains(name) || name.isEmpty())
            return;

        people.add(new Person(name, true));
        notifyDataSetChanged();
        update(true);
    }

    @Override
    public void onItemDismiss(int position) {
        people.remove(position);
        notifyItemRemoved(position);
        update(true);
    }

    @Override
    public void onItemMove(int fromPosition, int toPosition) {
        if (fromPosition < toPosition) {
            for (int i = fromPosition; i < toPosition; i++) {
                Collections.swap(people, i, i + 1);
            }
        }
        else {
            for (int i = fromPosition; i > toPosition; i--) {
                Collections.swap(people, i, i - 1);
            }
        }
        notifyItemMoved(fromPosition, toPosition);
        update(true);
        undoRandomizeButton.setEnabled(false);
    }

    @Override
    public void onClick(View v) {
        if (!(v instanceof CheckedTextView))
            return;

        CheckedTextView ctv = (CheckedTextView) v;
        ctv.toggle();

        String name = ctv.getText().toString();
        for (Person p : people) {
            if (p.name.equals(name)) {
                p.available = ctv.isChecked();
                update(true);
                return;
            }
        }
    }

    class ViewHolder extends RecyclerView.ViewHolder {
        CheckedTextView name;
        public ViewHolder(View itemView) {
            super(itemView);

            name = (CheckedTextView)itemView.findViewById(R.id.name_in_list);
            name.setOnClickListener(TeamNamesAdapter.this);
        }
    }
}

This is a recyclerview adapter for a list that holds a CheckedTextView. I save a class called Person, which contains a string and a bool. You situation is similar, as you can hold only booleans in the ArrayList (instead of Person), and on onBindViewHolder, set checkbox.isChecked to the boolean in that location. And you can set an View.OnClickerListener on the RecyclerView adapter, and set the ViewHolder onClickListener to YourAdapterName.this. And implement the method like I did, just disregard the Person stuff, just update your boolean You can see that on the adapters onBindViewHolder method,

查看更多
唯我独甜
3楼-- · 2020-08-01 07:23

It can Maintain in two ways:

1) Use the Hashmap to store the position of check box view. You can store the position and also store the Unique id of Particular view and then after in Adapter use can easily get the check box position in it.

2) When You can use the Getter setter class then you do create the one integer variable in it and then You can easily set the position in this variable like

  • When You can check the checkbox then variable value is 1
  • When You can uncheck the checkbox then variable value is 0

Maintain Your check box Position checked or unchecked in below ways.

查看更多
登录 后发表回答