android---RecycleView使用ItemTouchHelper实现拖拽和侧滑删除
来源:互联网 发布:java多线程入门书籍 编辑:程序博客网 时间:2024/05/16 15:23
我之前就写过关于手势拖动的文章比如这个
还有这个滑动
这里今天我介绍下recycleview中的滑动,recycleview为我们提供了提供了强大的工具类ItemTouchHelper,它已经处理了关于RecyclerView拖动和滑动的实现,既然都已经有这个了那么我们的思路就很简单了加个回调,滑动效果结束后触发不就好了。
最近开始用gif录制了 上图
我们先看下这个ItemTouchHelper处理滑动的方法
@Override public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) { Log.e(TAG, "getMovementFlags: " ); //START 右向左 END左向右 LEFT 向左 RIGHT向右 UP向上 //如果某个值传0,表示不触发该操作,次数设置支持上下拖拽,支持向右滑动 //第一个表示长按允许的 第二个并不是 return makeMovementFlags(ItemTouchHelper.UP|ItemTouchHelper.DOWN,ItemTouchHelper.LEFT|ItemTouchHelper.END); }
这里我可以看到
return makeMovementFlags(ItemTouchHelper.UP|ItemTouchHelper.DOWN,ItemTouchHelper.LEFT|ItemTouchHelper.END);
这个方法控制我们的滑动和拖动(这里的拖动是只长点击之后)
ItemTouchHelper.UP //滑动拖拽向上方向ItemTouchHelper.DOWN//向下ItemTouchHelper.LEFT//向左ItemTouchHelper.RIGHT//向右ItemTouchHelper.START//依赖布局方向的水平开始方向ItemTouchHelper.END//依赖布局方向的水平结束方向
好了改说下滑动结束的方法
public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction)
这里第二个参数是方向 我们可以根据这个处理不同的事件
下面的是拖动结束方法
public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target)
还有个回调
public interface ItemTouchHelperCallback{ void onItemDelete(int positon); void onMove(int fromPosition,int toPosition); }
那么这个类的代码给你们吧 (我觉得我描述的能力差了点)
package viewpage.yundong.com.recycleviewhuadong;import android.content.res.Resources;import android.graphics.Bitmap;import android.graphics.BitmapFactory;import android.graphics.Canvas;import android.graphics.Paint;import android.graphics.Rect;import android.support.v7.widget.RecyclerView;import android.support.v7.widget.helper.ItemTouchHelper;import android.util.Log;import android.view.View;/** * Created by Administrator on 2017/3/9. */public class RecycleItemTouchHelper extends ItemTouchHelper.Callback{ private static final String TAG ="RecycleItemTouchHelper" ; private final ItemTouchHelperCallback helperCallback; public RecycleItemTouchHelper(ItemTouchHelperCallback helperCallback) { this.helperCallback = helperCallback; } /** * 设置滑动类型标记 * * @param recyclerView * @param viewHolder * @return * 返回一个整数类型的标识,用于判断Item那种移动行为是允许的 */ @Override public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) { Log.e(TAG, "getMovementFlags: " ); //START 右向左 END左向右 LEFT 向左 RIGHT向右 UP向上 //如果某个值传0,表示不触发该操作,次数设置支持上下拖拽,支持向右滑动 //第一个表示长按允许的 第二个并不是 return makeMovementFlags(ItemTouchHelper.UP|ItemTouchHelper.DOWN,ItemTouchHelper.LEFT|ItemTouchHelper.END); } /** * Item是否支持长按拖动 * * @return * true 支持长按操作 * false 不支持长按操作 */ @Override public boolean isLongPressDragEnabled() { return super.isLongPressDragEnabled(); } /** * Item是否支持滑动 * * @return * true 支持滑动操作 * false 不支持滑动操作 */ @Override public boolean isItemViewSwipeEnabled() { return super.isItemViewSwipeEnabled(); } /** * 拖拽切换Item的回调 * * @param recyclerView * @param viewHolder * @param target * @return * 如果Item切换了位置,返回true;反之,返回false */ @Override public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) { Log.e(TAG, "onMove: " ); helperCallback.onMove(viewHolder.getAdapterPosition(),target.getAdapterPosition()); return true; } /** * 滑动Item * * @param viewHolder * @param direction * Item滑动的方向 */ @Override public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) { Log.e(TAG, "onSwiped: "+direction); if (direction==ItemTouchHelper.END){ helperCallback.onItemDelete(viewHolder.getAdapterPosition()); }else if (direction==ItemTouchHelper.LEFT){ Log.e(TAG, "这是向左滑动操作" ); } } /** * Item被选中时候回调 * * @param viewHolder * @param actionState * 当前Item的状态 * ItemTouchHelper.ACTION_STATE_IDLE 闲置状态 * ItemTouchHelper.ACTION_STATE_SWIPE 滑动中状态 * ItemTouchHelper#ACTION_STATE_DRAG 拖拽中状态 */ @Override public void onSelectedChanged(RecyclerView.ViewHolder viewHolder, int actionState) { super.onSelectedChanged(viewHolder, actionState); } public interface ItemTouchHelperCallback{ void onItemDelete(int positon); void onMove(int fromPosition,int toPosition); }}
然后是使用方法
ItemTouchHelper.Callback callback=new RecycleItemTouchHelper(itemAdapter); ItemTouchHelper itemTouchHelper=new ItemTouchHelper(callback); itemTouchHelper.attachToRecyclerView(recycle);
当然 这里你的适配器也要写了 因为要控制数据变化
package viewpage.yundong.com.recycleviewhuadong;import android.content.Context;import android.support.v7.widget.RecyclerView;import android.view.LayoutInflater;import android.view.View;import android.view.ViewGroup;import android.widget.TextView;import java.util.Collections;import java.util.List;/** * Created by Administrator on 2017/3/10. */public class ItemAdapter extends RecyclerView.Adapter implements RecycleItemTouchHelper.ItemTouchHelperCallback{ private Context context; private List<String>list; private LayoutInflater layoutInflater; public ItemAdapter( Context context,List<String>list){ this.context=context; this.list=list; layoutInflater=LayoutInflater.from(context); } @Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { View view=layoutInflater.inflate(R.layout.item,parent, false); return new ItemViewHolder(view); } @Override public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { ItemViewHolder itemViewHolder= (ItemViewHolder) holder; itemViewHolder.textView.setText(list.get(position)); ViewGroup.LayoutParams layoutParams=itemViewHolder.itemView.getLayoutParams(); layoutParams.height=ViewGroup.LayoutParams.WRAP_CONTENT; itemViewHolder.itemView.setLayoutParams(layoutParams); } @Override public int getItemCount() { return list.size(); } @Override public void onItemDelete(int positon) { list.remove(positon); notifyItemRemoved(positon); } @Override public void onMove(int fromPosition, int toPosition) { Collections.swap(list,fromPosition,toPosition);//交换数据 notifyItemMoved(fromPosition,toPosition); } static class ItemViewHolder extends RecyclerView.ViewHolder{ private TextView textView; public ItemViewHolder(View itemView) { super(itemView); textView= (TextView) itemView.findViewById(R.id.text_view); } }}
当然这我们还可以添加动画效果 ItemTouchHelper.ACTION_STATE_SWIPE 滑动中状态
在这个状态下绘制就有效果了
就是在
/** * 移动过程中绘制Item * * @param c * @param recyclerView * @param viewHolder * @param dX * X轴移动的距离 * @param dY * Y轴移动的距离 * @param actionState * 当前Item的状态 * @param isCurrentlyActive * 如果当前被用户操作为true,反之为false */ @Override public void onChildDraw(Canvas c, RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, float dX, float dY, int actionState, boolean isCurrentlyActive) { Log.e("滑动",dX+"==="+dY+"==="+actionState); //滑动时自己实现背景及图片 if (actionState==ItemTouchHelper.ACTION_STATE_SWIPE){ //dX大于0时向右滑动,小于0向左滑动 View itemView=viewHolder.itemView;//获取滑动的view Resources resources= MyApplication.getAppContext().getResources(); Bitmap bitmap= BitmapFactory.decodeResource(resources, R.drawable.ic_launcher);//获取删除指示的背景图片 int padding =10;//图片绘制的padding int maxDrawWidth=2*padding+bitmap.getWidth();//最大的绘制宽度 Paint paint=new Paint(); paint.setColor(resources.getColor(R.color.colorPrimaryDark)); int x=Math.round(Math.abs(dX));// int drawWidth=Math.min(x,maxDrawWidth);//实际的绘制宽度,取实时滑动距离x和最大绘制距离maxDrawWidth最小值 int itemTop=itemView.getBottom()-itemView.getHeight();//绘制的top位置 //向右滑动 if(dX>0){ //根据滑动实时绘制一个背景 c.drawRect(itemView.getLeft(),itemTop,drawWidth,itemView.getBottom(),paint); //在背景上面绘制图片 if (x>padding){//滑动距离大于padding时开始绘制图片 //指定图片绘制的位置 Rect rect=new Rect();//画图的位置 rect.left=itemView.getLeft()+padding; rect.top=itemTop+(itemView.getBottom()-itemTop-bitmap.getHeight())/2;//图片居中 int maxRight=rect.left+bitmap.getWidth(); rect.right=Math.min(x,maxRight); rect.bottom=rect.top+bitmap.getHeight(); //指定图片的绘制区域 Rect rect1=null; if (x<maxRight){ rect1=new Rect();//不能再外面初始化,否则dx大于画图区域时,删除图片不显示 rect1.left=0; rect1.top = 0; rect1.bottom=bitmap.getHeight(); rect1.right=x-padding; } c.drawBitmap(bitmap,rect1,rect,paint); } //绘制时需调用平移动画,否则滑动看不到反馈 itemView.setTranslationX(dX); }else { //根据滑动实时绘制一个背景 c.drawRect(itemView.getRight()-drawWidth,itemTop,itemView.getRight(),itemView.getBottom(),paint); //在背景上面绘制图片 if (x>padding){//滑动距离大于padding时开始绘制图片 //指定图片绘制的位置 Rect rect=new Rect();//画图的位置 rect.right=itemView.getRight()-padding; rect.top=itemTop+(itemView.getBottom()-itemTop-bitmap.getHeight())/2;//图片居中 int maxLeft=rect.right-bitmap.getWidth(); rect.left=Math.max(itemView.getRight()-x,maxLeft); rect.bottom=rect.top+bitmap.getHeight(); //指定图片的绘制区域 这里是对图片的剪裁 Rect rect1=null; Log.e("这里执行到没",Math.max(itemView.getRight()-x-padding,maxLeft)+"==="+(bitmap.getWidth()-x+padding)+"====padding"+padding); if ((itemView.getRight()-x-padding)>maxLeft){ Log.e("这里执行到没1111",(itemView.getRight()-x-padding)+"===="+maxLeft); rect1=new Rect();//不能再外面初始化,否则dx大于画图区域时,删除图片不显示 rect1.left=bitmap.getWidth()-x+padding; rect1.top = 0; rect1.bottom=bitmap.getHeight(); rect1.right=bitmap.getWidth()+padding; } c.drawBitmap(bitmap,rect1,rect,paint); } //绘制时需调用平移动画,否则滑动看不到反馈 itemView.setTranslationX(dX); } }else { //拖动时有系统自己完成 super.onChildDraw(c, recyclerView, viewHolder, dX, dY, actionState, isCurrentlyActive); } }
这个你就也是在继承了ItemTouchHelper.Callback的类里加入即可
tip:我这里没写左滑的删除事件,就是做对比而已觉得不舒服在
public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) { Log.e(TAG, "onSwiped: "+direction); if (direction==ItemTouchHelper.END){ helperCallback.onItemDelete(viewHolder.getAdapterPosition()); }else if (direction==ItemTouchHelper.LEFT){ Log.e(TAG, "这是向左滑动操作" ); } }
改下就好了
0 0
- android---RecycleView使用ItemTouchHelper实现拖拽和侧滑删除
- RecyclerView使用ItemTouchHelper实现拖拽和侧滑删除
- android之RecycleView之ItemTouchHelper 处理拖拽、滑动删除
- ItemTouchHelper实现拖拽和侧滑删除
- RecyclerView进阶:使用ItemTouchHelper实现拖拽和侧滑删除
- Android实现RecyclerView侧滑删除和长按拖拽-ItemTouchHelper
- Android实现RecyclerView侧滑删除和长按拖拽-ItemTouchHelper
- Android实现RecyclerView侧滑删除和长按拖拽-ItemTouchHelper
- Android实现RecyclerView侧滑删除和长按拖拽-ItemTouchHelper
- 使用ItemTouchHelper实现侧滑删除,拖拽
- RecyclerView ItemTouchHelper实现拖拽,侧滑删除
- 使用ItemTouchHelper轻松实现RecyclerView拖拽排序和滑动删除
- 使用ItemTouchHelper轻松实现RecyclerView拖拽排序和滑动删除
- 使用ItemTouchHelper类轻松实现RecyclerView的拖拽和侧滑
- RecyclerView之使用ItemTouchHelper和ItemTouchHelper.Callback实现条目拖拽排序
- 使用RecycleView实现侧滑删除
- 使用ItemTouchHelper和RecyclerView实现拖拽移动效果
- Android学习之ItemTouchHelper实现RecylerView的拖拽以及滑动删除功能
- Android Butterknife 使用总结 8.4.0
- logstash配置文件详解
- NO.5 使用逻辑卷管理系统
- thinkphp5 command模式下无法获取配置信息的解决办法
- c++ 标准
- android---RecycleView使用ItemTouchHelper实现拖拽和侧滑删除
- Unity3D_uGUI学习笔记(1)_Canvas简述
- P2341 受欢迎的牛
- python的多线程编程——锁
- EL表达式不起作用
- Android笔记--WIFI开发
- java.lang.UnsupportedClassVersionError: org/apache/solr/client/solrj/SolrServerException
- 读面试题有感
- leetcode_15. 3Sum-求数组中三个数和为0