HeaderViewListAdapter

该类其实就是普通使用的Adapter的一个包装类,就是为了添加header和footer而定义的。
该类一般不直接使用,当ListView有header和footer时,ListView中会自动把Adapter封装成一个HeaderViewListAdapter。
源码很简单,相信都能看懂的。下面是android-23版本的源码

/**
* ListAdapter used when a ListView has header views. This ListAdapter
* wraps another one and also keeps track of the header views and their
* associated data objects.
*<p>This is intended as a base class; you will probably not need to
* use this class directly in your own code.
*/
public class HeaderViewListAdapter implements WrapperListAdapter, Filterable {

private final ListAdapter mAdapter;

// These two ArrayList are assumed to NOT be null.
// They are indeed created when declared in ListView and then shared.
ArrayList<ListView.FixedViewInfo> mHeaderViewInfos;
ArrayList<ListView.FixedViewInfo> mFooterViewInfos;

// Used as a placeholder in case the provided info views are indeed null.
// Currently only used by some CTS tests, which may be removed.
static final ArrayList<ListView.FixedViewInfo> EMPTY_INFO_LIST =
new ArrayList<ListView.FixedViewInfo>();

boolean mAreAllFixedViewsSelectable;

private final boolean mIsFilterable;

public HeaderViewListAdapter(ArrayList<ListView.FixedViewInfo> headerViewInfos,
ArrayList<ListView.FixedViewInfo> footerViewInfos,
ListAdapter adapter) {
mAdapter = adapter;
mIsFilterable = adapter instanceof Filterable;

if (headerViewInfos == null) {
mHeaderViewInfos = EMPTY_INFO_LIST;
} else {
mHeaderViewInfos = headerViewInfos;
}

if (footerViewInfos == null) {
mFooterViewInfos = EMPTY_INFO_LIST;
} else {
mFooterViewInfos = footerViewInfos;
}

mAreAllFixedViewsSelectable =
areAllListInfosSelectable(mHeaderViewInfos)
&& areAllListInfosSelectable(mFooterViewInfos);
}

public int getHeadersCount() {
return mHeaderViewInfos.size();
}

public int getFootersCount() {
return mFooterViewInfos.size();
}

public boolean isEmpty() {
return mAdapter == null || mAdapter.isEmpty();
}

private boolean areAllListInfosSelectable(ArrayList<ListView.FixedViewInfo> infos) {
if (infos != null) {
for (ListView.FixedViewInfo info : infos) {
if (!info.isSelectable) {
return false;
}
}
}
return true;
}

public boolean removeHeader(View v) {
for (int i = 0; i < mHeaderViewInfos.size(); i++) {
ListView.FixedViewInfo info = mHeaderViewInfos.get(i);
if (info.view == v) {
mHeaderViewInfos.remove(i);

mAreAllFixedViewsSelectable =
areAllListInfosSelectable(mHeaderViewInfos)
&& areAllListInfosSelectable(mFooterViewInfos);

return true;
}
}

return false;
}

public boolean removeFooter(View v) {
for (int i = 0; i < mFooterViewInfos.size(); i++) {
ListView.FixedViewInfo info = mFooterViewInfos.get(i);
if (info.view == v) {
mFooterViewInfos.remove(i);

mAreAllFixedViewsSelectable =
areAllListInfosSelectable(mHeaderViewInfos)
&& areAllListInfosSelectable(mFooterViewInfos);

return true;
}
}

return false;
}

public int getCount() {
if (mAdapter != null) {
return getFootersCount() + getHeadersCount() + mAdapter.getCount();
} else {
return getFootersCount() + getHeadersCount();
}
}

public boolean areAllItemsEnabled() {
if (mAdapter != null) {
return mAreAllFixedViewsSelectable && mAdapter.areAllItemsEnabled();
} else {
return true;
}
}

public boolean isEnabled(int position) {
// Header (negative positions will throw an IndexOutOfBoundsException)
int numHeaders = getHeadersCount();
if (position < numHeaders) {
return mHeaderViewInfos.get(position).isSelectable;
}

// Adapter
final int adjPosition = position - numHeaders;
int adapterCount = 0;
if (mAdapter != null) {
adapterCount = mAdapter.getCount();
if (adjPosition < adapterCount) {
return mAdapter.isEnabled(adjPosition);
}
}

// Footer (off-limits positions will throw an IndexOutOfBoundsException)
return mFooterViewInfos.get(adjPosition - adapterCount).isSelectable;
}

public Object getItem(int position) {
// Header (negative positions will throw an IndexOutOfBoundsException)
int numHeaders = getHeadersCount();
if (position < numHeaders) {
return mHeaderViewInfos.get(position).data;
}

// Adapter
final int adjPosition = position - numHeaders;
int adapterCount = 0;
if (mAdapter != null) {
adapterCount = mAdapter.getCount();
if (adjPosition < adapterCount) {
return mAdapter.getItem(adjPosition);
}
}

// Footer (off-limits positions will throw an IndexOutOfBoundsException)
return mFooterViewInfos.get(adjPosition - adapterCount).data;
}

public long getItemId(int position) {
int numHeaders = getHeadersCount();
if (mAdapter != null && position >= numHeaders) {
int adjPosition = position - numHeaders;
int adapterCount = mAdapter.getCount();
if (adjPosition < adapterCount) {
return mAdapter.getItemId(adjPosition);
}
}
return -1;
}

public boolean hasStableIds() {
if (mAdapter != null) {
return mAdapter.hasStableIds();
}
return false;
}

public View getView(int position, View convertView, ViewGroup parent) {
// Header (negative positions will throw an IndexOutOfBoundsException)
int numHeaders = getHeadersCount();
if (position < numHeaders) {
return mHeaderViewInfos.get(position).view;
}

// Adapter
final int adjPosition = position - numHeaders;
int adapterCount = 0;
if (mAdapter != null) {
adapterCount = mAdapter.getCount();
if (adjPosition < adapterCount) {
return mAdapter.getView(adjPosition, convertView, parent);
}
}

// Footer (off-limits positions will throw an IndexOutOfBoundsException)
return mFooterViewInfos.get(adjPosition - adapterCount).view;
}

public int getItemViewType(int position) {
int numHeaders = getHeadersCount();
if (mAdapter != null && position >= numHeaders) {
int adjPosition = position - numHeaders;
int adapterCount = mAdapter.getCount();
if (adjPosition < adapterCount) {
return mAdapter.getItemViewType(adjPosition);
}
}

return AdapterView.ITEM_VIEW_TYPE_HEADER_OR_FOOTER;
}

public int getViewTypeCount() {
if (mAdapter != null) {
return mAdapter.getViewTypeCount();
}
return 1;
}

public void registerDataSetObserver(DataSetObserver observer) {
if (mAdapter != null) {
mAdapter.registerDataSetObserver(observer);
}
}

public void unregisterDataSetObserver(DataSetObserver observer) {
if (mAdapter != null) {
mAdapter.unregisterDataSetObserver(observer);
}
}

public Filter getFilter() {
if (mIsFilterable) {
return ((Filterable) mAdapter).getFilter();
}
return null;
}

public ListAdapter getWrappedAdapter() {
return mAdapter;
}
}
posted @ 2016-08-24 17:05  linghu_java  阅读(444)  评论(0编辑  收藏  举报