1
0
Fork 0
mirror of https://github.com/MatomoCamp/matomocamp-companion-android.git synced 2024-09-19 16:13:46 +02:00

- Improved SlidingTabLayout to properly handle adapter change and refresh automatically on dataset changed.

- Fixed memory leak caused by keeping the PagerAdapter around after the view hierarchy has been destroyed.
This commit is contained in:
Christophe Beyls 2016-05-29 18:57:49 +02:00
parent ff140b060c
commit 97156d6061
3 changed files with 58 additions and 33 deletions

View file

@ -9,26 +9,19 @@ import android.support.v4.view.ViewPager;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import be.digitalia.fosdem.R;
import com.example.android.common.view.SlidingTabLayout; import com.example.android.common.view.SlidingTabLayout;
import be.digitalia.fosdem.R;
public class LiveFragment extends Fragment { public class LiveFragment extends Fragment {
private LivePagerAdapter livePagerAdapter;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
livePagerAdapter = new LivePagerAdapter(getChildFragmentManager(), getResources());
}
@Override @Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_live, container, false); View view = inflater.inflate(R.layout.fragment_live, container, false);
ViewPager pager = (ViewPager) view.findViewById(R.id.pager); ViewPager pager = (ViewPager) view.findViewById(R.id.pager);
pager.setAdapter(livePagerAdapter); pager.setAdapter(new LivePagerAdapter(getChildFragmentManager(), getResources()));
SlidingTabLayout slidingTabs = (SlidingTabLayout) view.findViewById(R.id.sliding_tabs); SlidingTabLayout slidingTabs = (SlidingTabLayout) view.findViewById(R.id.sliding_tabs);
slidingTabs.setViewPager(pager); slidingTabs.setViewPager(pager);

View file

@ -33,19 +33,18 @@ public class TracksFragment extends Fragment implements LoaderCallbacks<List<Day
View emptyView; View emptyView;
ViewPager pager; ViewPager pager;
SlidingTabLayout slidingTabs; SlidingTabLayout slidingTabs;
DaysAdapter daysAdapter;
} }
private static final int DAYS_LOADER_ID = 1; private static final int DAYS_LOADER_ID = 1;
private static final String PREF_CURRENT_PAGE = "tracks_current_page"; private static final String PREF_CURRENT_PAGE = "tracks_current_page";
private DaysAdapter daysAdapter;
private ViewHolder holder; private ViewHolder holder;
private int savedCurrentPage = -1; private int savedCurrentPage = -1;
@Override @Override
public void onCreate(Bundle savedInstanceState) { public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState); super.onCreate(savedInstanceState);
daysAdapter = new DaysAdapter(getChildFragmentManager());
if (savedInstanceState == null) { if (savedInstanceState == null) {
// Restore the current page from preferences // Restore the current page from preferences
@ -62,6 +61,7 @@ public class TracksFragment extends Fragment implements LoaderCallbacks<List<Day
holder.emptyView = view.findViewById(android.R.id.empty); holder.emptyView = view.findViewById(android.R.id.empty);
holder.pager = (ViewPager) view.findViewById(R.id.pager); holder.pager = (ViewPager) view.findViewById(R.id.pager);
holder.slidingTabs = (SlidingTabLayout) view.findViewById(R.id.sliding_tabs); holder.slidingTabs = (SlidingTabLayout) view.findViewById(R.id.sliding_tabs);
holder.daysAdapter = new DaysAdapter(getChildFragmentManager());
return view; return view;
} }
@ -131,20 +131,19 @@ public class TracksFragment extends Fragment implements LoaderCallbacks<List<Day
@Override @Override
public void onLoadFinished(Loader<List<Day>> loader, List<Day> data) { public void onLoadFinished(Loader<List<Day>> loader, List<Day> data) {
daysAdapter.setDays(data); holder.daysAdapter.setDays(data);
final int totalPages = daysAdapter.getCount(); final int totalPages = holder.daysAdapter.getCount();
if (totalPages == 0) { if (totalPages == 0) {
holder.contentView.setVisibility(View.GONE); holder.contentView.setVisibility(View.GONE);
holder.emptyView.setVisibility(View.VISIBLE); holder.emptyView.setVisibility(View.VISIBLE);
holder.pager.clearOnPageChangeListeners();
} else { } else {
holder.contentView.setVisibility(View.VISIBLE); holder.contentView.setVisibility(View.VISIBLE);
holder.emptyView.setVisibility(View.GONE); holder.emptyView.setVisibility(View.GONE);
if (holder.pager.getAdapter() == null) { if (holder.pager.getAdapter() == null) {
holder.pager.setAdapter(daysAdapter); holder.pager.setAdapter(holder.daysAdapter);
}
holder.slidingTabs.setViewPager(holder.pager); holder.slidingTabs.setViewPager(holder.pager);
}
if (savedCurrentPage != -1) { if (savedCurrentPage != -1) {
holder.pager.setCurrentItem(Math.min(savedCurrentPage, totalPages - 1), false); holder.pager.setCurrentItem(Math.min(savedCurrentPage, totalPages - 1), false);
savedCurrentPage = -1; savedCurrentPage = -1;

View file

@ -20,6 +20,7 @@ package com.example.android.common.view;
import android.content.Context; import android.content.Context;
import android.content.res.ColorStateList; import android.content.res.ColorStateList;
import android.content.res.TypedArray; import android.content.res.TypedArray;
import android.database.DataSetObserver;
import android.graphics.Typeface; import android.graphics.Typeface;
import android.os.Build; import android.os.Build;
import android.support.annotation.ColorInt; import android.support.annotation.ColorInt;
@ -59,6 +60,9 @@ public class SlidingTabLayout extends HorizontalScrollView {
private ColorStateList mTextColor; private ColorStateList mTextColor;
private ViewPager mViewPager; private ViewPager mViewPager;
private PagerAdapter mAdapter;
private final InternalViewPagerListener mPageChangeListener = new InternalViewPagerListener();
private final PagerAdapterObserver mPagerAdapterObserver = new PagerAdapterObserver();
private TabListener mTabListener; private TabListener mTabListener;
@ -148,18 +152,32 @@ public class SlidingTabLayout extends HorizontalScrollView {
} }
/** /**
* Sets the associated view pager. Note that the assumption here is that the pager content * Sets the associated view pager. The ViewPager must have an adapter set.
* (number of tabs and tab titles) does not change after this call has been made. * The SlidingTabLayout will then listen for changes and update the tabs automatically.
*/ */
public void setViewPager(ViewPager viewPager) { public void setViewPager(ViewPager viewPager) {
mViewPager = viewPager; if (mViewPager != null) {
mViewPager.removeOnPageChangeListener(mPageChangeListener);
mAdapter.unregisterDataSetObserver(mPagerAdapterObserver);
}
if (viewPager != null) { if (viewPager != null) {
viewPager.addOnPageChangeListener(new InternalViewPagerListener()); PagerAdapter adapter = viewPager.getAdapter();
if (adapter == null) {
throw new IllegalArgumentException("ViewPager does not have a PagerAdapter set");
}
mViewPager = viewPager;
mAdapter = adapter;
mPageChangeListener.reset();
viewPager.addOnPageChangeListener(mPageChangeListener);
adapter.registerDataSetObserver(mPagerAdapterObserver);
} else {
mViewPager = null;
mAdapter = null;
} }
notifyDataSetChanged(); notifyDataSetChanged();
} }
public void notifyDataSetChanged() { private void notifyDataSetChanged() {
mTabStrip.removeAllViews(); mTabStrip.removeAllViews();
if (mViewPager != null) { if (mViewPager != null) {
populateTabStrip(); populateTabStrip();
@ -167,8 +185,7 @@ public class SlidingTabLayout extends HorizontalScrollView {
} }
private void populateTabStrip() { private void populateTabStrip() {
final PagerAdapter adapter = mViewPager.getAdapter(); final int adapterCount = mAdapter.getCount();
final int adapterCount = adapter.getCount();
final View.OnClickListener tabClickListener = new TabClickListener(); final View.OnClickListener tabClickListener = new TabClickListener();
final LayoutInflater inflater = LayoutInflater.from(getContext()); final LayoutInflater inflater = LayoutInflater.from(getContext());
final int currentItem = mViewPager.getCurrentItem(); final int currentItem = mViewPager.getCurrentItem();
@ -203,7 +220,7 @@ public class SlidingTabLayout extends HorizontalScrollView {
lp.weight = 1; lp.weight = 1;
} }
tabTitleView.setText(adapter.getPageTitle(i)); tabTitleView.setText(mAdapter.getPageTitle(i));
tabView.setFocusable(true); tabView.setFocusable(true);
tabView.setOnClickListener(tabClickListener); tabView.setOnClickListener(tabClickListener);
@ -270,6 +287,22 @@ public class SlidingTabLayout extends HorizontalScrollView {
mTabStrip.getChildAt(i).setSelected(position == i); mTabStrip.getChildAt(i).setSelected(position == i);
} }
} }
public void reset() {
mScrollState = ViewPager.SCROLL_STATE_IDLE;
}
}
private class PagerAdapterObserver extends DataSetObserver {
@Override
public void onChanged() {
notifyDataSetChanged();
}
@Override
public void onInvalidated() {
notifyDataSetChanged();
}
} }
private class TabClickListener implements View.OnClickListener { private class TabClickListener implements View.OnClickListener {