RecycleView Adapter的封装

扯一扯

现在越来越多的开始使用RecycleView去替代ListView,在使用ListView的时候数据和界面的绑定一般是去继承BaseAdapter,对于BaseAdapter的封装网上已经很多了,其实也不用去封装太多的东西,BaseAdapter的整体也比较见简单。但是当使用更为强大的RecycleView的时候,如果不去对它的adapter进行适当的封装,使用起来就显得繁琐的多了。现在来说一下我对RecycleView.Adapter的封装。

原始的样子

先看一下如果如果不进行封装的话是怎样的一个写法:

public class TestAdapter extends RecyclerView.Adapter<TestAdapter.MyHolder> {

    @Override
    public MyHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        return null;
    }

    @Override
    public void onBindViewHolder(MyHolder holder, int position) {

    }

    @Override
    public int getItemCount() {
        return 0;
    }

    class MyHolder extends RecyclerView.ViewHolder{

        public MyHolder(View itemView) {
            super(itemView);
        }
    }
}

至于各个函数是什么作用,这里就不说了,以前写过一篇关于RecycleView的使用,地址。这里主要来说一下怎么去简写这些。

开始

首先说一下我想要什么样的一个结果,我希望输入一个Layoutid,然后就可以进行数据和控件的绑定了。也就是说我只希望有两个函数暴露出来,这里先定为public void onBind(MyViewHolder viewHolder, int Position)用于绑定,注意这里的MyViewHolder,这其实并不是常见意义上的viewholder,这个后面再说。还有一个就是用于输入Layoutid的,protected int getLayout()。一般传进adapteer里面的都是list,所以可以使用泛型来使使用更加的灵活,同时去实现list的一些常见操作,使操作recycleview更加的方便。当然点击事件是必不可少的。下面就来具体说一下做法。

1.选择这样实现继承和实现

public abstract class ArrayRecyclerAdapter<E, VH extends RecyclerView.ViewHolder>
        extends RecyclerView.Adapter<VH> implements List<E> 

这里去使用泛型去当具体的model,这样在子类里面去具体化,就更加的灵活,还实现了List接口,来实现常见的对list的操作,因为RecyclerView的数据更新要比ListView复杂的多,不能简单的notifyItemChanged。在实现list的方法的同时来对RecyclerView进行改变。

2.继续
再看一下以后要要使用的BaseAdapter:

public abstract class BaseAdapter<E> extends ArrayRecyclerAdapter<E, BaseAdapter.ViewHolder>

这里对ViewHolder进行了具体化,但是依然保留了model的泛化,因为这个我希望去到具体的子类里面实现。
同时定义了抽象方法:

protected abstract void onItemClick(View v, int position);

    public abstract void onBind(MyViewHolder viewHolder, int RealPosition);

    protected abstract int getLayout();

这个分别在这些函数调用:

  @Override
    public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        View layout = LayoutInflater.from(mContext).inflate(getLayout(), parent, false);
        return new ViewHolder(layout);
    }
 @Override
    public void onBindViewHolder(BaseAdapter.ViewHolder viewHolder, int position) {
        viewHolder.itemView.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                onItemClick(v, position);
            }
        });
        onBind(viewHolder.getViewHolder(), position);
    }

下面就是关于ViewHolder的写法了,直接看吧

 public class ViewHolder extends RecyclerView.ViewHolder {
        private MyViewHolder viewHolder;
        public ViewHolder(View itemView) {
            super(itemView);
            viewHolder = MyViewHolder.getViewHolder(itemView);
        }

        public MyViewHolder getViewHolder() {
            return viewHolder;
        }
    }

这里还使用了一个叫MyViewHolder的类,其实他和RecyclerView.ViewHolder并没有什么关系,可以看做是一个容器或者工具类,这个也说不清,看代码就明白了:

public class MyViewHolder {
    private SparseArray<View> viewHolder;
    private View view;

    public static MyViewHolder getViewHolder(View view) {

        MyViewHolder viewHolder = (MyViewHolder) view.getTag();
        if (viewHolder == null) {
            viewHolder = new MyViewHolder(view);
            view.setTag(viewHolder);
        }
        return viewHolder;
    }

    private MyViewHolder(View view) {
        this.view = view;
        viewHolder = new SparseArray<View>();
        view.setTag(viewHolder);
    }

    public <T extends View> T get(int id) {
        View childView = viewHolder.get(id);
        if (childView == null) {
            childView = view.findViewById(id);
            viewHolder.put(id, childView);
        }
        return (T) childView;
    }

    public View getConvertView() {
        return view;
    }

    public TextView getTextView(int id) {

        return get(id);
    }

    public Button getButton(int id) {

        return get(id);
    }

    public ImageView getImageView(int id) {
        return get(id);
    }

    public void setTextView(int id, CharSequence charSequence) {
        getTextView(id).setText(charSequence);
    }

}

这里使用了SparseArray来优化,避免多次的findview来优化性能,还封装了一些常用控件的简单用法。下面就是看效果喽.

效果

public abstract class SecondHandAdapter extends BaseAdapter<Post> {
    public SecondHandAdapter(Context context) {
        super(context);
    }

    @Override
    protected int getLayout() {
        return R.layout.second_hand_item;
    }

    @Override
    public void onBind(MyViewHolder viewHolder, int RealPosition) {
        Post post = get(RealPosition);
        viewHolder.setTextView(R.id.test_text, post.getPostContent());
    }

}

看,这样使用不就简单的多了,也不用去创建自己的ViewHolder,也不用去关心数据。只需要简单的使用就够啦。当然如果有不同的ItemType或者增加head或者foot也不用去修改太多。

更多欢迎访问博客
http://70kg.info

参考:

RecyclerView适配器的超省写法
xingrz的干·妹纸
CommonAdapter

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值