0、相关文章
1、前言
使用ViewPager的时候,删除数据后调用 notifyDataSetChanged(),界面却无法刷新。
2、PagerAdapter 的刷新
2.1、源码解析
要想真正的理解PagerAdapter的刷新,就一定要从源码找突破口。下面是PagerAdapter的类注释。
/**
* ......
*
* <p>PagerAdapter supports data set changes. Data set changes must occur on the
* main thread and must end with a call to {@link #notifyDataSetChanged()} similar
* to AdapterView adapters derived from {@link android.widget.BaseAdapter}. A data
* set change may involve pages being added, removed, or changing position. The
* ViewPager will keep the current page active provided the adapter implements
* the method {@link #getItemPosition(Object)}.</p>
*/
public abstract class PagerAdapter {
//......
public static final int POSITION_UNCHANGED = -1;
public static final int POSITION_NONE = -2;
//......
}
看PagerAdapter的最后一段,大概翻译一下,意思是:
PagerAdapter支持数据集改变。数据集的改变必须发生在主线程,并且以调用notifyDataSetChanged()方法结束,类似于AdapterView的适配器(继承自android.widget.BaseAdapter的)。数据集改变包括页面被添加、删除或位置改变。如果适配器实现了方法getItemPosition(Object),ViewPager将保持当前页面处于活动状态。
这段话有一个非常明确的信息:PagerAdapter可以通过调用notifyDataSetChanged()方法实现数据集的刷新。这就打破了有些人认为的ViewPager无法通过notifyDataSetChanged()刷新的认知。而且,这段话还告诉我们,我们可能需要实现方法getItemPosition(Object)。下面我面找到该方法的源码看一下:
/**
* Called when the host view is attempting to determine if an item's position
* has changed. Returns {@link #POSITION_UNCHANGED} if the position of the given
* item has not changed or {@link #POSITION_NONE} if the item is no longer present
* in the adapter.
*
* <p>The default implementation assumes that items will never
* change position and always returns {@link #POSITION_UNCHANGED}.
*
* @param object Object representing an item, previously returned by a call to
* {@link #instantiateItem(View, int)}.
* @return object's new position index from [0, {@link #getCount()}),
* {@link #POSITION_UNCHANGED} if the object's position has not changed,
* or {@link #POSITION_NONE} if the item is no longer present.
*/
public int getItemPosition(Object object) {
return POSITION_UNCHANGED;
}
需要看一下方法注释,大概意思是:
当主控件(个人认为是ViewPager)尝试确定item的位置是否已经改变时调用。如果给定的item位置没有改变,返回POSITION_UNCHANGED;如果item已经在适配器中不存在了,返回POSITION_NONE。
默认实现假设所有item永远不会改变位置并且总是返回POSITION_UNCHANGED(未改变)。
参数:object 代表一个item的对象(个人认为:View或Fragment),最初由instantiateItem(View, int) 方法返回。
返回 如果位置发生改变,返回对象的新位置,是0到getCount()的索引(不包括getCount());如果位置没有改变,返回 POSITION_UNCHANGED ;如果item不存在了,返回 POSITION_NONE 。
2.2、代码实现
覆写以下方法并返回 POSITION_NONE 就可以了。
@Override
public int getItemPosition(Object object) {
return POSITION_NONE;
}