Sometimes delete function works sometimes not. I think the problem is with the notifyItemRemove or removing items inside the array. Worked on finding the bug for 3 days but in vain. This is the adapter class
public class ChecklistItems extends AppCompatActivity {
Toolbar toolbar;
RecyclerView recyclerView;
String content;
String status;
String[] contentSplit;
String[] statusSplit;
private ChecklistAdapter checklistAdapter;
DbHelper dbHelper;
List<ChecklistHelper> checks;
int id;
ChecklistHelper checklistHelper;
StringBuilder stringBuilderContent;
StringBuilder stringBuilderStatus;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_checklist_items);
toolbar = findViewById(R.id.tool_bar);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
recyclerView = findViewById(R.id.recycler_view_child);
id = getIntent().getIntExtra("id", 0);
content = getIntent().getStringExtra("content");
status = getIntent().getStringExtra("status");
contentSplit = content.split("\n");
statusSplit = status.split("\n");
checklistHelper = new ChecklistHelper();
dbHelper = new DbHelper(this);
checks = dbHelper.getChecklists();
recyclerView.setLayoutManager(new LinearLayoutManager(this));
checklistHelper = dbHelper.getChecklists(id);
String status = checklistHelper.getStatus();
String[] statusSplit = status.split("\n");
ArrayList<String> newStatusList = new ArrayList<>(Arrays.asList(statusSplit));
ArrayList<String> newContentList = new ArrayList<>(Arrays.asList(statusSplit));
checklistAdapter = new ChecklistAdapter(newStatusList, newContentList);
recyclerView.setAdapter(checklistAdapter);
}
public class ChecklistAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
ArrayList<String> newStatusList;
ArrayList<String> newContentList;
public ChecklistAdapter( ArrayList<String> newStatusList, ArrayList<String> newContentList) {
this.newStatusList = newStatusList;
this.newContentList = newContentList;
}
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
LayoutInflater layoutInflater = LayoutInflater.from(parent.getContext());
View view = layoutInflater.inflate(R.layout.checklist_layout_child, parent, false);
return new ChecklistChildViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, @SuppressLint("RecyclerView") int position) {
ChecklistChildViewHolder checklistChildViewHolder = (ChecklistChildViewHolder) holder;
checklistChildViewHolder.checkBox.setText(contentSplit[position]);
boolean state;
if (statusSplit[position].equals("1")) {
state = true;
checklistChildViewHolder.checkBox.setText(lineThrough(checklistChildViewHolder.checkBox.getText().toString()));
}
else
{
state = false;
checklistChildViewHolder.checkBox.setText(checklistChildViewHolder.checkBox.getText().toString());
}
checklistChildViewHolder.checkBox.setChecked(state);
checklistChildViewHolder.delete.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
doDelete(position);
}
});
}
@Override
public int getItemCount() {
return newStatusList.size();
}
public class ChecklistChildViewHolder extends RecyclerView.ViewHolder {
CheckBox checkBox;
ImageView delete, edit;
ChecklistChildViewHolder(@NonNull View itemView) {
super(itemView);
checkBox = itemView.findViewById(R.id.checkbox_child);
delete = itemView.findViewById(R.id.delete_child);
edit = itemView.findViewById(R.id.edit_child);
delete.setVisibility(View.INVISIBLE);
edit.setVisibility(View.INVISIBLE);
}
public void updateVisibility(boolean isEnableDelete){
if (isEnableDelete) {
delete.setVisibility(View.VISIBLE);
edit.setVisibility(View.VISIBLE);
}
else {
delete.setVisibility(View.INVISIBLE);
edit.setVisibility(View.INVISIBLE);
}
}
}
public int doDelete(int position) {
int idd = getIntent().getIntExtra("id", 0);
checklistHelper = dbHelper.getChecklists(idd);
String status = checklistHelper.getStatus();
String content = checklistHelper.getContent();
String[] statusSplit = status.split("\n");
String[] contentSplit = content.split("\n");
newStatusList = new ArrayList<>(Arrays.asList(statusSplit));
newContentList = new ArrayList<>(Arrays.asList(contentSplit));
newStatusList.remove(position);
newContentList.remove(position);
stringBuilderStatus = new StringBuilder();
stringBuilderContent = new StringBuilder();
for(String singleStatus : newStatusList) {
stringBuilderStatus.append(singleStatus);
stringBuilderStatus.append("\n");
}
for(String singleContent: newContentList){
stringBuilderContent.append(singleContent);
stringBuilderContent.append("\n");
}
String allStatus = stringBuilderStatus.toString();
String allContent = stringBuilderContent.toString();
dbHelper.updateChecklist(id,allStatus , allContent, DateTime.date(), DateTime.time(), System.currentTimeMillis());
if(allContent.length()==0) {
dbHelper.deleteChecklist(id);
finish();
}
notifyItemRemoved(position);
notifyItemChanged(position);
return newStatusList.size();
}
}
} I have used most of the (notify) functions which update the RecyclerView but none worked properly.
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_checklist_items);
toolbar = findViewById(R.id.tool_bar);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
recyclerView = findViewById(R.id.recycler_view_child);
id = getIntent().getIntExtra("id", 0);
content = getIntent().getStringExtra("content");
status = getIntent().getStringExtra("status");
contentSplit = content.split("\n");
statusSplit = status.split("\n");
checklistHelper = new ChecklistHelper();
dbHelper = new DbHelper(this);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
recyclerView.setAdapter(checklistAdapter);
checklistHelper = dbHelper.getChecklists(id);
String status = checklistHelper.getStatus();
String[] statusSplit = status.split("\n");
ArrayList<String> newStatusList = new ArrayList<>(Arrays.asList(statusSplit));
ArrayList<String> newContentList = new ArrayList<>(Arrays.asList(statusSplit));
checklistAdapter = new ChecklistAdapter(newStatusList, newContentList);
recyclerView.setAdapter(checklistAdapter);
}
CodePudding user response:
Your problem is notifyItemChanged(position);
. When you remove an item, you are changing the position of all other items beyond it.
You want to use notifyItemRangeChanged(position, newContentList.size());
as this will take into account the shifting positions.
You use notifyItemChanged(position);
if the content of the position has changed, but the position it self remains the same.
CodePudding user response:
you need to remove the lines in doDelete method:
newStatusList = new ArrayList<>(Arrays.asList(statusSplit));
newContentList = new ArrayList<>(Arrays.asList(contentSplit));
two lines will re-assign the new object and the underlay data may not locate in the same memory position as the old newStatusList and newContentList
And you can use Adapter.notifyDataSetChanged() instead of notifyItemXXX