我们做listview左右滑动操作时,一般中情况下,都是像QQ那样,左滑弹出操作菜单(删除、编辑),然后选择菜单操作; 这样的效果不可谓不好,算是非常经典。 另外,有少数的APP,尤其是任务管理类的APP,更加注重listview的操作交互,例如ToDoList及滴答清单,这两个APP对任务的操作是直接通过滑动列表进行操作的;效果图如下:
gtihub上有一个开源项目,已经很好的实现了对该效果:https://github.com/wdullaer/SwipeActionAdapter ; 此处,就简单下介绍该开源项目。
1. 使用Android Studio新建项目导入该开源库:
导入该库,可以在build.gradle中添加:
dependencies { compile 'com.wdullaer:swipeactionadapter:2.0.0' }当然,我更建议直接把该项目的library直接导入到项目中,这样会更加方便对代码进行修改。
2. 首先,设置ListView显示:
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Create an Adapter for your content String[] content = new String[20]; for (int i=0;i<20;i++) content[i] = "Row "+(i+1); ArrayAdapter<String> stringAdapter = new ArrayAdapter<String>( this, R.layout.row_bg, R.id.text, new ArrayList<String>(Arrays.asList(content)) ); // Wrap your content in a SwipeActionAdapter mAdapter = new SwipeActionAdapter(stringAdapter); // Pass a reference of your ListView to the SwipeActionAdapter mAdapter.setListView(getListView()); // Set the SwipeActionAdapter as the Adapter for your ListView setListAdapter(mAdapter); }上面的代码很简单,只是比正常使用ListView多了一步: SwipeActionAdapter mAdapter = new SwipeActionAdapter(stringAdapter); 就是在普通Adapter的基础上包裹上一层 SwipeActionAdapter。
3. 为ListView的Item添加滑动时的背景色
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Create an Adapter for your content String[] content = new String[20]; for (int i=0;i<20;i++) content[i] = "Row "+(i+1); ArrayAdapter<String> stringAdapter = new ArrayAdapter<String>( this, R.layout.row_bg, R.id.text, new ArrayList<String>(Arrays.asList(content)) ); // Wrap your content in a SwipeActionAdapter mAdapter = new SwipeActionAdapter(stringAdapter); // Pass a reference of your ListView to the SwipeActionAdapter mAdapter.setListView(getListView()); // Set the SwipeActionAdapter as the Adapter for your ListView setListAdapter(mAdapter); // Set backgrounds for the swipe directions mAdapter.addBackground(SwipeDirection.DIRECTION_FAR_LEFT,R.layout.row_bg_left_far) .addBackground(SwipeDirection.DIRECTION_NORMAL_LEFT,R.layout.row_bg_left) .addBackground(SwipeDirection.DIRECTION_FAR_RIGHT,R.layout.row_bg_right_far) .addBackground(SwipeDirection.DIRECTION_NORMAL_RIGHT,R.layout.row_bg_right); }
上述代码最后,既是添加背景的代码,代码很明了,在为不同的滑动过程,添加不同的背景,该背景其实就是一个布局,例如row_bg_left_far.xml文件:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="?android:listPreferredItemHeight" android:background="@android:color/holo_blue_bright"> </LinearLayout>
此处,可以查看下SwipeDirection.java类源码:
public enum SwipeDirection { // Constants DIRECTION_NORMAL_LEFT, DIRECTION_FAR_LEFT, DIRECTION_NORMAL_RIGHT, DIRECTION_FAR_RIGHT, DIRECTION_NEUTRAL; @NonNull public static List<SwipeDirection> getAllDirections(){ return Arrays.asList( DIRECTION_FAR_LEFT, DIRECTION_FAR_RIGHT, DIRECTION_NEUTRAL, DIRECTION_NORMAL_LEFT, DIRECTION_NORMAL_RIGHT ); } public boolean isLeft() { return this.equals(DIRECTION_NORMAL_LEFT) || this.equals(DIRECTION_FAR_LEFT); } public boolean isRight() { return this.equals(DIRECTION_NORMAL_RIGHT) || this.equals(DIRECTION_FAR_RIGHT); } }
我们可以看出,主要的操作有四个: DIRECTION_NORMAL_LEFT(左滑一小段距离),DIRECTION_FAR_LEFT (左滑较长距离), DIRECTION_NORMAL_RIGHT (右滑一小段距离),DIRECTION_FAR_RIGHT (右滑较长距离)。
4. 添加ListView左右滑动监听:
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Create an Adapter for your content String[] content = new String[20]; for (int i=0;i<20;i++) content[i] = "Row "+(i+1); ArrayAdapter<String> stringAdapter = new ArrayAdapter<String>( this, R.layout.row_bg, R.id.text, new ArrayList<String>(Arrays.asList(content)) ); // Wrap your content in a SwipeActionAdapter mAdapter = new SwipeActionAdapter(stringAdapter); // Pass a reference of your ListView to the SwipeActionAdapter mAdapter.setListView(getListView()); // Set the SwipeActionAdapter as the Adapter for your ListView setListAdapter(mAdapter); // Set backgrounds for the swipe directions mAdapter.addBackground(SwipeDirection.DIRECTION_FAR_LEFT,R.layout.row_bg_left_far) .addBackground(SwipeDirection.DIRECTION_NORMAL_LEFT,R.layout.row_bg_left) .addBackground(SwipeDirection.DIRECTION_FAR_RIGHT,R.layout.row_bg_right_far) .addBackground(SwipeDirection.DIRECTION_NORMAL_RIGHT,R.layout.row_bg_right); // Listen to swipes mAdapter.setSwipeActionListener(new SwipeActionListener(){ @Override public boolean hasActions(int position, SwipeDirection direction){ if(direction.isLeft()) return true; // Change this to false to disable left swipes if(direction.isRight()) return true; return false; } @Override public boolean shouldDismiss(int position, SwipeDirection direction){ // Only dismiss an item when swiping normal left return direction == SwipeDirection.DIRECTION_NORMAL_LEFT; } @Override public void onSwipe(int[] positionList, SwipeDirection[] directionList){ for(int i=0;i<positionList.length;i++) { int direction = directionList[i]; int position = positionList[i]; String dir = ""; switch (direction) { case SwipeDirection.DIRECTION_FAR_LEFT: dir = "Far left"; break; case SwipeDirection.DIRECTION_NORMAL_LEFT: dir = "Left"; break; case SwipeDirection.DIRECTION_FAR_RIGHT: dir = "Far right"; break; case SwipeDirection.DIRECTION_NORMAL_RIGHT: AlertDialog.Builder builder = new AlertDialog.Builder(this); builder.setTitle("Test Dialog").setMessage("You swiped right").create().show(); dir = "Right"; break; } Toast.makeText( this, dir + " swipe Action triggered on " + mAdapter.getItem(position), Toast.LENGTH_SHORT ).show(); mAdapter.notifyDataSetChanged(); } } }); }
· public boolean hasActions(int position, SwipeDirection direction) : 该方法主要判断滑动方向:左滑还是右滑。
· public boolean shouldDismiss(int position, SwipeDirection direction):该方法主要判断list item滑动后是否有消失的动画。
· public void onSwipe(int[] positionList, SwipeDirection[] directionList): 主要在该方法中处理滑动逻辑。
以上,就是SwipeActionAdapter的基本使用方式,相信善用该库,一定会给APP增添几分色彩,提高用户体验!