Disable Swipe for position in RecyclerView using ItemTouchHelper.SimpleCallback

If someone is using ItemTouchHelper.Callback. Then You can remove any related flags in getMovementFlags(..) function.

@Override
public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
    int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN;
    int swipeFlags = ItemTouchHelper.START | ItemTouchHelper.END;
    return makeMovementFlags(dragFlags, swipeFlags);
}

Here instead of dragFlags and swipeFlags You can pass 0 to disable corresponding feature.

ItemTouchHelper.START means swiping left to right in case of left to right locale (LTR application Support), but the other way around in a right to left locale (RTL application Support). ItemTouchHelper.END means swiping in the opposite direction of START.

so you can remove any flag according to your requirements.


After playing a bit, I managed that SimpleCallback has a method called getSwipeDirs(). As I have a specific ViewHolder for the not swipable position, I can make use of instanceof to avoid the swipe. If that's not your case, you can perform this control using the position of ViewHolder in the Adapter.

Java

@Override
public int getSwipeDirs(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
    if (viewHolder instanceof CartAdapter.MyViewHolder) return 0;
    return super.getSwipeDirs(recyclerView, viewHolder);
}

Kotlin

override fun getSwipeDirs (recyclerView: RecyclerView, viewHolder: RecyclerView.ViewHolder): Int {
    if (viewHolder is CartAdapter.MyViewHolder) return 0
    return super.getSwipeDirs(recyclerView, viewHolder)
}

Here's a simple way to do this that only depends upon the position of the item being swiped:

@Override
public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder holder) {
    int position = holder.getAdapterPosition();
    int dragFlags = 0; // whatever your dragFlags need to be
    int swipeFlags = createSwipeFlags(position)

    return makeMovementFlags(dragFlags, swipeFlags);
}

private int createSwipeFlags(int position) {
  return position == 0 ? 0 : ItemTouchHelper.START | ItemTouchHelper.END;
}

This should also work if you're using SimpleCallback:

@Override
public int getSwipeDirs(RecyclerView recyclerView, RecyclerView.ViewHolder holder) {
    int position = holder.getAdapterPosition();
    return createSwipeFlags(position);
}

private int createSwipeFlags(int position) {
  return position == 0 ? 0 : super.getSwipeDirs(recyclerView, viewHolder);
}

If you want to disable swiping conditional upon the data in the item, use the position value to get data from the adapter for the item being swiped and disable accordingly.

If you already have specific holder types which need to not swipe, the accepted answer will work. However, creating holder types as a proxy for position is a kludge and should be avoided.