给RecyclerView增加头部布局本身不存在什么难度,按照我们正常的流程,写一个符合我们业务逻辑的头部布局的ViewHolder,然后在getItemViewType()里通过position返回一个表示头部布局ViewHolder的Type类型,然后在onCreateItemViewHolder(ViewGroup parent, int viewType)里通过viewType来初始化return我们不同的ViewHolder。
public void addHeader(View headerView) {
if (!headerViews.contains(headerView)) {
headerViews.add(headerView);
//当然这里可以使用notifyItemChanged(int position)去优化
notifyDataSetChanged();
}
}
给Header设置一个合适的Type,比如:
public static final int VIEW_TYPE_HEADER_OFFSET = Integer.MIN_VALUE;
接下来就是getItemViewType()方法的处理了。
@Override
public int getItemViewType(int position) {
if (!headerViews.isEmpty() && position < headerViews.size()) {
return VIEW_TYPE_HEADER_OFFSET + position;
}
//计算我们常规数据的position,也就是减去Header的List的size的数量即可
if (!headerViews.isEmpty()) {
position -= headerViews.size();
}
//adapter就是我们在构造方法里传进来的RecyclerView.Adapter
if (adapter != null && position < adapter.getItemCount()) {
return adapter.getItemViewType(position);
}
}
return了viewType,那么我们就要处理onCreateViewHolder()方法了。
public static boolean isHeaderView(int viewType) {
return viewType < VIEW_TYPE_HEADER_OFFSET;
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
if (isHeaderView(viewType)) {
return new HeaderViewHolder(headerViews.get(viewType - VIEW_TYPE_HEADER_OFFSET));
}
return adapter.onCreateViewHolder(parent, viewType);
}
@Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
int viewType = getItemViewType(position);
//这里直接return的原因,我们这里不做对Header的处理,交由外部。
if (isHeaderView(viewType)) {
return;
}
position -= headerViews.size();
adapter.onBindViewHolder(holder, position);
}