本帖最后由 孟凡凯老师 于 2016-5-15 22:39 编辑
【济南校区】凯哥兵法之RecyclerView 概述: RecyclerView是ListView的升级版,它具备了更好的性能,且更容易使用。和ListView一样,RecyclerView是用来显示大量数据的容器,并通过复用有限数量的View,来提高滚动时的性能。当你的视图上的元素经常动态的且有规律的改变时候,可以使用RecyclerView控件。 与ListView不同的是RecyclerView现在不再负责布局,只专注于复用机制,布局交由LayoutManager来管理。 RecyclerView仍然通过Adapter来获取需要显示的对象。 使用: 在布局中引入v7包中的RecyclerView - <android.support.v7.widget.RecyclerView
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:id="@+id/recycler" />
复制代码 在代码找到RecyclerView- mRrecyclerView = (RecyclerView) findViewById(R.id.recycler);
复制代码 ListView的用法:
- // LinearLayoutManager 布局管理者可以将每个条目的视图放置于适当的位置。
- LinearLayoutManager layoutManager = new LinearLayoutManager (this);
- //设置布局的方向 LinearLayoutManager.VERTICAL:垂直;LinearLayoutManager.HORIZONTAL:水平;
- layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
- //给RrecyclerView设置布局管理者
- mRrecyclerView.setLayoutManager(layoutManager);
- //设置RrecyclerView适配器。
- mRrecyclerView.setAdapter(new MyListAdapter(getApplication(),mList));
- //设置RrecyclerView背景颜色
- mRrecyclerView.setBackgroundColor(Color.parseColor("#eeeeee"));
- //设置RrecyclerView条目的动画
- mRrecyclerView.setItemAnimator(new DefaultItemAnimator());
复制代码 下面是RecyclerView的适配器,要使用RecyclerView组件,创建Adapter不再继承自BaseAdapter,而是应该继承自RecyclerView.Adapter类,并且最好指定一个继承自RecyclerView.ViewHolder的范型,Adapter不再要求你返回一个View,而是一个ViewHolder。需要实现三个方法:
public ListHolder onCreateViewHolder(ViewGroup parent, int viewType) 当RecyclerView需要一个ViewHolder时会回调该方法,如果有可复用的View不会回调该方法
public void onBindViewHolder(ListHolder holder, int position) 当一个View需要出现在屏幕上时,该方法会被回调,可以在该方法中根据数据来更改视图
public int getItemCount()返回RecycleView有多少条目- public class MyListAdapter extends RecyclerView.Adapter<MyListAdapter.ListHolder> {
- private Context mContext;
- private ArrayList<String> mList;
- public MyListAdapter(Context context , ArrayList<String> list){
- this.mContext = context;
- this.mList=list;
- }
- /** 类似BaseAdapter中的getView()方法*/
- @Override
- public ListHolder onCreateViewHolder(ViewGroup parent, int viewType) {
- View view = LayoutInflater.from(mContext).inflate( R.layout.item_list, parent, false);
- return new ListHolder(view) ;
- }
- /**一般是用来进行绑定数据*/
- @Override
- public void onBindViewHolder(ListHolder holder, int position) {
- holder.setData(position);
- }
- /**返回RecycleView有多少条目*/
- @Override
- public int getItemCount() {
- return mList.size();
- }
复制代码 效果图如下:
GirdView的用法: - // 创建布局管理,需要传入两个参数,第一个参数是Context上下文对象,第二个是GridView需要展示的列数。
- GridLayoutManager layoutManager = new GridLayoutManager(getApplicationContext(),3);
- //设置布局的方向
- layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
- //给RrecyclerView设置布局管理者
- mRrecyclerView.setLayoutManager(layoutManager);
- //设置RrecyclerView适配器。
- mRrecyclerView.setAdapter(new MyListAdapter(getApplication(),mList));
- //设置RrecyclerView背景颜色
- mRrecyclerView.setBackgroundColor(Color.parseColor("#eeeeee"));
- //设置RrecyclerView条目的动画
- mRrecyclerView.setItemAnimator(new DefaultItemAnimator());
复制代码
效果图如下:
StaggeredGrid(瀑布流)的用法:- // 创建布局管理,需要传入两个参数,第一个参数是StaggeredGrid需要展示的列数,第二个是布局的方向。
- StaggeredGridLayoutManager layoutManager = new StaggeredGridLayoutManager(2,LinearLayoutManager.VERTICAL);
- //给RrecyclerView设置布局管理者
- mRrecyclerView.setLayoutManager(layoutManager);
- //设置RrecyclerView适配器。
- mRrecyclerView.setAdapter(new StaggeredGridAdapter(getApplication(),true));
- //设置RrecyclerView背景颜色
- mRrecyclerView.setBackgroundColor(Color.parseColor("#eeeeee"));
- //设置RrecyclerView条目的动画
- mRrecyclerView.setItemAnimator(new DefaultItemAnimator());
- mRrecyclerView.addItemDecoration(new DividerGridItemDecoration(this));
复制代码
分割线: 各位也看到,RecyclerView没有分割线啊,看起来好丑,对此,RecyclerView 提供了addItemDecoration(ItemDecoration decor)方法用来设置分割线但是ItemDecoration是抽象类,并且没有实现类,所以我们需要去自己定制分割线。首先我们要继承ItemDecoratio,在绘制的时候,去绘制decorator,即调用该类的
onDraw和onDrawOver方法,一般情况下只需要去复写其中一个就可以。
public void onDrawOver(Canvas c, RecyclerView parent) {}
public void onDraw(Canvas c, RecyclerView parent, RecyclerView.State state){}
public void getItemOffsets(Rect outRect, int itemPosition, RecyclerView parent){}
ItemDecoration的实现类可以参考:DividerItemDecoration
添加分割线后的效果图:
RecyclerView条目点击事件: 虽然说RecyclerView功能十分强大,但是RecyclerView并没有提供条目的点击事件,所以说要自己去设置点击事件。仿照ListView的setOnItemClickListener()方法,将被点击条目的View和position暴露给调用者。在Adapter的根布局中设置点击事件,之后在根布局被点击的时候进行接口回调,将被点击条目的View和position暴露出去,最后给Adapter设置点击事件,在根布局的点击事件的时候,就会回调Adapter的方法
首先声明一个接口对外暴露被点击条目的View和position- public interface OnItemClickListener {
- void onItemClick(View view, int position);
- }
复制代码 在Adapter的根布局中设置点击事件- public ListHolder onCreateViewHolder(ViewGroup parent, int viewType) {
- View view = LayoutInflater.from(mContext).inflate( R.layout.item_list, parent, false);
- view.setOnClickListener(this);
- return new ListHolder(view) ;
- }
复制代码 在onBindViewHolder()方法中获取position- public void onBindViewHolder(ListHolder holder, int position) {
- holder.setData(position);
- holder.itemView.setTag(position);
- }
复制代码 提供设置条目监听的方法,并用成员变量mOnItemClickListener 进行接收- public void setOnItemClickListener(OnItemClickListener listener) {
- mOnItemClickListener = listener;
- }
复制代码 实现根布局的点击事件点击事件- @Override
- public void onClick(View v) {
- if(mOnItemClickListener != null) {
- mOnItemClickListener.onItemClick(v, (Integer) v.getTag());
- }
- }
复制代码 最后我们让Adapter去实现点击事件- adapter.setOnItemClickListener(new OnItemClickListener() {
- @Override
- public void onItemClick(View view, int position) {
- Toast.makeText(DemoActivity.this, "position: "mList.get(position), Toast.LENGTH_SHORT).show();
- }
- });
复制代码 最后的效果图:
可以看到最后在点击条目李俊的时候弹出了相对应的信息,所以说咱们的这个思路去实现点击事件是没错的。
|