赞
踩
我们都知道使用Adapter为ListView或GridView填充数据,而我们需要实现Adapter里的getView、getCount等方法。但内部到底是怎么调用,怎么调用的getView方法,就需要看源码了,下面来简单分析一下:
以GridView为例,为它设置适配器的方法是GridView.setAdapter:
- @Override
- public void setAdapter(ListAdapter adapter) {
- 。。。。。。
- mDataSetObserver = new AdapterDataSetObserver();
- mAdapter.registerDataSetObserver(mDataSetObserver);
- 。。。。。。
- requestLayout();//调用了requestLayout重绘布局方法,简称 重绘(1)。
- }
方法中为adapter注册了一个监听器AdapterDataSetObserver,它存在于GridView的父类AbsListView中(其实这个监听器的真正实现是在AdapterView类中),这个监听器有一个主要的监听方法:
- public void onChanged() {
- mDataChanged = true;
- mOldItemCount = mItemCount;
- mItemCount = getAdapter().getCount();
-
- // Detect the case where a cursor that was previously invalidated has
- // been repopulated with new data.
- if (AdapterView.this.getAdapter().hasStableIds() && mInstanceState != null
- && mOldItemCount == 0 && mItemCount > 0) {
- AdapterView.this.onRestoreInstanceState(mInstanceState);
- mInstanceState = null;
- } else {
- rememberSyncState();
- }
- checkFocus();
- requestLayout();//注意这里也调用了重绘布局方法,简称 重绘(2)。
- }
requestLayout会向系统发一个重新布局的message,重新布局就要重新测量,就要走measure流程,最终会调用到GridView中的onMeasure方法(具体过程可查看android内核剖析的第十三章关于View的绘制内容)。而在GridView的onMeasure中就会调用为GridView设置的Adapter对象的getCount、getItemType方法还会调用一个obtainView(存在于GridView的父类AbsListView中),obtainView中会就会调用Adapter的getView方法来获得单个Item的View了。
了解了这些之后,就可以清楚的了解适配器的调用流程了:
场景1:我们在为GridView设置Adapter(GridView.setAdapter)时最终会调用 “重绘(1)”,然后就会一直调用到GridView的onMeasure方法,在onMeasure方法里就会调用Adapter的getcount、getView等方法获取数据了。
场景2:当数据源改变,我们会调用adapter的notifyDataSetChanged方法来刷新数据,这样会触发Adapter中注册的监听器,最终会调用“重绘(2)”,之后就同场景1的过程一样来获取adapter的数据了。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。