RecyclerView

RecyclerView相对于ListView的优点:     

        1、可以使用布局管理器LayoutManager来管理RecyclerView的显示方式:水平、垂直、网络、网格交错布局;

        2、自定义item的分割条,实现自定义(不知道是优点还是缺点,见仁见智吧   ( ̄▽ ̄)");

        3、可以控制item的添加和删除的动画,非常自由,可以自定义动画,配合具体场景,效果非常棒;

        4、可以动态的在指定位置添加和删除某一项,而列表不会回到顶部,动态的update列表数据(非常需要);
    
        5、缺点:就是没有OnItemClickListenter(),需要自己在RecycleView内部自定义列表项的点击事件或则长按事件(按需求自己添加);
       
        6、在Material Design中和CardView(和RecycleView同时出现的新控件)配合使用,显示效果非常突出(现在很多新的主流App都使用了这种结构,后面会有demo展示)。


RecycleView的基本使用步骤:
      
       1、模拟对象和获取对象集合数据(这里只是模拟数据)

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. package com.world.hello.recycleview;  
  2.   
  3. /** 
  4.  * 模拟对象数据 
  5.  * Created by chengguo on 2016/5/30. 
  6.  */  
  7. public class SampleModel {  
  8.     private String message;  
  9.   
  10.     public SampleModel(String message) {  
  11.         this.message = message;  
  12.     }  
  13.   
  14.     public void setMessage(String s) {  
  15.         message = s;  
  16.     }  
  17.   
  18.     public String getMessage() {  
  19.         return message;  
  20.     }  
  21. }  

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. package com.world.hello.recycleview;  
  2.   
  3. import java.util.ArrayList;  
  4.   
  5. /** 
  6.  * 模拟数据集合 
  7.  * Created by chengguo on 2016/5/30. 
  8.  */  
  9. public class DemoApp {  
  10.     //获取要显示的数据(初始化数据)  
  11.     public static ArrayList<SampleModel> getSampleData(int size) {  
  12.         ArrayList<SampleModel> sampleData = new ArrayList<SampleModel>(size);  
  13.         for (int i = 0; i < size; i++) {  
  14.             sampleData.add(new SampleModel("新的列表项 " + i));  
  15.         }  
  16.           
  17.         return sampleData;  
  18.     }  
  19. }  
       
      2、绘制列表项之间的分割条

                   使用RecyclerView控件通常需要指定列表项的分割条。定制分割条的原理是编写一个RecyclerView.ItemDecoration的子类,并实现onDrawOver方法,在该方法中需要绘制所有列表项之间的分割条。如下所示:

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. package com.world.hello.recycleview;  
  2.   
  3. import android.content.Context;  
  4. import android.content.res.TypedArray;  
  5. import android.graphics.Canvas;  
  6. import android.graphics.drawable.Drawable;  
  7. import android.support.v7.widget.RecyclerView;  
  8. import android.view.View;  
  9.   
  10. /** 
  11.  * 定制分割线 
  12.  * Created by chengguo on 2016/5/30. 
  13.  */  
  14. public class SampleDivider extends RecyclerView.ItemDecoration {  
  15.     //默认分割条Drawable资源的Id  
  16.     private static final int[] ATTRS = {android.R.attr.listDivider};  
  17.     //分割条的Drawable对象  
  18.     private Drawable mDicider;  
  19.   
  20.     public SampleDivider(Context context) {  
  21.         TypedArray ta = context.obtainStyledAttributes(ATTRS);  
  22.         //获取分割条的drawable对象  
  23.         mDicider = ta.getDrawable(0);  
  24.         //回收ta所占用的空间  
  25.         ta.recycle();  
  26.   
  27.     }  
  28.   
  29.     /** 
  30.      * 在改方法中绘制了所有列表项之间的分割条 
  31.      * 
  32.      * @param c 
  33.      * @param parent 
  34.      */  
  35.     @Override  
  36.     public void onDrawOver(Canvas c, RecyclerView parent) {  
  37.   
  38.         //获取列表项距离左边源的距离  
  39.         int left = parent.getPaddingLeft();  
  40.         //获取列表项距离右边源的距离  
  41.         int right = parent.getWidth() - parent.getPaddingRight();  
  42.         //获取列表的总数  
  43.         int childCount = parent.getChildCount();  
  44.         //开始绘制这些列表项之间的分割线  
  45.         for (int i = 0; i < childCount; i++) {  
  46.             //获取当前的列表  
  47.             View child = parent.getChildAt(i);  
  48.             //获取当前列表项的布局参数信息  
  49.             RecyclerView.LayoutParams params = (RecyclerView.LayoutParams) child.getLayoutParams();  
  50.             //计算分割条左上角的的纵坐标  
  51.             int top = child.getBottom() + params.bottomMargin;  
  52.             //计算分割条右下角的纵坐标  
  53.             int bottom = top + mDicider.getIntrinsicHeight();  
  54.             //设置分割条绘制的位置  
  55.             mDicider.setBounds(left,top,right,bottom);  
  56.             //开始绘制当前列表项下方的分割条  
  57.             mDicider.draw(c);  
  58.         }  
  59.     }  
  60. }  
 
        3、实现Adapter类

                 就像ListView的adapter一般会继承BaseAdapter一样,RecyclerView也提供了这样的一个基类RecyclerView.Adapter,改基类支持泛型,泛型用于指定列表项中控件。如下:

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. package com.world.hello.recycleview;  
  2.   
  3. import android.support.v7.widget.RecyclerView;  
  4. import android.view.LayoutInflater;  
  5. import android.view.View;  
  6. import android.view.ViewGroup;  
  7. import android.widget.TextView;  
  8.   
  9. import java.util.ArrayList;  
  10. import java.util.Random;  
  11.   
  12. /** 
  13.  * recycleView的adapter 
  14.  * Created by chengguo on 2016/5/30. 
  15.  */  
  16. public class SampleRecycleAdapter extends RecyclerView.Adapter<SampleRecycleAdapter.ViewHolder>{  
  17.   
  18.     //保存列表项数据  
  19.     private final ArrayList<SampleModel> sampleData = DemoApp.getSampleData(30);  
  20.   
  21.     //创建列表项中显示的控件对象(需要使用Adapter指定泛型)  
  22.     @Override  
  23.     public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {  
  24.         //获取列表项控件LinearLayer对象  
  25.         View rowView = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_item,parent,false);  
  26.         return new ViewHolder(rowView);  
  27.     }  
  28.   
  29.     //在该方法中设置列表项中显示的值  
  30.     @Override  
  31.     public void onBindViewHolder(ViewHolder holder, int position) {  
  32.   
  33.         SampleModel rowData = sampleData.get(position);  
  34.         holder.textViewSample.setText(rowData.getMessage());  
  35.         holder.itemView.setTag(rowData);  
  36.     }  
  37.   
  38.     //设置列表项总和  
  39.     @Override  
  40.     public int getItemCount() {  
  41.         return sampleData.size();  
  42.     }  
  43.   
  44.     //删除指定列表项的数据  
  45.     public void removeData(int position){  
  46.         sampleData.remove(position);  
  47.         //通知recycleView某个列表项被删除了  
  48.         notifyItemRemoved(position);  
  49.     }  
  50.   
  51.     //在指定的位置添加一个新的列表项  
  52.     public void addItem(int position){  
  53.         //使用随机数字  
  54.         sampleData.add(position,new SampleModel("新增列表项"new Random().nextInt(100)));  
  55.         notifyItemInserted(position);  
  56.     }  
  57.   
  58.     /** 
  59.      * ViewHolder用于存储列表项中显示的控件,(这里只有一个TextView做示例) 
  60.      */  
  61.     public static class ViewHolder extends RecyclerView.ViewHolder{  
  62.   
  63.         private TextView textViewSample;  
  64.   
  65.         public ViewHolder(View itemView) {  
  66.             super(itemView);  
  67.             textViewSample = (TextView) itemView.findViewById(R.id.text_view);  
  68.         }  
  69.     }  
[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. }  

          注意:SampleRecyclerAdapter类中所有使用@Override的方法都是覆盖的父类的同名方法。这些方法中和ListView对应的Adapter中的方法有些不同,在新Adapter中没有了getView()方法,而是使用onCreateViewHolder和OnBindViewHolder方法。前者用于获取列表项控件,后者用于指定在控件中显示的数据。 还有就是以前数据发生变化时,只能调用notifyDataSetChanged()方法通知数据是否发生变化,现在可以使用notifyItemRemoved()方法告诉具体哪个位置的数据被移除,使用notifyItemInserted()方法通知某一个新的列表项背添加。还有很多新的Api非常实用,如下面图片,就不一一介绍了;



     4、在Activity中使用RecyclerView

          recycleView是Android Support library中的控件,所以需要在Android studio中的app的gradle中添加下面的依赖
compile 'com.android.support:design:23.4.0'
 
          然后就可以使用RecycleView这个控件了,这里实现了RecycleView的动态添加和删除操作。稍微要比listview复杂点,要设置RecycleView的排列方式 、item间的分割线、item增加和删除的动画;具体使用代码如下:

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. package com.world.hello.recycleview;  
  2.   
  3. import android.app.Activity;  
  4. import android.os.Bundle;  
  5. import android.support.design.widget.FloatingActionButton;  
  6. import android.support.v7.widget.DefaultItemAnimator;  
  7. import android.support.v7.widget.LinearLayoutManager;  
  8. import android.support.v7.widget.RecyclerView;  
  9. import android.view.View;  
  10. import android.view.animation.AnimationUtils;  
  11. import android.widget.Button;  
  12.   
  13. public class MainActivity extends Activity {  
  14.   
  15.     //顶部删除按钮  
  16.     private Button mDeleteBar;  
  17.     //recyclerView  
  18.     private RecyclerView mRecyclerView;  
  19.     //添加item按钮,这里也是使用Design库里面的一个新控件,就当做一个按钮使用。只是样式很好看  
  20.     private FloatingActionButton mAddBtn;  
  21.   
  22.     @Override  
  23.     protected void onCreate(Bundle savedInstanceState) {  
  24.         super.onCreate(savedInstanceState);  
  25.         setContentView(R.layout.activity_main);  
  26.         mDeleteBar = (Button) findViewById(R.id.delete_btn);  
  27.         mAddBtn = (FloatingActionButton) findViewById(R.id.add_item);  
  28.   
  29.         //获取到recyclerView  
  30.         mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);  
  31.         //创建LinearLayoutManager  
  32.         final LinearLayoutManager layoutManager = new LinearLayoutManager(this);  
  33.         //为RecyclerView指定布局管理器对象  
  34.         mRecyclerView.setLayoutManager(layoutManager);  
  35.         //创建列表项分割线对象  
  36.         final RecyclerView.ItemDecoration itemDecoration = new SampleDivider(this);  
  37.         //RecyclerView控件指定分割线对象  
  38.         mRecyclerView.addItemDecoration(itemDecoration);  
  39.         //创建SampleRecyclerAdapter  
  40.         final SampleRecycleAdapter sampleRecycleAdapter = new SampleRecycleAdapter();  
  41.         //为RecyclerView控件指定Adapter  
  42.         mRecyclerView.setAdapter(sampleRecycleAdapter);  
  43.         //设置Item增加、移除动画  
  44.         mRecyclerView.setItemAnimator(new DefaultItemAnimator());  
  45.   
  46.   
  47.         //为右下角按钮添加点击事件  
  48.         mAddBtn.setOnClickListener(new View.OnClickListener() {  
  49.             @Override  
  50.             public void onClick(View v) {  
  51.                 //获取第一个可视的列表项的位置,再加上2个位置,为了演示方便  
  52.                 int positionToAdd = layoutManager.findFirstCompletelyVisibleItemPosition() + 2;  
  53.                 //在该位置的后面插入新的列表项  
  54.                 sampleRecycleAdapter.addItem(positionToAdd);  
  55.             }  
  56.         });  
  57.   
  58.         //为顶部的删除面板添加点击事件  
  59.         mDeleteBar.setOnClickListener(new View.OnClickListener() {  
  60.             @Override  
  61.             public void onClick(View v) {  
  62.                 //获取第一个可视的列表项的位置,再加上2个位置,为了演示方便  
  63.                 int positionToRemove = layoutManager.findFirstCompletelyVisibleItemPosition() + 2;  
  64.                 //删除第一个可视的列表项  
  65.                 sampleRecycleAdapter.removeData(positionToRemove);  
  66.                 //删除完成后隐藏删除面板  
  67.                 hideDeleteBar();  
  68.             }  
  69.         });  
  70.   
  71.         //为RecyclerView控件设置滚动事件  
  72.         mRecyclerView.setOnScrollListener(new RecyclerView.OnScrollListener() {  
  73.             //滚动状态变化事件的方法  
  74.             @Override  
  75.             public void onScrollStateChanged(RecyclerView recyclerView, int newState) {  
  76.                 super.onScrollStateChanged(recyclerView, newState);  
  77.             }  
  78.   
  79.             //滚动事件方法(判断上下或者左右滚动)  
  80.             @Override  
  81.             public void onScrolled(RecyclerView recyclerView, int dx, int dy) {  
  82.                 //如果是垂直显示的列表, dy>0 表示向上滚动,否则表示向下滚动  
  83.                 //如果是水平显示的列表,dx > 0 表示向右滚动,否则表示向左滚动  
  84.                 if (dy > 0) {  
  85.                     //向上滚动时,隐藏删除面板,  
  86.                     if (mDeleteBar.getVisibility() == View.VISIBLE) {  
  87.                         hideDeleteBar();  
  88.                     }  
  89.                 } else {  
  90.                     //向下滚动时,显示显示面板  
  91.                     if (mDeleteBar.getVisibility() == View.GONE) {  
  92.                         showDeleteBar();  
  93.                     }  
  94.                 }  
  95.             }  
  96.         });  
  97.     }  
  98.   
  99.     /** 
  100.      * 显示删除栏,使用动画效果 
  101.      */  
  102.     private void showDeleteBar() {  
  103.         mDeleteBar.startAnimation(AnimationUtils.loadAnimation(this, R.anim.translate_show));  
  104.         mDeleteBar.setVisibility(View.VISIBLE);  
  105.     }  
  106.   
  107.     /** 
  108.      * 隐藏删除栏,使用动画效果 
  109.      */  
  110.     private void hideDeleteBar() {  
  111.         mDeleteBar.startAnimation(AnimationUtils.loadAnimation(this, R.anim.translate_hide));  
  112.         mDeleteBar.setVisibility(View.GONE);  
  113.     }  
  114. }  

 main_activity.xml文件如下:

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     xmlns:tools="http://schemas.android.com/tools"  
  4.     xmlns:app ="http://schemas.android.com/apk/res-auto"  
  5.     android:layout_width="match_parent"  
  6.     android:layout_height="match_parent"  
  7.     tools:context="com.world.hello.recycleview.MainActivity">  
  8.   
  9.     <Button  
  10.         android:id="@+id/delete_btn"  
  11.         android:layout_width="match_parent"  
  12.         android:layout_height="40dp"  
  13.         android:text="删除一项"  
  14.         android:background="#4400ffee"  
  15.         android:textSize="14dp"/>  
  16.   
  17.     <android.support.v7.widget.RecyclerView  
  18.         android:id="@+id/recycler_view"  
  19.         android:layout_width="match_parent"  
  20.         android:layout_height="match_parent"/>  
  21.   
  22.     <android.support.design.widget.FloatingActionButton  
  23.         android:id="@+id/add_item"  
  24.         android:layout_width="wrap_content"  
  25.         android:layout_height="wrap_content"  
  26.         app:borderWidth="0dp"  
  27.         app:rippleColor="#eeff0000"  
  28.         android:src="@android:drawable/ic_input_add"  
  29.         android:layout_alignParentBottom="true"  
  30.         android:layout_alignParentRight="true"  
  31.         android:layout_alignParentEnd="true"  
  32.         android:layout_marginRight="33dp"  
  33.         android:layout_marginEnd="33dp"  
  34.         android:layout_marginBottom="38dp" />  
  35.   
  36. </RelativeLayout>  

list_item.xml文件如下:

[java]  view plain  copy
  在CODE上查看代码片 派生到我的代码片
  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:layout_width="match_parent"  
  4.     android:layout_height="40dp"  
  5.     android:gravity="center_vertical"  
  6.     android:orientation="vertical">  
  7.   
  8.     <TextView  
  9.         android:id="@+id/text_view"  
  10.         android:layout_width="match_parent"  
  11.         android:layout_height="match_parent"  
  12.         android:gravity="center_vertical"  
  13.         android:textColor="@android:color/black"  
  14.         android:textSize="16sp" />  
  15. </LinearLayout>  

效果图如下:





下一篇,将详细讲解。recycleView的排列方法、动画和CardView结合的使用示例
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值