RecyclerView侧滑交互优化:实现点击删除+左侧编辑按钮
实现RecyclerView侧滑显示编辑、删除按钮(点击触发操作)
我来帮你调整代码,实现侧滑只显示操作按钮、点击才执行删除/编辑的需求,具体分这几步来做:
一、修改SwipeToActionCallback类,支持双向侧滑并绘制按钮
首先我们要重构原来的回调类,让它支持左右双向侧滑,并且只绘制按钮不自动执行删除逻辑:
public abstract class SwipeToActionCallback extends ItemTouchHelper.Callback { private Context context; private Paint clearPaint; private ColorDrawable leftBackground; // 编辑按钮背景 private ColorDrawable rightBackground; // 删除按钮背景 private int editBgColor; private int deleteBgColor; private Drawable editDrawable; private Drawable deleteDrawable; private int intrinsicWidth; private int intrinsicHeight; public SwipeToActionCallback(Context context) { this.context = context; // 初始化编辑相关资源 leftBackground = new ColorDrawable(); editBgColor = Color.parseColor("#F4B400"); editDrawable = ContextCompat.getDrawable(context, R.drawable.ic_edit_white_24dp); // 初始化删除相关资源 rightBackground = new ColorDrawable(); deleteBgColor = Color.parseColor("#DB3236"); deleteDrawable = ContextCompat.getDrawable(context, R.drawable.ic_delete_white_24dp); clearPaint = new Paint(); clearPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR)); if (editDrawable != null) { intrinsicWidth = editDrawable.getIntrinsicWidth(); intrinsicHeight = editDrawable.getIntrinsicHeight(); } } @Override public int getMovementFlags(@NonNull RecyclerView recyclerView, @NonNull RecyclerView.ViewHolder viewHolder) { // 支持左右双向侧滑 return makeMovementFlags(0, ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT); } @Override public boolean onMove(@NonNull RecyclerView recyclerView, @NonNull RecyclerView.ViewHolder viewHolder, @NonNull RecyclerView.ViewHolder target) { return false; } // 移除自动删除逻辑,这个方法留空 @Override public void onSwiped(@NonNull RecyclerView.ViewHolder viewHolder, int direction) {} @Override public void onChildDraw(@NonNull Canvas canvas, @NonNull RecyclerView recyclerView, @NonNull RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, boolean isCurrentlyActive) { super.onChildDraw(canvas, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive); View itemView = viewHolder.itemView; int itemHeight = itemView.getHeight(); boolean isCancelled = dX == 0 && !isCurrentlyActive; if (isCancelled) { clearCanvas(canvas, itemView.getLeft(), itemView.getTop(), itemView.getRight(), itemView.getBottom()); super.onChildDraw(canvas, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive); return; } // 根据侧滑方向绘制对应按钮 if (dX < 0) { // 左滑:显示右侧删除按钮 rightBackground.setColor(deleteBgColor); rightBackground.setBounds(itemView.getRight() + (int) dX, itemView.getTop(), itemView.getRight(), itemView.getBottom()); rightBackground.draw(canvas); // 绘制删除图标 int deleteIconTop = itemView.getTop() + (itemHeight - intrinsicHeight) / 2; int deleteIconMargin = (itemHeight - intrinsicHeight) / 2; int deleteIconLeft = itemView.getRight() - deleteIconMargin - intrinsicWidth; int deleteIconRight = itemView.getRight() - deleteIconMargin; int deleteIconBottom = deleteIconTop + intrinsicHeight; if (deleteDrawable != null) { deleteDrawable.setBounds(deleteIconLeft, deleteIconTop, deleteIconRight, deleteIconBottom); deleteDrawable.draw(canvas); } } else if (dX > 0) { // 右滑:显示左侧编辑按钮 leftBackground.setColor(editBgColor); leftBackground.setBounds(itemView.getLeft(), itemView.getTop(), itemView.getLeft() + (int) dX, itemView.getBottom()); leftBackground.draw(canvas); // 绘制编辑图标 int editIconTop = itemView.getTop() + (itemHeight - intrinsicHeight) / 2; int editIconMargin = (itemHeight - intrinsicHeight) / 2; int editIconLeft = itemView.getLeft() + editIconMargin; int editIconRight = itemView.getLeft() + editIconMargin + intrinsicWidth; int editIconBottom = editIconTop + intrinsicHeight; if (editDrawable != null) { editDrawable.setBounds(editIconLeft, editIconTop, editIconRight, editIconBottom); editDrawable.draw(canvas); } } super.onChildDraw(canvas, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive); } private void clearCanvas(Canvas canvas, float left, float top, float right, float bottom) { canvas.drawRect(left, top, right, bottom, clearPaint); } // 降低侧滑阈值,让按钮更容易完全显示 @Override public float getSwipeThreshold(@NonNull RecyclerView.ViewHolder viewHolder) { return 0.3f; } // 定义回调接口,让外部处理点击事件 public interface OnActionClickListener { void onEdit(int position); void onDelete(int position); } }
二、给操作按钮添加点击事件
ItemTouchHelper仅负责绘制按钮,没有内置点击逻辑,我们需要通过RecyclerView的触摸监听来判断点击区域:
// 在你的Activity/Fragment中给RecyclerView添加触摸监听 recyclerView.addOnItemTouchListener(new RecyclerView.OnItemTouchListener() { @Override public boolean onInterceptTouchEvent(@NonNull RecyclerView rv, @NonNull MotionEvent e) { if (e.getAction() == MotionEvent.ACTION_UP) { View child = rv.findChildViewUnder(e.getX(), e.getY()); if (child != null) { int position = rv.getChildAdapterPosition(child); RecyclerView.ViewHolder holder = rv.findViewHolderForAdapterPosition(position); if (holder != null) { View itemView = holder.itemView; float touchX = e.getX(); // 判断点击区域 if (touchX < itemView.getLeft() + intrinsicWidth + 40) { // 点击了编辑按钮区域 actionClickListener.onEdit(position); // 点击后恢复条目原始位置 new ItemTouchHelper(callback).startSwipe(holder); } else if (touchX > itemView.getRight() - intrinsicWidth - 40) { // 点击了删除按钮区域 actionClickListener.onDelete(position); // 点击后恢复条目原始位置 new ItemTouchHelper(callback).startSwipe(holder); } } } } return false; } @Override public void onTouchEvent(@NonNull RecyclerView rv, @NonNull MotionEvent e) {} @Override public void onRequestDisallowInterceptTouchEvent(boolean disallowIntercept) {} });
三、在Adapter中处理编辑/删除逻辑
在你的RecyclerView Adapter中实现回调接口,处理具体的业务逻辑:
public class YourAdapter extends RecyclerView.Adapter<YourAdapter.ViewHolder> { private List<YourData> dataList; private SwipeToActionCallback.OnActionClickListener actionClickListener; // 构造方法传入回调 public YourAdapter(List<YourData> dataList, SwipeToActionCallback.OnActionClickListener listener) { this.dataList = dataList; this.actionClickListener = listener; } // ... 省略onCreateViewHolder、onBindViewHolder等基础方法 public static class ViewHolder extends RecyclerView.ViewHolder { // 初始化你的条目组件 public ViewHolder(@NonNull View itemView) { super(itemView); } } // 处理删除操作 public void deleteItem(int position) { dataList.remove(position); notifyItemRemoved(position); } // 处理编辑操作 public void editItem(int position) { YourData targetData = dataList.get(position); // 这里可以跳转到编辑界面或执行编辑逻辑 } }
四、初始化组件并绑定
最后在你的Activity/Fragment中完成初始化和绑定:
// 初始化侧滑回调 SwipeToActionCallback callback = new SwipeToActionCallback(this) {}; ItemTouchHelper itemTouchHelper = new ItemTouchHelper(callback); itemTouchHelper.attachToRecyclerView(recyclerView); // 初始化Adapter并设置回调 SwipeToActionCallback.OnActionClickListener actionClickListener = new SwipeToActionCallback.OnActionClickListener() { @Override public void onEdit(int position) { adapter.editItem(position); } @Override public void onDelete(int position) { adapter.deleteItem(position); } }; YourAdapter adapter = new YourAdapter(dataList, actionClickListener); recyclerView.setAdapter(adapter);
这样修改后,你就能实现:右滑条目显示左侧编辑按钮,左滑显示右侧删除按钮,点击对应按钮才会执行编辑或删除操作,侧滑后不会自动删除条目啦。
内容的提问来源于stack exchange,提问作者Harry
相关产品推荐
相关产品推荐

