我有一个RecyclerView
,显示项目列表。每行的ViewHolder
包含一个删除按钮,用于删除该行。如果我删除最后一行并在消失的行上快速点击,我的应用将崩溃,因为第二次点击事件已传递到删除的行。我很惊讶android提供了第二个事件。在尝试向boolean isDeleted
子类中添加类似ViewHolder
之类的内容之前,我想知道:在这种情况下,我是否在做其他错误的事情?
class MyAdapter extends RecyclerView.Adapter<MyViewHolder>
implements ItemTouchHelperAdapter {
List<Segment> segments;
MyAdapter(List<Segment> objs) {
this.segments = objs;
}
@Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
LinearLayout v = (LinearLayout) LayoutInflater.from(parent.getContext())
.inflate(R.layout.segment_edit_row, parent, false);
MyViewHolder vh = new MyViewHolder(v);
return vh;
}
@Override
public void onBindViewHolder(MyViewHolder holder, int position) {
Segment seg = segments.get(position);
holder.textView.setText(seg.getTitle());
holder.dragHandle.setOnTouchListener((v, event) -> {
if (MotionEventCompat.getActionMasked(event) ==
MotionEvent.ACTION_DOWN) {
onStartDrag(holder);
}
return false;
});
holder.deleteButton.setOnClickListener(v -> {
segments.remove(position);
notifyItemRemoved(position);
});
View.OnClickListener editExerciseListener = v -> {
Segment segment = segments.get(position);
startEditSegmentActivity(segment, position);
};
holder.textView.setOnClickListener(editExerciseListener);
holder.arrow.setOnClickListener(editExerciseListener);
}
deleteButton
处理程序首先运行,然后运行editExerciseListener
,而position
现已超出范围。
更新
几个人建议我打电话给notifyDataSetChanged
。如果您可以通过调用notifyItemRemoved
来描述更改,则Android文档特别建议不要这样做。
那些文档错了吗?
答案 0 :(得分:1)
每次执行删除操作时,您都必须重新加载recyclerview: 您可以通过添加以下行来完成此操作:
select value, min(fromdate) as fromdate, max(todate) as todate
from (select t.*,
sum(case when prev_todate >= dateadd(day, -1, fromdate)
then 0 -- overlap, so this does not begin a new group
else 1 -- no overlap, so this does begin a new group
end) over
(partition by value order by fromdate) as grp
from (select t.*,
max(todate) over (partition by value
order by fromdate
rows between unbounded preceding and 1 preceding
) as prev_todate
from t
) t
) t
group by value, grp
order by value, min(fromdate);
答案 1 :(得分:0)
将代码更新为:
View.OnClickListener editExerciseListener = v -> {
if(position >= segments.size()){
//index not exists
}else{
// index exists
Segment segment = segments.get(position);
startEditSegmentActivity(segment, position);
}
};
答案 2 :(得分:0)
首次通话notifyItemRemoved(position);
然后致电segments.remove(position);
答案 3 :(得分:0)
前一段时间,我遇到了类似情况。当我单击recyclerview项目时,该应用程序崩溃了,而该项目正在被删除并且正在进行删除动画(不到一秒钟)。在这种情况下,您的应用容易遭受潜在崩溃的持续时间非常短。
我做什么:
当应用崩溃时,我记录了position(holder.getAdapterPosition())的值。令人惊讶的是,每次发生崩溃时,该值为-1。最终,我编写了一个自定义版本的notifyItemRemoved。在这里:
private void notifyItemRemovedModified(int pos_removed){
if(pos_removed!=-1){
// your list is your list
yourList.remove(pos_removed);
notifyItemRemoved(pos_removed);
}
}