Make dashboard tile refresh more effcient.
Instead of removing and re-adding all dashboard tiles, figure out a diff and rebind/add/remove as necessary. Bug: 32255863 Test: RunSettingsRoboTests Change-Id: I9d87ba30ab746257d0ea71282951348ebc4e8965
This commit is contained in:
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.android.settings.dashboard;
|
||||
|
||||
import android.content.Context;
|
||||
import android.support.v7.preference.Preference;
|
||||
|
||||
import com.android.settingslib.drawer.DashboardCategory;
|
||||
@@ -53,4 +54,10 @@ public interface DashboardFeatureProvider {
|
||||
* Returns an unique string key for the tile.
|
||||
*/
|
||||
String getDashboardKeyForTile(Tile tile);
|
||||
|
||||
/**
|
||||
* Returns a {@link ProgressiveDisclosureMixin} for specified fragment.
|
||||
*/
|
||||
ProgressiveDisclosureMixin getProgressiveDisclosureMixin(Context context,
|
||||
DashboardFragment fragment);
|
||||
}
|
||||
|
@@ -72,4 +72,10 @@ public class DashboardFeatureProviderImpl implements DashboardFeatureProvider {
|
||||
sb.append(component.getClassName());
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ProgressiveDisclosureMixin getProgressiveDisclosureMixin(Context context,
|
||||
DashboardFragment fragment) {
|
||||
return new ProgressiveDisclosureMixin(context, this, fragment);
|
||||
}
|
||||
}
|
||||
|
@@ -22,7 +22,9 @@ import android.graphics.Color;
|
||||
import android.graphics.drawable.ColorDrawable;
|
||||
import android.graphics.drawable.Drawable;
|
||||
import android.os.Bundle;
|
||||
import android.support.annotation.VisibleForTesting;
|
||||
import android.support.v7.preference.Preference;
|
||||
import android.support.v7.preference.PreferenceManager;
|
||||
import android.support.v7.preference.PreferenceScreen;
|
||||
import android.text.TextUtils;
|
||||
import android.util.ArrayMap;
|
||||
@@ -41,6 +43,7 @@ import com.android.settingslib.drawer.DashboardCategory;
|
||||
import com.android.settingslib.drawer.SettingsDrawerActivity;
|
||||
import com.android.settingslib.drawer.Tile;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
@@ -69,7 +72,8 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
super.onAttach(context);
|
||||
mDashboardFeatureProvider =
|
||||
FeatureFactory.getFactory(context).getDashboardFeatureProvider(context);
|
||||
mProgressiveDisclosureMixin = new ProgressiveDisclosureMixin(context, this);
|
||||
mProgressiveDisclosureMixin = mDashboardFeatureProvider
|
||||
.getProgressiveDisclosureMixin(context, this);
|
||||
getLifecycle().addObserver(mProgressiveDisclosureMixin);
|
||||
|
||||
final List<PreferenceController> controllers = getPreferenceControllers(context);
|
||||
@@ -81,6 +85,24 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreate(Bundle icicle) {
|
||||
super.onCreate(icicle);
|
||||
// Set ComparisonCallback so we get better animation when list changes.
|
||||
getPreferenceManager().setPreferenceComparisonCallback(
|
||||
new PreferenceManager.SimplePreferenceComparisonCallback());
|
||||
}
|
||||
|
||||
@Override
|
||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||
Bundle savedInstanceState) {
|
||||
final View view = super.onCreateView(inflater, container, savedInstanceState);
|
||||
if (mDashboardFeatureProvider.isEnabled()) {
|
||||
getListView().addItemDecoration(mDividerDecoration);
|
||||
}
|
||||
return view;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCategoriesChanged() {
|
||||
final DashboardCategory category =
|
||||
@@ -98,6 +120,18 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
refreshAllPreferences(getLogTag());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDivider(Drawable divider) {
|
||||
if (mDashboardFeatureProvider.isEnabled()) {
|
||||
// Intercept divider and set it transparent so system divider decoration is disabled.
|
||||
// We will use our decoration to draw divider more intelligently.
|
||||
mDividerDecoration.setDivider(divider);
|
||||
super.setDivider(new ColorDrawable(Color.TRANSPARENT));
|
||||
} else {
|
||||
super.setDivider(divider);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStart() {
|
||||
super.onStart();
|
||||
@@ -210,16 +244,6 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||
Bundle savedInstanceState) {
|
||||
final View view = super.onCreateView(inflater, container, savedInstanceState);
|
||||
if (mDashboardFeatureProvider.isEnabled()) {
|
||||
getListView().addItemDecoration(mDividerDecoration);
|
||||
}
|
||||
return view;
|
||||
}
|
||||
|
||||
/**
|
||||
* Update state of each preference managed by PreferenceController.
|
||||
*/
|
||||
@@ -238,18 +262,6 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDivider(Drawable divider) {
|
||||
if (mDashboardFeatureProvider.isEnabled()) {
|
||||
// Intercept divider and set it transparent so system divider decoration is disabled.
|
||||
// We will use our decoration to draw divider more intelligently.
|
||||
mDividerDecoration.setDivider(divider);
|
||||
super.setDivider(new ColorDrawable(Color.TRANSPARENT));
|
||||
} else {
|
||||
super.setDivider(divider);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Refresh all preference items, including both static prefs from xml, and dynamic items from
|
||||
* DashboardCategory.
|
||||
@@ -275,18 +287,15 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
/**
|
||||
* Refresh preference items backed by DashboardCategory.
|
||||
*/
|
||||
private void refreshDashboardTiles(final String TAG) {
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
void refreshDashboardTiles(final String TAG) {
|
||||
final PreferenceScreen screen = getPreferenceScreen();
|
||||
for (String key : mDashboardTilePrefKeys) {
|
||||
// Remove tiles from screen
|
||||
mProgressiveDisclosureMixin.removePreference(screen, key);
|
||||
}
|
||||
mDashboardTilePrefKeys.clear();
|
||||
|
||||
final Context context = getContext();
|
||||
final DashboardCategory category =
|
||||
mDashboardFeatureProvider.getTilesForCategory(getCategoryKey());
|
||||
if (category == null) {
|
||||
Log.d(TAG, "NO dynamic tiles for " + TAG);
|
||||
Log.d(TAG, "NO dashboard tiles for " + TAG);
|
||||
return;
|
||||
}
|
||||
List<Tile> tiles = category.tiles;
|
||||
@@ -294,6 +303,9 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
Log.d(TAG, "tile list is empty, skipping category " + category.title);
|
||||
return;
|
||||
}
|
||||
// Create a list to track which tiles are to be removed.
|
||||
final List<String> remove = new ArrayList<>(mDashboardTilePrefKeys);
|
||||
|
||||
// There are dashboard tiles, so we need to install SummaryLoader.
|
||||
if (mSummaryLoader != null) {
|
||||
mSummaryLoader.release();
|
||||
@@ -307,32 +319,51 @@ public abstract class DashboardFragment extends SettingsPreferenceFragment
|
||||
Log.d(TAG, "tile does not contain a key, skipping " + tile);
|
||||
continue;
|
||||
}
|
||||
mDashboardTilePrefKeys.add(key);
|
||||
final Preference pref = new DashboardTilePreference(context);
|
||||
pref.setTitle(tile.title);
|
||||
pref.setKey(key);
|
||||
pref.setSummary(tile.summary);
|
||||
if (tile.icon != null) {
|
||||
pref.setIcon(tile.icon.loadDrawable(context));
|
||||
if (mDashboardTilePrefKeys.contains(key)) {
|
||||
// Have the key already, will rebind.
|
||||
final Preference preference = mProgressiveDisclosureMixin.findPreference(
|
||||
screen, key);
|
||||
bindPreferenceToTile(context, preference, tile, key);
|
||||
} else {
|
||||
// Don't have this key, add it.
|
||||
final Preference pref = new DashboardTilePreference(context);
|
||||
bindPreferenceToTile(context, pref, tile, key);
|
||||
mProgressiveDisclosureMixin.addPreference(screen, pref);
|
||||
mDashboardTilePrefKeys.add(key);
|
||||
}
|
||||
final Bundle metadata = tile.metaData;
|
||||
if (metadata != null) {
|
||||
String clsName = metadata.getString(SettingsActivity.META_DATA_KEY_FRAGMENT_CLASS);
|
||||
if (!TextUtils.isEmpty(clsName)) {
|
||||
pref.setFragment(clsName);
|
||||
}
|
||||
} else if (tile.intent != null) {
|
||||
final Intent intent = new Intent(tile.intent);
|
||||
pref.setOnPreferenceClickListener(preference -> {
|
||||
getActivity().startActivityForResult(intent, 0);
|
||||
return true;
|
||||
});
|
||||
}
|
||||
// Use negated priority for order, because tile priority is based on intent-filter
|
||||
// (larger value has higher priority). However pref order defines smaller value has
|
||||
// higher priority.
|
||||
pref.setOrder(-tile.priority);
|
||||
mProgressiveDisclosureMixin.addPreference(screen, pref);
|
||||
remove.remove(key);
|
||||
}
|
||||
// Finally remove tiles that are gone.
|
||||
for (String key : remove) {
|
||||
mDashboardTilePrefKeys.remove(key);
|
||||
mProgressiveDisclosureMixin.removePreference(screen, key);
|
||||
}
|
||||
}
|
||||
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
void bindPreferenceToTile(Context context, Preference pref, Tile tile, String key) {
|
||||
pref.setTitle(tile.title);
|
||||
pref.setKey(key);
|
||||
pref.setSummary(tile.summary);
|
||||
if (tile.icon != null) {
|
||||
pref.setIcon(tile.icon.loadDrawable(context));
|
||||
}
|
||||
final Bundle metadata = tile.metaData;
|
||||
if (metadata != null) {
|
||||
String clsName = metadata.getString(SettingsActivity.META_DATA_KEY_FRAGMENT_CLASS);
|
||||
if (!TextUtils.isEmpty(clsName)) {
|
||||
pref.setFragment(clsName);
|
||||
}
|
||||
} else if (tile.intent != null) {
|
||||
final Intent intent = new Intent(tile.intent);
|
||||
pref.setOnPreferenceClickListener(preference -> {
|
||||
getActivity().startActivityForResult(intent, 0);
|
||||
return true;
|
||||
});
|
||||
}
|
||||
// Use negated priority for order, because tile priority is based on intent-filter
|
||||
// (larger value has higher priority). However pref order defines smaller value has
|
||||
// higher priority.
|
||||
pref.setOrder(-tile.priority);
|
||||
}
|
||||
}
|
||||
|
@@ -28,9 +28,9 @@ import android.util.Log;
|
||||
import com.android.settings.core.lifecycle.LifecycleObserver;
|
||||
import com.android.settings.core.lifecycle.events.OnCreate;
|
||||
import com.android.settings.core.lifecycle.events.OnSaveInstanceState;
|
||||
import com.android.settings.overlay.FeatureFactory;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickListener,
|
||||
@@ -43,18 +43,19 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
private int mTileLimit = DEFAULT_TILE_LIMIT;
|
||||
|
||||
private final DashboardFeatureProvider mDashboardFeatureProvider;
|
||||
private final List<Preference> collapsedPrefs = new ArrayList<>();
|
||||
// Collapsed preference sorted by order.
|
||||
private final List<Preference> mCollapsedPrefs = new ArrayList<>();
|
||||
private final ExpandPreference mExpandButton;
|
||||
private final PreferenceFragment mFragment;
|
||||
|
||||
private boolean mUserExpanded;
|
||||
|
||||
public ProgressiveDisclosureMixin(Context context, PreferenceFragment fragment) {
|
||||
public ProgressiveDisclosureMixin(Context context,
|
||||
DashboardFeatureProvider dashboardFeatureProvider, PreferenceFragment fragment) {
|
||||
mFragment = fragment;
|
||||
mExpandButton = new ExpandPreference(context);
|
||||
mExpandButton.setOnPreferenceClickListener(this);
|
||||
mDashboardFeatureProvider = FeatureFactory.getFactory(context)
|
||||
.getDashboardFeatureProvider(context);
|
||||
mDashboardFeatureProvider = dashboardFeatureProvider;
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -75,10 +76,10 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
final PreferenceScreen screen = mFragment.getPreferenceScreen();
|
||||
if (screen != null) {
|
||||
screen.removePreference(preference);
|
||||
for (Preference pref : collapsedPrefs) {
|
||||
for (Preference pref : mCollapsedPrefs) {
|
||||
screen.addPreference(pref);
|
||||
}
|
||||
collapsedPrefs.clear();
|
||||
mCollapsedPrefs.clear();
|
||||
mUserExpanded = true;
|
||||
}
|
||||
}
|
||||
@@ -96,7 +97,7 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
* Whether the controller is in collapsed state.
|
||||
*/
|
||||
public boolean isCollapsed() {
|
||||
return !collapsedPrefs.isEmpty();
|
||||
return !mCollapsedPrefs.isEmpty();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -115,7 +116,7 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
if (!shouldCollapse(screen)) {
|
||||
return;
|
||||
}
|
||||
if (!collapsedPrefs.isEmpty()) {
|
||||
if (!mCollapsedPrefs.isEmpty()) {
|
||||
Log.w(TAG, "collapsed list should ALWAYS BE EMPTY before collapsing!");
|
||||
}
|
||||
|
||||
@@ -134,12 +135,27 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
public void addPreference(PreferenceScreen screen, Preference pref) {
|
||||
// Either add to screen, or to collapsed list.
|
||||
if (isCollapsed()) {
|
||||
// Already collapsed, add to collapsed list.
|
||||
addToCollapsedList(pref);
|
||||
// insert the preference to right position.
|
||||
final int lastPreferenceIndex = screen.getPreferenceCount() - 2;
|
||||
if (lastPreferenceIndex >= 0) {
|
||||
final Preference lastPreference = screen.getPreference(lastPreferenceIndex);
|
||||
if (lastPreference.getOrder() > pref.getOrder()) {
|
||||
// insert to screen and move the last pref to collapsed list.
|
||||
screen.removePreference(lastPreference);
|
||||
screen.addPreference(pref);
|
||||
addToCollapsedList(lastPreference);
|
||||
} else {
|
||||
// Insert to collapsed list.
|
||||
addToCollapsedList(pref);
|
||||
}
|
||||
} else {
|
||||
// Couldn't find last preference on screen, just add to collapsed list.
|
||||
addToCollapsedList(pref);
|
||||
}
|
||||
} else if (shouldCollapse(screen)) {
|
||||
// About to have too many tiles on scree, collapse and add pref to collapsed list.
|
||||
screen.addPreference(pref);
|
||||
collapse(screen);
|
||||
addToCollapsedList(pref);
|
||||
} else {
|
||||
// No need to collapse, add to screen directly.
|
||||
screen.addPreference(pref);
|
||||
@@ -158,11 +174,11 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
return;
|
||||
}
|
||||
// Didn't find on screen, try removing from collapsed list.
|
||||
for (int i = 0; i < collapsedPrefs.size(); i++) {
|
||||
final Preference pref = collapsedPrefs.get(i);
|
||||
for (int i = 0; i < mCollapsedPrefs.size(); i++) {
|
||||
final Preference pref = mCollapsedPrefs.get(i);
|
||||
if (TextUtils.equals(key, pref.getKey())) {
|
||||
collapsedPrefs.remove(pref);
|
||||
if (collapsedPrefs.isEmpty()) {
|
||||
mCollapsedPrefs.remove(pref);
|
||||
if (mCollapsedPrefs.isEmpty()) {
|
||||
// Removed last element, remove expand button too.
|
||||
screen.removePreference(mExpandButton);
|
||||
}
|
||||
@@ -179,8 +195,8 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
if (preference != null) {
|
||||
return preference;
|
||||
}
|
||||
for (int i = 0; i < collapsedPrefs.size(); i++) {
|
||||
final Preference pref = collapsedPrefs.get(i);
|
||||
for (int i = 0; i < mCollapsedPrefs.size(); i++) {
|
||||
final Preference pref = mCollapsedPrefs.get(i);
|
||||
if (TextUtils.equals(key, pref.getKey())) {
|
||||
return pref;
|
||||
}
|
||||
@@ -192,9 +208,18 @@ public class ProgressiveDisclosureMixin implements Preference.OnPreferenceClickL
|
||||
/**
|
||||
* Add preference to collapsed list.
|
||||
*/
|
||||
@VisibleForTesting
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
void addToCollapsedList(Preference preference) {
|
||||
collapsedPrefs.add(preference);
|
||||
// Insert preference based on it's order.
|
||||
int insertionIndex = Collections.binarySearch(mCollapsedPrefs, preference);
|
||||
if (insertionIndex < 0) {
|
||||
insertionIndex = insertionIndex * -1 - 1;
|
||||
}
|
||||
mCollapsedPrefs.add(insertionIndex, preference);
|
||||
}
|
||||
|
||||
@VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
|
||||
List<Preference> getCollapsedPrefs() {
|
||||
return mCollapsedPrefs;
|
||||
}
|
||||
}
|
||||
|
@@ -16,10 +16,13 @@
|
||||
package com.android.settings.dashboard;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Bitmap;
|
||||
import android.graphics.drawable.Icon;
|
||||
import android.os.Bundle;
|
||||
import android.support.v7.preference.Preference;
|
||||
import android.support.v7.preference.PreferenceScreen;
|
||||
|
||||
import com.android.settings.SettingsActivity;
|
||||
import com.android.settings.TestConfig;
|
||||
import com.android.settings.core.PreferenceController;
|
||||
import com.android.settings.overlay.FeatureFactory;
|
||||
@@ -44,6 +47,7 @@ import java.util.List;
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
import static org.mockito.Matchers.any;
|
||||
import static org.mockito.Matchers.anyString;
|
||||
import static org.mockito.Matchers.eq;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.never;
|
||||
import static org.mockito.Mockito.verify;
|
||||
@@ -59,6 +63,8 @@ public class DashboardFragmentTest {
|
||||
private DashboardCategory mDashboardCategory;
|
||||
@Mock
|
||||
private FakeFeatureFactory mFakeFeatureFactory;
|
||||
@Mock
|
||||
private ProgressiveDisclosureMixin mDisclosureMixin;
|
||||
private TestFragment mTestFragment;
|
||||
|
||||
@Before
|
||||
@@ -69,9 +75,12 @@ public class DashboardFragmentTest {
|
||||
mDashboardCategory.tiles = new ArrayList<>();
|
||||
mDashboardCategory.tiles.add(new Tile());
|
||||
mTestFragment = new TestFragment(ShadowApplication.getInstance().getApplicationContext());
|
||||
mTestFragment.onAttach(ShadowApplication.getInstance().getApplicationContext());
|
||||
when(mFakeFeatureFactory.dashboardFeatureProvider
|
||||
.getProgressiveDisclosureMixin(any(Context.class), eq(mTestFragment)))
|
||||
.thenReturn(mDisclosureMixin);
|
||||
when(mFakeFeatureFactory.dashboardFeatureProvider.getTilesForCategory(anyString()))
|
||||
.thenReturn(mDashboardCategory);
|
||||
mTestFragment.onAttach(ShadowApplication.getInstance().getApplicationContext());
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -87,11 +96,14 @@ public class DashboardFragmentTest {
|
||||
|
||||
@Test
|
||||
public void displayTilesAsPreference_shouldAddTilesWithIntent() {
|
||||
when(mFakeFeatureFactory.dashboardFeatureProvider.getTilesForCategory(anyString()))
|
||||
.thenReturn(mDashboardCategory);
|
||||
when(mFakeFeatureFactory.dashboardFeatureProvider.getDashboardKeyForTile(any(Tile.class)))
|
||||
.thenReturn("test_key");
|
||||
mTestFragment.onCreatePreferences(new Bundle(), "rootKey");
|
||||
|
||||
verify(mTestFragment.mScreen).addPreference(any(DashboardTilePreference.class));
|
||||
verify(mDisclosureMixin).addPreference(any(PreferenceScreen.class),
|
||||
any(DashboardTilePreference.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -109,6 +121,27 @@ public class DashboardFragmentTest {
|
||||
verify(mTestFragment.mScreen, never()).addPreference(any(DashboardTilePreference.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void bindPreference_shouldBindAllData() {
|
||||
final Preference preference = new Preference(
|
||||
ShadowApplication.getInstance().getApplicationContext());
|
||||
final Tile tile = new Tile();
|
||||
tile.title = "title";
|
||||
tile.summary = "summary";
|
||||
tile.icon = Icon.createWithBitmap(Bitmap.createBitmap(1, 1, Bitmap.Config.RGB_565));
|
||||
tile.metaData = new Bundle();
|
||||
tile.metaData.putString(SettingsActivity.META_DATA_KEY_FRAGMENT_CLASS, "HI");
|
||||
tile.priority = 10;
|
||||
mTestFragment.bindPreferenceToTile(mContext, preference, tile, "123");
|
||||
|
||||
assertThat(preference.getTitle()).isEqualTo(tile.title);
|
||||
assertThat(preference.getSummary()).isEqualTo(tile.summary);
|
||||
assertThat(preference.getIcon()).isNotNull();
|
||||
assertThat(preference.getFragment())
|
||||
.isEqualTo(tile.metaData.getString(SettingsActivity.META_DATA_KEY_FRAGMENT_CLASS));
|
||||
assertThat(preference.getOrder()).isEqualTo(-tile.priority);
|
||||
}
|
||||
|
||||
public static class TestPreferenceController extends PreferenceController {
|
||||
|
||||
public TestPreferenceController(Context context) {
|
||||
@@ -139,7 +172,6 @@ public class DashboardFragmentTest {
|
||||
public static class TestFragment extends DashboardFragment {
|
||||
|
||||
private final Context mContext;
|
||||
@Mock
|
||||
public PreferenceScreen mScreen;
|
||||
|
||||
public TestFragment(Context context) {
|
||||
|
@@ -35,6 +35,8 @@ import org.robolectric.RobolectricTestRunner;
|
||||
import org.robolectric.annotation.Config;
|
||||
import org.robolectric.shadows.ShadowApplication;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
import static org.mockito.Matchers.any;
|
||||
import static org.mockito.Matchers.anyInt;
|
||||
@@ -67,7 +69,8 @@ public class ProgressiveDisclosureTest {
|
||||
mScreen = mPreferenceFragment.getPreferenceScreen();
|
||||
mAppContext = ShadowApplication.getInstance().getApplicationContext();
|
||||
mFakeFeatureFactory = (FakeFeatureFactory) FeatureFactory.getFactory(mContext);
|
||||
mMixin = new ProgressiveDisclosureMixin(mAppContext, mPreferenceFragment);
|
||||
mMixin = new ProgressiveDisclosureMixin(mAppContext,
|
||||
mFakeFeatureFactory.dashboardFeatureProvider, mPreferenceFragment);
|
||||
mPreference = new Preference(mAppContext);
|
||||
mPreference.setKey("test");
|
||||
when(mFakeFeatureFactory.dashboardFeatureProvider.isEnabled()).thenReturn(true);
|
||||
@@ -180,4 +183,77 @@ public class ProgressiveDisclosureTest {
|
||||
verify(screen, times(3)).removePreference(any(Preference.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void addToCollapsedList_shouldAddInOrder() {
|
||||
final Preference pref1 = new Preference(mAppContext);
|
||||
final Preference pref2 = new Preference(mAppContext);
|
||||
pref1.setOrder(10);
|
||||
pref2.setOrder(20);
|
||||
|
||||
// Pref1 has lower order than pref2, but add pref2 first. The collapsed list should maintain
|
||||
// items in increasing order.
|
||||
mMixin.addToCollapsedList(pref2);
|
||||
mMixin.addToCollapsedList(pref1);
|
||||
|
||||
List<Preference> collapsedList = mMixin.getCollapsedPrefs();
|
||||
assertThat(collapsedList.get(0)).isSameAs(pref1);
|
||||
assertThat(collapsedList.get(1)).isSameAs(pref2);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void addPreferenceWhenCollapsed_noPrefOnScreen_shouldAddToList() {
|
||||
// Add something to collapsed list so we are in collapsed state.
|
||||
mMixin.addToCollapsedList(new Preference(mAppContext));
|
||||
assertThat(mMixin.getCollapsedPrefs().size()).isEqualTo(1);
|
||||
|
||||
// Just 1 preference on screen: the more button
|
||||
when(mScreen.getPreferenceCount()).thenReturn(1);
|
||||
final Preference toBeAdded = new Preference(mAppContext);
|
||||
toBeAdded.setOrder(100);
|
||||
mMixin.addPreference(mScreen, toBeAdded);
|
||||
|
||||
// Should have 2 prefs in collapsed list now
|
||||
assertThat(mMixin.getCollapsedPrefs().size()).isEqualTo(2);
|
||||
assertThat(mMixin.getCollapsedPrefs().get(0)).isSameAs(toBeAdded);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void addPreferenceWhenCollapsed_prefOrderLessThanLastOnScreen_shouldAddToScreen() {
|
||||
final Preference lastPref = new Preference(mAppContext);
|
||||
lastPref.setOrder(100);
|
||||
// Add something to collapsed list so we are in collapsed state.
|
||||
mMixin.addToCollapsedList(new Preference(mAppContext));
|
||||
assertThat(mMixin.getCollapsedPrefs().size()).isEqualTo(1);
|
||||
// 3 prefs on screen, 2 are real and the last one is more button.
|
||||
when(mScreen.getPreferenceCount()).thenReturn(3);
|
||||
when(mScreen.getPreference(1)).thenReturn(lastPref);
|
||||
|
||||
final Preference toBeAdded = new Preference(mAppContext);
|
||||
toBeAdded.setOrder(50);
|
||||
mMixin.addPreference(mScreen, toBeAdded);
|
||||
|
||||
verify(mScreen).removePreference(lastPref);
|
||||
verify(mScreen).addPreference(toBeAdded);
|
||||
assertThat(mMixin.getCollapsedPrefs().get(0)).isSameAs(lastPref);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void addPreferenceWhenCollapsed_prefOrderMoreThanLastOnScreen_shouldAddToList() {
|
||||
final Preference lastPref = new Preference(mAppContext);
|
||||
lastPref.setOrder(100);
|
||||
// Add something to collapsed list so we are in collapsed state.
|
||||
mMixin.addToCollapsedList(new Preference(mAppContext));
|
||||
assertThat(mMixin.getCollapsedPrefs().size()).isEqualTo(1);
|
||||
// 3 prefs on screen, 2 are real and the last one is more button.
|
||||
when(mScreen.getPreferenceCount()).thenReturn(3);
|
||||
when(mScreen.getPreference(1)).thenReturn(lastPref);
|
||||
|
||||
final Preference toBeAdded = new Preference(mAppContext);
|
||||
toBeAdded.setOrder(200);
|
||||
mMixin.addPreference(mScreen, toBeAdded);
|
||||
|
||||
verify(mScreen, never()).removePreference(any(Preference.class));
|
||||
verify(mScreen, never()).addPreference(any(Preference.class));
|
||||
assertThat(mMixin.getCollapsedPrefs().get(0)).isSameAs(toBeAdded);
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user