整体总结
listview的用法
- 继承BaseAdapter,需要重写四个方法
- 不强制使用viewholder
- 可以直接使用item的点击事件
- 不用单独设置分隔线
android:divider="@android:color/transparent"
android:dividerHeight="5dp"
- 不可以定向刷新某一条数据
public class MyListAdapter<T> extends BaseAdapter {
private static final String TAG = "MyListAdapter";
private Context mContext;
// private int itemViewId;
private List<T> datas;
public MyListAdapter(Context mContext, /*int itemViewId,*/ List<T> datas) {
this.mContext = mContext;
// this.itemViewId = itemViewId;
this.datas = datas;
}
@Override
public int getCount() {
return datas == null ? 0 : datas.size();
}
@Override
public T getItem(int position) {
return datas.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
Log.d(TAG, "getView: " + position);
MyHolder holder;
if (convertView == null) {
convertView = View.inflate(mContext, R.layout.ada_item, null);
holder = new MyHolder(convertView);
convertView.setTag(holder);
} else {
holder = (MyHolder) convertView.getTag();
}
holder.itemTv.setText((CharSequence) datas.get(position));
return convertView;
}
static class MyHolder {
@BindView(R.id.item)
TextView itemTv;
public MyHolder(View view) {
ButterKnife.bind(this, view);
}
}
}
recycleview的用法
- 继承的是Recycleview.Adapter
- 必须使用viewholder,封装了view的复用
- 使用布局管理器管理布局的样式(横向、竖向、网格、瀑布流布局)
- 点击事件可以使用给控件设置点击事件,也可以自定义点击事件。
- 可以自定义绘制分隔线
- 可以自定义item删除增加的动画效果
- 可以定向刷新某一条数据notifyItemChanged等众多方法
public class StepViewAdapter extends RecyclerView.Adapter<StepViewAdapter.StepViewViewHolder> {
private final Context context;
private List<String> data;
private int currentPosition = 0;
public StepViewAdapter(Context context) {
this(context, new ArrayList<>());
}
public StepViewAdapter(Context context, List<String> data) {
this.context = context;
this.data = data;
}
public void setData(List<String> data) {
this.data = data;
notifyDataSetChanged();
}
public int getCurrentPosition() {
return currentPosition;
}
@NonNull
@Override
public StepViewViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View view = View.inflate(context, R.layout.profilenew_step_view_item, null);
return new StepViewViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull StepViewViewHolder holder, int position) {
holder.textView.setText(data.get(position));
// textViews.add(holder.textView);
}
@Override
public int getItemCount() {
return data.size();
}
public class StepViewViewHolder extends RecyclerView.ViewHolder {
private LinearLayout linearLayout;
private TextView textView;
public StepViewViewHolder(@NonNull View itemView) {
super(itemView);
linearLayout = itemView.findViewById(R.id.ll_step_view);
textView = itemView.findViewById(R.id.step_view_item);
}
}
}
布局上
listview:布局比较单一,只支持竖直方向滑动
recyclerview:三种布局
1、线性布局,这个和listview相似 ,实现横向/纵向列表方向的item
LinearLayoutManager layoutManager = new LinearLayoutManager(this);
recyclerView.setLayoutManager(layoutManager);
2、网格布局,可以指定item的数量
mRecyclerView.setLayoutManager(new GridLayoutManager(this,2));//可指定一行item的数目
3、瀑布流布局,可以指定列表方向,也可以指定同方向的item数量StaggeredGridLayoutManager
局部刷新
1.listview:listview中通常刷新数据 notifyDataSetChanged() ,这种刷新是全局刷新的,每一个item的数据都会重新加载一次,这样很消耗资源,在一些需要频繁更新数据的场景,比如淘宝实时更新的界面,listview实现会很鸡肋
2.recyclerview:可以通过 notifyItemChanged() 来实现局部刷新
ps:不过如果要在ListView实现局部刷新,依然是可以实现的,当一个item数据刷新时,我们可以在Adapter中,实现一个onItemChanged()方法,在方法里面获取到这个item的position(可以通过getFirstVisiblePosition()),然后调用getView()方法来刷新这个item的数据。
item view的重用
listview:默认每次加载一个新的item创建一个新view,引起内存增加,不过可以通过判断 convertView 是否为空来重用view。
convertView 不为空,则不会产生新的条目, 屏幕上始终是一开始生成的那几个条目
recyclerview:默认实现重用view, RecyclerView复用item全部搞定,不需要像ListView那样setTag()与getTag();
ViewHolder
listview:viewHolder需要自定义,如果用getview去获取控件,则每次调用getview都要通过 findViewById 去获取控件, 如果控件个数过多,会严重影响性能 ,因为findViewById相对比较耗时,所以我们需要创建自定义viewHolder,通过getTag和setTag直接获取view。
recyclerview:继承recyclerView.ViewHolder,默认需要重写viewHodler,使用已经封装好的
嵌套滑动机制
Android 5.0推出了嵌套滑动机制,在之前,一旦子View处理了触摸事件,父View就没有机会再处理这次的触摸事件,而嵌套滑动机制解决了这个问题,
为了支持嵌套滑动,子View必须实现NestedScrollingChild接口,父View必须实现NestedScrollingParent接口。
NestedScrollingChild接口,而CoordinatorLayout实现了NestedScrollingParent接口,上图是实现CoordinatorLayout嵌套RecyclerView的效果。
listview: ListView 并不支持嵌套滚动机制
空数据处理
ListView 提供了 setEmptyView 这个 API 来让我们处理 Adapter 中数据为空的情况
recyclerview没有提供
缓存机制
Android ListView与RecyclerView对比浅析_recycleview的好处_萨达哈鲁君的博客-CSDN博客