Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
An implementation of PagerAdapter for views
/**
* View Pager Adapter - An implementation of PagerAdapter for views
* Simplified implementation which enables access to created view at a specific position
* for controlling the view status and force pre creation of a view when necessary
*
* Created by tomergoldst on 15/11/2018.
*/
public abstract class ViewPagerAdapter<T> extends PagerAdapter {
private SparseArray<T> mViews = new SparseArray<>();
private final Object mLock = new Object();
/**
* Force create view at position
*
* @param position position
* @return view created by createView(int position)
*/
public final T forceViewCreation(int position) {
return instantiateView(position);
}
/**
* re-instantiate all cached views, this will trigger the abstract {@link #createView(int)} and
* {@link #onViewCreated(Object, int)}
*/
public final void reInstantiateCachedViews() {
synchronized (mLock) {
for (int i = 0, N = mViews.size(); i < N; i++) {
int key = mViews.keyAt(i);
instantiateView(key);
}
}
}
/**
* Clear cache. Using this operation should follow a call to setAdapter which in turn will call
* instantiateItem
*/
public final void clearCache() {
synchronized (mLock) {
mViews.clear();
}
}
/**
* Create view at position
*
* @param position position
* @return view created by createView(int position)
*/
private T instantiateView(int position) {
synchronized (mLock) {
isValidPosition(position);
T view = checkNotNull(createView(position));
mViews.put(position, view);
onViewCreated(view, position);
return view;
}
}
/**
* Called after view was created
*
* @param view created view
* @param position position
*/
public void onViewCreated(T view, int position) {
// Empty implementation
}
/**
* Check if position is valid
*
* @param position position
*/
private void isValidPosition(int position) {
if (position < 0 || position > getCount() - 1) {
throw new RuntimeException("position " + position + " is not valid, " +
"getCount() == " + getCount());
}
}
/**
* Create view at position
*
* @param position viewpager position
* @return DaysPickerView
*/
public abstract T createView(int position);
/**
* get view at position. If view at position doesn't exist create the view
*
* @param position viewpager position
* @return DaysPickerView
*/
public final T getViewAtPosition(int position) {
synchronized (mLock) {
isValidPosition(position);
T view = mViews.get(position);
if (view == null) {
view = instantiateView(position);
}
return view;
}
}
/**
* get cached view at position. If view at position doesn't exist return null
*
* @param position viewpager position
* @return DaysPickerView
*/
public final T getCachedViewAtPosition(int position) {
synchronized (mLock) {
isValidPosition(position);
return mViews.get(position);
}
}
/**
* @param position requested view position
* @return true if mViews contain view on position
*/
protected final boolean isViewExist(int position) {
synchronized (mLock) {
isValidPosition(position);
return mViews.get(position) != null;
}
}
@Override
abstract public int getCount();
@NotNull
@Override
public final Object instantiateItem(ViewGroup container, int position) {
View view = (View) getViewAtPosition(position);
container.addView(view);
return view;
}
@Override
public final boolean isViewFromObject(@NotNull View view, @NotNull Object object) {
return view == object;
}
@Override
public void destroyItem(@NotNull ViewGroup container, int position, @NotNull Object object) {
View view = (View) object;
container.removeView(view);
removeView(position);
}
/**
* @param position of view to remove
*/
private void removeView(int position) {
synchronized (mLock) {
isValidPosition(position);
mViews.remove(position);
}
}
private static <T> T checkNotNull(T reference) {
if (reference == null) {
throw new NullPointerException();
} else {
return reference;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.