From e226c9a8bff7366cdbc4ccf638ceca954f423be0 Mon Sep 17 00:00:00 2001 From: Victor Chang Date: Thu, 1 Feb 2018 17:54:16 +0000 Subject: [PATCH 1/5] Use 24-hour settings for time formatting Test: m RunSettingsRoboTests Bug: 72311296 Change-Id: I7c1458dbc2e4e15765f703c35a0113341b912a2b --- .../datetime/timezone/TimeZoneAdapter.java | 7 +- .../timezone/TimeZoneAdapterTest.java | 68 ++++++++++++++++++- 2 files changed, 71 insertions(+), 4 deletions(-) diff --git a/src/com/android/settings/datetime/timezone/TimeZoneAdapter.java b/src/com/android/settings/datetime/timezone/TimeZoneAdapter.java index 79075ca78f5..62fc8c9baea 100644 --- a/src/com/android/settings/datetime/timezone/TimeZoneAdapter.java +++ b/src/com/android/settings/datetime/timezone/TimeZoneAdapter.java @@ -35,6 +35,7 @@ import com.android.settings.R; import java.util.Collections; import java.util.Date; import java.util.List; +import java.util.Locale; /** * Adapter for showing {@link TimeZoneInfo} objects in a recycler view. @@ -55,7 +56,11 @@ class TimeZoneAdapter extends RecyclerView.Adapter { TimeZoneAdapter(View.OnClickListener onClickListener, Context context) { mOnClickListener = onClickListener; mContext = context; - mTimeFormat = DateFormat.getTimeInstance(SimpleDateFormat.SHORT); + // Use android.text.format.DateFormat to observe 24-hour settings and find the best pattern + // using ICU with skeleton. + mTimeFormat = new SimpleDateFormat( + android.text.format.DateFormat.getTimeFormatString(context), + Locale.getDefault()); mDateFormat = DateFormat.getDateInstance(SimpleDateFormat.MEDIUM); mDateFormat.setContext(DisplayContext.CAPITALIZATION_NONE); mCurrentTimeZone = TimeZone.getDefault().getID(); diff --git a/tests/robotests/src/com/android/settings/datetime/timezone/TimeZoneAdapterTest.java b/tests/robotests/src/com/android/settings/datetime/timezone/TimeZoneAdapterTest.java index 5f29a0b65f1..1377f1df604 100644 --- a/tests/robotests/src/com/android/settings/datetime/timezone/TimeZoneAdapterTest.java +++ b/tests/robotests/src/com/android/settings/datetime/timezone/TimeZoneAdapterTest.java @@ -15,13 +15,18 @@ */ package com.android.settings.datetime.timezone; +import android.content.Context; import android.icu.util.TimeZone; +import android.provider.Settings; import android.text.TextUtils; import android.view.View; import android.widget.FrameLayout; + import com.android.settings.TestConfig; import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.testutils.shadow.SettingsShadowResources; + +import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; @@ -29,8 +34,11 @@ import org.mockito.Mock; import org.mockito.MockitoAnnotations; import org.robolectric.RuntimeEnvironment; import org.robolectric.annotation.Config; +import org.robolectric.annotation.Implementation; +import org.robolectric.annotation.Implements; import java.util.Collections; +import java.util.Locale; import static com.google.common.truth.Truth.assertThat; @@ -38,17 +46,39 @@ import static com.google.common.truth.Truth.assertThat; @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION, shadows = { SettingsShadowResources.class, - SettingsShadowResources.SettingsShadowTheme.class}) + SettingsShadowResources.SettingsShadowTheme.class, + TimeZoneAdapterTest.ShadowDataFormat.class}) public class TimeZoneAdapterTest { @Mock private View.OnClickListener mOnClickListener; private TimeZoneAdapter mTimeZoneAdapter; + private Context mContext; + private Locale mDefaultLocale; + @Before - public void setUp() { + public void setUp() throws Exception { MockitoAnnotations.initMocks(this); - mTimeZoneAdapter = new TimeZoneAdapter(mOnClickListener, RuntimeEnvironment.application); + mContext = RuntimeEnvironment.application; + mTimeZoneAdapter = new TimeZoneAdapter(mOnClickListener, mContext); + mDefaultLocale = Locale.getDefault(); + } + + @After + public void tearDown() throws Exception { + Locale.setDefault(mDefaultLocale); + } + + @Implements(android.text.format.DateFormat.class) + public static class ShadowDataFormat { + + public static String mTimeFormatString = ""; + + @Implementation + public static String getTimeFormatString(Context context) { + return mTimeFormatString; + } } @Test @@ -89,6 +119,38 @@ public class TimeZoneAdapterTest { assertThat(viewHolder.mDstView.getVisibility()).isEqualTo(View.GONE); } + @Test + public void bindViewHolder_on24Hour() { + Locale.setDefault(Locale.US); + ShadowDataFormat.mTimeFormatString = "HH:mm"; + mTimeZoneAdapter = new TimeZoneAdapter(mOnClickListener, mContext); + + final TimeZoneInfo tzi = dummyTimeZoneInfo(TimeZone.getTimeZone("Etc/UTC")); + mTimeZoneAdapter.setTimeZoneInfos(Collections.singletonList(tzi)); + + final FrameLayout parent = new FrameLayout(RuntimeEnvironment.application); + + final ViewHolder viewHolder = (ViewHolder) mTimeZoneAdapter.createViewHolder(parent, TimeZoneAdapter.VIEW_TYPE_NORMAL); + mTimeZoneAdapter.bindViewHolder(viewHolder, 0); + assertThat(viewHolder.mTimeView.getText().toString()).hasLength(5); + } + + @Test + public void bindViewHolder_on12Hour() { + Locale.setDefault(Locale.US); + ShadowDataFormat.mTimeFormatString = "hh:mm a"; + mTimeZoneAdapter = new TimeZoneAdapter(mOnClickListener, mContext); + + final TimeZoneInfo tzi = dummyTimeZoneInfo(TimeZone.getTimeZone("Etc/UTC")); + mTimeZoneAdapter.setTimeZoneInfos(Collections.singletonList(tzi)); + + final FrameLayout parent = new FrameLayout(RuntimeEnvironment.application); + + final ViewHolder viewHolder = (ViewHolder) mTimeZoneAdapter.createViewHolder(parent, TimeZoneAdapter.VIEW_TYPE_NORMAL); + mTimeZoneAdapter.bindViewHolder(viewHolder, 0); + assertThat(viewHolder.mTimeView.getText().toString()).hasLength(8); + } + // Pick an arbitrary time zone that's not the current default. private static TimeZone getNonDefaultTimeZone() { final String[] availableIDs = TimeZone.getAvailableIDs(); From 1987c8e5628de074c3e78d1d03087ee5a4d0424c Mon Sep 17 00:00:00 2001 From: Fan Zhang Date: Mon, 12 Feb 2018 12:52:17 -0800 Subject: [PATCH 2/5] Fix intent launch flag Change-Id: I0cb744fcccc6fb9f6d0d338f726f3dd29dccc718 Fixes: 73224739 Test: manual --- src/com/android/settings/accounts/AccountTypePreference.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/com/android/settings/accounts/AccountTypePreference.java b/src/com/android/settings/accounts/AccountTypePreference.java index 1d394730556..574cbd57056 100644 --- a/src/com/android/settings/accounts/AccountTypePreference.java +++ b/src/com/android/settings/accounts/AccountTypePreference.java @@ -103,7 +103,8 @@ public class AccountTypePreference extends AppPreference implements OnPreference } Utils.startWithFragment(getContext(), mFragment, mFragmentArguments, null /* resultTo */, 0 /* resultRequestCode */, mTitleResPackageName, - mTitleResId, null /* title */, mMetricsCategory); + mTitleResId, null /* title */,false /* isShortCut */, mMetricsCategory, + 0 /* flag */); return true; } return false; From 58eb43a2e4fe86665229318b96ab351b229c7000 Mon Sep 17 00:00:00 2001 From: Leslie Watkins Date: Fri, 9 Feb 2018 16:43:06 -0800 Subject: [PATCH 3/5] Remove all reference to SmsMirroring in Android Settings. Test: Robotests Change-Id: I3318c6915cae95522f09838f00a3c567fe9e5fc5 --- res/drawable/ic_sms_mirroring_24dp.xml | 25 ---------- res/values/strings.xml | 3 -- res/xml/connected_devices_advanced.xml | 7 --- res/xml/connected_devices_old.xml | 7 --- ...ancedConnectedDeviceDashboardFragment.java | 11 ----- .../ConnectedDeviceDashboardFragmentOld.java | 11 ----- .../SmsMirroringFeatureProvider.java | 28 ----------- .../SmsMirroringFeatureProviderImpl.java | 31 ------------- .../SmsMirroringPreferenceController.java | 45 ------------------ .../settings/overlay/FeatureFactory.java | 3 -- .../settings/overlay/FeatureFactoryImpl.java | 11 ----- ...dConnectedDeviceDashboardFragmentTest.java | 46 ------------------- ...ConnectedDeviceDashboardFragment2Test.java | 46 ------------------- .../testutils/FakeFeatureFactory.java | 8 ---- .../settings/core/UniquePreferenceTest.java | 1 - 15 files changed, 283 deletions(-) delete mode 100644 res/drawable/ic_sms_mirroring_24dp.xml delete mode 100644 src/com/android/settings/connecteddevice/SmsMirroringFeatureProvider.java delete mode 100644 src/com/android/settings/connecteddevice/SmsMirroringFeatureProviderImpl.java delete mode 100644 src/com/android/settings/connecteddevice/SmsMirroringPreferenceController.java diff --git a/res/drawable/ic_sms_mirroring_24dp.xml b/res/drawable/ic_sms_mirroring_24dp.xml deleted file mode 100644 index 5fe30030214..00000000000 --- a/res/drawable/ic_sms_mirroring_24dp.xml +++ /dev/null @@ -1,25 +0,0 @@ - - - - - diff --git a/res/values/strings.xml b/res/values/strings.xml index 72db2537492..b1278a68ec8 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -8129,9 +8129,6 @@ and powering other device [CHAR LIMIT=NONE] --> MIDI and supplying power - - SMS Mirroring - Background check diff --git a/res/xml/connected_devices_advanced.xml b/res/xml/connected_devices_advanced.xml index 83a63e40c22..4ad94c8d76e 100644 --- a/res/xml/connected_devices_advanced.xml +++ b/res/xml/connected_devices_advanced.xml @@ -42,13 +42,6 @@ android:icon="@drawable/ic_android" android:order="-4"/> - - - - keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).contains(mSmsMirroringPreferenceController.getPreferenceKey()); - } - - @Test - public void testSearchIndexProvider_SmsMirroring_KeyNotAdded() { - when(mFeatureProvider.shouldShowSmsMirroring(mContext)).thenReturn(true); - mSmsMirroringPreferenceController.mIsAvailable = true; - - final List keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).doesNotContain(mSmsMirroringPreferenceController.getPreferenceKey()); - } - @Test public void testGetCategoryKey_returnCategoryDevice() { assertThat(mFragment.getCategoryKey()).isEqualTo(CategoryKey.CATEGORY_DEVICE); diff --git a/tests/robotests/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment2Test.java b/tests/robotests/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment2Test.java index 1bc8a1bcc67..3eacd7a4f96 100644 --- a/tests/robotests/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment2Test.java +++ b/tests/robotests/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragment2Test.java @@ -60,37 +60,15 @@ public class ConnectedDeviceDashboardFragment2Test { private PackageManager mManager; private FakeFeatureFactory mFeatureFactory; - private SmsMirroringFeatureProvider mFeatureProvider; private ConnectedDeviceDashboardFragmentOld mFragment; - private TestSmsMirroringPreferenceController mSmsMirroringPreferenceController; - - private static final class TestSmsMirroringPreferenceController - extends SmsMirroringPreferenceController implements PreferenceControllerMixin { - - private boolean mIsAvailable; - - public TestSmsMirroringPreferenceController(Context context) { - super(context); - } - - @Override - public boolean isAvailable() { - return mIsAvailable; - } - } @Before public void setUp() { MockitoAnnotations.initMocks(this); mFeatureFactory = FakeFeatureFactory.setupForTest(); - mFeatureProvider = mFeatureFactory.smsMirroringFeatureProvider; mFragment = new ConnectedDeviceDashboardFragmentOld(); when(mContext.getPackageManager()).thenReturn(mManager); - - mSmsMirroringPreferenceController = new TestSmsMirroringPreferenceController(mContext); - when(mFeatureProvider.getController(mContext)).thenReturn( - mSmsMirroringPreferenceController); } @Test @@ -130,30 +108,6 @@ public class ConnectedDeviceDashboardFragment2Test { assertThat(keys).doesNotContain(NfcPreferenceController.KEY_ANDROID_BEAM_SETTINGS); } - @Test - public void testSearchIndexProvider_NoSmsMirroring_KeyAdded() { - when(mFeatureProvider.shouldShowSmsMirroring(mContext)).thenReturn(false); - mSmsMirroringPreferenceController.mIsAvailable = false; - - final List keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).contains(mSmsMirroringPreferenceController.getPreferenceKey()); - } - - @Test - public void testSearchIndexProvider_SmsMirroring_KeyNotAdded() { - when(mFeatureProvider.shouldShowSmsMirroring(mContext)).thenReturn(true); - mSmsMirroringPreferenceController.mIsAvailable = true; - - final List keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).doesNotContain(mSmsMirroringPreferenceController.getPreferenceKey()); - } - @Test public void testNonIndexableKeys_existInXmlLayout() { final Context context = RuntimeEnvironment.application; diff --git a/tests/robotests/src/com/android/settings/testutils/FakeFeatureFactory.java b/tests/robotests/src/com/android/settings/testutils/FakeFeatureFactory.java index 57244c15ec0..601164032d5 100644 --- a/tests/robotests/src/com/android/settings/testutils/FakeFeatureFactory.java +++ b/tests/robotests/src/com/android/settings/testutils/FakeFeatureFactory.java @@ -24,7 +24,6 @@ import android.content.Context; import com.android.settings.accounts.AccountFeatureProvider; import com.android.settings.applications.ApplicationFeatureProvider; import com.android.settings.bluetooth.BluetoothFeatureProvider; -import com.android.settings.connecteddevice.SmsMirroringFeatureProvider; import com.android.settings.dashboard.DashboardFeatureProvider; import com.android.settings.dashboard.suggestions.SuggestionFeatureProvider; import com.android.settings.enterprise.EnterprisePrivacyFeatureProvider; @@ -61,7 +60,6 @@ public class FakeFeatureFactory extends FeatureFactory { public final UserFeatureProvider userFeatureProvider; public final AssistGestureFeatureProvider assistGestureFeatureProvider; public final BluetoothFeatureProvider bluetoothFeatureProvider; - public final SmsMirroringFeatureProvider smsMirroringFeatureProvider; public final SlicesFeatureProvider slicesFeatureProvider; public SearchFeatureProvider searchFeatureProvider; public final AccountFeatureProvider mAccountFeatureProvider; @@ -101,7 +99,6 @@ public class FakeFeatureFactory extends FeatureFactory { userFeatureProvider = mock(UserFeatureProvider.class); assistGestureFeatureProvider = mock(AssistGestureFeatureProvider.class); bluetoothFeatureProvider = mock(BluetoothFeatureProvider.class); - smsMirroringFeatureProvider = mock(SmsMirroringFeatureProvider.class); slicesFeatureProvider = mock(SlicesFeatureProvider.class); mAccountFeatureProvider = mock(AccountFeatureProvider.class); } @@ -176,11 +173,6 @@ public class FakeFeatureFactory extends FeatureFactory { return assistGestureFeatureProvider; } - @Override - public SmsMirroringFeatureProvider getSmsMirroringFeatureProvider() { - return smsMirroringFeatureProvider; - } - @Override public SlicesFeatureProvider getSlicesFeatureProvider() { return slicesFeatureProvider; diff --git a/tests/unit/src/com/android/settings/core/UniquePreferenceTest.java b/tests/unit/src/com/android/settings/core/UniquePreferenceTest.java index 3daecce7aa7..aa1b55fc29e 100644 --- a/tests/unit/src/com/android/settings/core/UniquePreferenceTest.java +++ b/tests/unit/src/com/android/settings/core/UniquePreferenceTest.java @@ -74,7 +74,6 @@ public class UniquePreferenceTest { "toggle_bluetooth", "toggle_nfc", "android_beam_settings", - "sms_mirroring", // Dup keys from About Phone v2 experiment. "ims_reg_state", "bt_address", From 2edbaa7062aa1988fc1f8b60566c53eaa4f3f891 Mon Sep 17 00:00:00 2001 From: Fan Zhang Date: Fri, 9 Feb 2018 16:39:27 -0800 Subject: [PATCH 4/5] Change print setting from a dynamic tile to static pref ...because dynamic tile is a lot harder to index correctly. - Removed metadata that makes PrintSettings a dynamic tile. - Added PrintSettings into connected_device xml. - Added a new PreferenceController - all summary updating logic is copied from PrintSettingsFragment Change-Id: I41e7c9d23e97ecd5a043ac7c33f2d404260c92e7 Fixes: 73128944 Test: robotests --- AndroidManifest.xml | 5 - PREUPLOAD.cfg | 2 - res/xml/connected_devices_advanced.xml | 8 + res/xml/print_settings.xml | 2 +- .../android/settings/SettingsActivity.java | 5 - ...ancedConnectedDeviceDashboardFragment.java | 30 +++- .../ConnectedDeviceDashboardFragmentOld.java | 4 +- .../usb/UsbModePreferenceController.java | 7 +- .../core/BasePreferenceController.java | 3 + .../PrintSettingPreferenceController.java | 135 ++++++++++++++++ .../settings/print/PrintSettingsFragment.java | 150 ++---------------- .../settings/wrapper/PrintManagerWrapper.java | 54 +++++++ ...dConnectedDeviceDashboardFragmentTest.java | 30 +--- .../usb/UsbModePreferenceControllerTest.java | 17 +- .../core/BasePreferenceControllerTest.java | 7 +- .../print/PrintSettingsFragmentTest.java | 102 ------------ ...PrintSettingsPreferenceControllerTest.java | 125 +++++++++++++++ 17 files changed, 379 insertions(+), 307 deletions(-) create mode 100644 src/com/android/settings/print/PrintSettingPreferenceController.java create mode 100644 src/com/android/settings/wrapper/PrintManagerWrapper.java delete mode 100644 tests/robotests/src/com/android/settings/print/PrintSettingsFragmentTest.java create mode 100644 tests/robotests/src/com/android/settings/print/PrintSettingsPreferenceControllerTest.java diff --git a/AndroidManifest.xml b/AndroidManifest.xml index f5c368f1ff6..dec12ba4e5c 100644 --- a/AndroidManifest.xml +++ b/AndroidManifest.xml @@ -1984,11 +1984,6 @@ - - - - diff --git a/PREUPLOAD.cfg b/PREUPLOAD.cfg index 62a2e434793..8af69c74b1c 100644 --- a/PREUPLOAD.cfg +++ b/PREUPLOAD.cfg @@ -1,5 +1,3 @@ [Hook Scripts] -checkstyle_hook = ${REPO_ROOT}/prebuilts/checkstyle/checkstyle.py --sha ${PREUPLOAD_COMMIT} - -fw src/com/android/settings/print/ checkcolor_hook = ${REPO_ROOT}/prebuilts/checkcolor/checkcolor.py -p . diff --git a/res/xml/connected_devices_advanced.xml b/res/xml/connected_devices_advanced.xml index 4ad94c8d76e..a5d48fd00b4 100644 --- a/res/xml/connected_devices_advanced.xml +++ b/res/xml/connected_devices_advanced.xml @@ -50,6 +50,14 @@ settings:controller="com.android.settings.connecteddevice.BluetoothOnWhileDrivingPreferenceController" android:order="-2"/> + + getPreferenceControllers(Context context) { + return buildControllers(context, getLifecycle()); + } + + private static List buildControllers(Context context, + Lifecycle lifecycle) { final List controllers = new ArrayList<>(); - final Lifecycle lifecycle = getLifecycle(); final NfcPreferenceController nfcPreferenceController = new NfcPreferenceController(context); - lifecycle.addObserver(nfcPreferenceController); controllers.add(nfcPreferenceController); - mUsbPrefController = new UsbModePreferenceController(context, new UsbBackend(context)); - lifecycle.addObserver(mUsbPrefController); - controllers.add(mUsbPrefController); + controllers.add(new UsbModePreferenceController( + context, new UsbBackend(context), lifecycle)); final BluetoothSwitchPreferenceController bluetoothPreferenceController = new BluetoothSwitchPreferenceController(context); - lifecycle.addObserver(bluetoothPreferenceController); controllers.add(bluetoothPreferenceController); controllers.add(new BluetoothFilesPreferenceController(context)); controllers.add(new BluetoothOnWhileDrivingPreferenceController(context)); + final PrintSettingPreferenceController printerController = + new PrintSettingPreferenceController(context); + if (lifecycle != null) { + lifecycle.addObserver(printerController); + lifecycle.addObserver(nfcPreferenceController); + lifecycle.addObserver(bluetoothPreferenceController); + } + controllers.add(printerController); + return controllers; } @@ -111,5 +121,11 @@ public class AdvancedConnectedDeviceDashboardFragment extends DashboardFragment return keys; } + + @Override + public List getPreferenceControllers( + Context context) { + return buildControllers(context, null /* lifecycle */); + } }; } diff --git a/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragmentOld.java b/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragmentOld.java index b732e1e7975..54ae8f6dc89 100644 --- a/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragmentOld.java +++ b/src/com/android/settings/connecteddevice/ConnectedDeviceDashboardFragmentOld.java @@ -80,8 +80,8 @@ public class ConnectedDeviceDashboardFragmentOld extends DashboardFragment { new NfcPreferenceController(context); lifecycle.addObserver(nfcPreferenceController); controllers.add(nfcPreferenceController); - mUsbPrefController = new UsbModePreferenceController(context, new UsbBackend(context)); - lifecycle.addObserver(mUsbPrefController); + mUsbPrefController = new UsbModePreferenceController(context, new UsbBackend(context), + lifecycle); controllers.add(mUsbPrefController); final BluetoothMasterSwitchPreferenceController bluetoothPreferenceController = new BluetoothMasterSwitchPreferenceController( diff --git a/src/com/android/settings/connecteddevice/usb/UsbModePreferenceController.java b/src/com/android/settings/connecteddevice/usb/UsbModePreferenceController.java index e342460fef6..d7624f00823 100644 --- a/src/com/android/settings/connecteddevice/usb/UsbModePreferenceController.java +++ b/src/com/android/settings/connecteddevice/usb/UsbModePreferenceController.java @@ -23,6 +23,7 @@ import com.android.internal.annotations.VisibleForTesting; import com.android.settings.R; import com.android.settings.core.PreferenceControllerMixin; import com.android.settingslib.core.AbstractPreferenceController; +import com.android.settingslib.core.lifecycle.Lifecycle; import com.android.settingslib.core.lifecycle.LifecycleObserver; import com.android.settingslib.core.lifecycle.events.OnPause; import com.android.settingslib.core.lifecycle.events.OnResume; @@ -37,12 +38,16 @@ public class UsbModePreferenceController extends AbstractPreferenceController UsbConnectionBroadcastReceiver mUsbReceiver; private Preference mUsbPreference; - public UsbModePreferenceController(Context context, UsbBackend usbBackend) { + public UsbModePreferenceController(Context context, UsbBackend usbBackend, + Lifecycle lifecycle) { super(context); mUsbBackend = usbBackend; mUsbReceiver = new UsbConnectionBroadcastReceiver(mContext, (connected, newMode) -> { updateSummary(mUsbPreference, connected, newMode); }, mUsbBackend); + if (lifecycle != null) { + lifecycle.addObserver(this); + } } @Override diff --git a/src/com/android/settings/core/BasePreferenceController.java b/src/com/android/settings/core/BasePreferenceController.java index 4bd7ba48991..777f3dd3ea3 100644 --- a/src/com/android/settings/core/BasePreferenceController.java +++ b/src/com/android/settings/core/BasePreferenceController.java @@ -21,6 +21,7 @@ import android.util.Log; import com.android.settings.search.ResultPayload; import com.android.settings.search.SearchIndexableRaw; import com.android.settingslib.core.AbstractPreferenceController; +import com.android.settingslib.core.lifecycle.Lifecycle; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; @@ -70,6 +71,8 @@ public abstract class BasePreferenceController extends AbstractPreferenceControl protected final String mPreferenceKey; + protected Lifecycle mLifecycle; + public BasePreferenceController(Context context, String preferenceKey) { super(context); mPreferenceKey = preferenceKey; diff --git a/src/com/android/settings/print/PrintSettingPreferenceController.java b/src/com/android/settings/print/PrintSettingPreferenceController.java new file mode 100644 index 00000000000..bb8a81efa7d --- /dev/null +++ b/src/com/android/settings/print/PrintSettingPreferenceController.java @@ -0,0 +1,135 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.print; + +import android.content.Context; +import android.content.pm.PackageManager; +import android.print.PrintJob; +import android.print.PrintJobId; +import android.print.PrintJobInfo; +import android.print.PrintManager; +import android.printservice.PrintServiceInfo; +import android.support.v7.preference.Preference; +import android.support.v7.preference.PreferenceScreen; + +import com.android.settings.R; +import com.android.settings.core.BasePreferenceController; +import com.android.settings.wrapper.PrintManagerWrapper; +import com.android.settingslib.core.lifecycle.LifecycleObserver; +import com.android.settingslib.core.lifecycle.events.OnStart; +import com.android.settingslib.core.lifecycle.events.OnStop; + +import java.util.List; + +/** + * {@link BasePreferenceController} for Print settings. + */ +public class PrintSettingPreferenceController extends BasePreferenceController implements + LifecycleObserver, OnStart, OnStop, PrintManager.PrintJobStateChangeListener { + + private final PackageManager mPackageManager; + private PrintManagerWrapper mPrintManager; + private Preference mPreference; + + public PrintSettingPreferenceController(Context context) { + super(context, "connected_device_printing" /* preferenceKey */); + mPackageManager = context.getPackageManager(); + mPrintManager = new PrintManagerWrapper(context); + } + + @Override + public int getAvailabilityStatus() { + return mPackageManager.hasSystemFeature(PackageManager.FEATURE_PRINTING) + ? AVAILABLE : DISABLED_UNSUPPORTED; + } + + @Override + public void displayPreference(PreferenceScreen screen) { + super.displayPreference(screen); + mPreference = screen.findPreference(getPreferenceKey()); + } + + @Override + public void onStart() { + mPrintManager.addPrintJobStateChanegListener(this); + } + + @Override + public void onStop() { + mPrintManager.removePrintJobStateChangeListener(this); + } + + @Override + public void onPrintJobStateChanged(PrintJobId printJobId) { + updateState(mPreference); + } + + @Override + public void updateState(Preference preference) { + if (preference == null) { + return; + } + preference.setSummary(getSummary()); + } + + @Override + public String getSummary() { + final List printJobs = mPrintManager.getPrintJobs(); + + int numActivePrintJobs = 0; + if (printJobs != null) { + for (PrintJob job : printJobs) { + if (shouldShowToUser(job.getInfo())) { + numActivePrintJobs++; + } + } + } + + if (numActivePrintJobs > 0) { + return mContext.getResources().getQuantityString( + R.plurals.print_jobs_summary, numActivePrintJobs, numActivePrintJobs); + } else { + final List services = + mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES); + if (services == null || services.isEmpty()) { + return mContext.getString(R.string.print_settings_summary_no_service); + } else { + final int count = services.size(); + return mContext.getResources().getQuantityString( + R.plurals.print_settings_summary, count, count); + } + } + } + + /** + * Should the print job the shown to the user in the settings app. + * + * @param printJob The print job in question. + * @return true iff the print job should be shown. + */ + static boolean shouldShowToUser(PrintJobInfo printJob) { + switch (printJob.getState()) { + case PrintJobInfo.STATE_QUEUED: + case PrintJobInfo.STATE_STARTED: + case PrintJobInfo.STATE_BLOCKED: + case PrintJobInfo.STATE_FAILED: { + return true; + } + } + return false; + } +} diff --git a/src/com/android/settings/print/PrintSettingsFragment.java b/src/com/android/settings/print/PrintSettingsFragment.java index 56bebcce94a..21ee360e98b 100644 --- a/src/com/android/settings/print/PrintSettingsFragment.java +++ b/src/com/android/settings/print/PrintSettingsFragment.java @@ -16,6 +16,8 @@ package com.android.settings.print; +import static com.android.settings.print.PrintSettingPreferenceController.shouldShowToUser; + import android.app.LoaderManager.LoaderCallbacks; import android.content.ActivityNotFoundException; import android.content.AsyncTaskLoader; @@ -37,7 +39,6 @@ import android.print.PrintServicesLoader; import android.printservice.PrintServiceInfo; import android.provider.SearchIndexableResource; import android.provider.Settings; -import android.support.annotation.VisibleForTesting; import android.support.v7.preference.Preference; import android.support.v7.preference.PreferenceCategory; import android.text.TextUtils; @@ -52,7 +53,6 @@ import android.widget.TextView; import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.settings.R; -import com.android.settings.dashboard.SummaryLoader; import com.android.settings.search.BaseSearchIndexProvider; import com.android.settings.search.Indexable; import com.android.settings.utils.ProfileSettingsPreferenceFragment; @@ -130,11 +130,6 @@ public class PrintSettingsFragment extends ProfileSettingsPreferenceFragment startSubSettingsIfNeeded(); } - @Override - public void onStop() { - super.onStop(); - } - @Override public void onViewCreated(View view, Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); @@ -359,7 +354,7 @@ public class PrintSettingsFragment extends ProfileSettingsPreferenceFragment printJob.getCreationTime(), printJob.getCreationTime(), DateFormat.SHORT, DateFormat.SHORT))); - TypedArray a = getActivity().obtainStyledAttributes(new int[]{ + TypedArray a = getActivity().obtainStyledAttributes(new int[] { android.R.attr.colorControlNormal}); int tintColor = a.getColor(0, 0); a.recycle(); @@ -494,136 +489,17 @@ public class PrintSettingsFragment extends ProfileSettingsPreferenceFragment } } - /** - * Should the print job the shown to the user in the settings app. - * - * @param printJob The print job in question. - * @return true iff the print job should be shown. - */ - private static boolean shouldShowToUser(PrintJobInfo printJob) { - switch (printJob.getState()) { - case PrintJobInfo.STATE_QUEUED: - case PrintJobInfo.STATE_STARTED: - case PrintJobInfo.STATE_BLOCKED: - case PrintJobInfo.STATE_FAILED: { - return true; - } - } - return false; - } - - /** - * Provider for the print settings summary - */ - @VisibleForTesting - static class PrintSummaryProvider - implements SummaryLoader.SummaryProvider, PrintJobStateChangeListener { - private final Context mContext; - private final PrintManagerWrapper mPrintManager; - private final SummaryLoader mSummaryLoader; - - /** - * Create a new {@link PrintSummaryProvider}. - * - * @param context The context this provider is for - * @param summaryLoader The summary load using this provider - */ - PrintSummaryProvider(Context context, SummaryLoader summaryLoader, - PrintManagerWrapper printManager) { - mContext = context; - mSummaryLoader = summaryLoader; - mPrintManager = printManager; - } - - @Override - public void setListening(boolean isListening) { - if (mPrintManager != null) { - if (isListening) { - mPrintManager.addPrintJobStateChanegListner(this); - onPrintJobStateChanged(null); - } else { - mPrintManager.removePrintJobStateChangeListener(this); - } - } - } - - @Override - public void onPrintJobStateChanged(PrintJobId printJobId) { - final List printJobs = mPrintManager.getPrintJobs(); - - int numActivePrintJobs = 0; - if (printJobs != null) { - for (PrintJob job : printJobs) { - if (shouldShowToUser(job.getInfo())) { - numActivePrintJobs++; - } - } - } - - if (numActivePrintJobs > 0) { - mSummaryLoader.setSummary(this, mContext.getResources().getQuantityString( - R.plurals.print_jobs_summary, numActivePrintJobs, numActivePrintJobs)); - } else { - List services = - mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES); - if (services == null || services.isEmpty()) { - mSummaryLoader.setSummary(this, - mContext.getString(R.string.print_settings_summary_no_service)); - } else { - final int count = services.size(); - mSummaryLoader.setSummary(this, - mContext.getResources().getQuantityString( - R.plurals.print_settings_summary, count, count)); - } - } - } - - static class PrintManagerWrapper { - - private final PrintManager mPrintManager; - - PrintManagerWrapper(Context context) { - mPrintManager = ((PrintManager) context.getSystemService(Context.PRINT_SERVICE)) - .getGlobalPrintManagerForUser(context.getUserId()); - } - - public List getPrintServices(int selectionFlags) { - return mPrintManager.getPrintServices(selectionFlags); - } - - public void addPrintJobStateChanegListner(PrintJobStateChangeListener listener) { - mPrintManager.addPrintJobStateChangeListener(listener); - } - - public void removePrintJobStateChangeListener(PrintJobStateChangeListener listener) { - mPrintManager.removePrintJobStateChangeListener(listener); - } - - public List getPrintJobs() { - return mPrintManager.getPrintJobs(); - } - } - } - - /** - * A factory for {@link PrintSummaryProvider providers} the settings app can use to read the - * print summary. - */ - public static final SummaryLoader.SummaryProviderFactory SUMMARY_PROVIDER_FACTORY = - (activity, summaryLoader) -> new PrintSummaryProvider(activity, summaryLoader, - new PrintSummaryProvider.PrintManagerWrapper(activity)); - public static final SearchIndexProvider SEARCH_INDEX_DATA_PROVIDER = new BaseSearchIndexProvider() { - @Override - public List getXmlResourcesToIndex(Context context, - boolean enabled) { - List indexables = new ArrayList<>(); - SearchIndexableResource indexable = new SearchIndexableResource(context); - indexable.xmlResId = R.xml.print_settings; - indexables.add(indexable); - return indexables; - } - }; + @Override + public List getXmlResourcesToIndex(Context context, + boolean enabled) { + List indexables = new ArrayList<>(); + SearchIndexableResource indexable = new SearchIndexableResource(context); + indexable.xmlResId = R.xml.print_settings; + indexables.add(indexable); + return indexables; + } + }; } diff --git a/src/com/android/settings/wrapper/PrintManagerWrapper.java b/src/com/android/settings/wrapper/PrintManagerWrapper.java new file mode 100644 index 00000000000..d05eaedcae0 --- /dev/null +++ b/src/com/android/settings/wrapper/PrintManagerWrapper.java @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.wrapper; + +import android.content.Context; +import android.print.PrintJob; +import android.print.PrintManager; +import android.printservice.PrintServiceInfo; + +import java.util.List; + +/** + * Wrapper class for {@link PrintManager}. This is necessary to increase testability in Robolectric. + */ +public class PrintManagerWrapper { + + private final PrintManager mPrintManager; + + public PrintManagerWrapper(Context context) { + mPrintManager = ((PrintManager) context.getSystemService(Context.PRINT_SERVICE)) + .getGlobalPrintManagerForUser(context.getUserId()); + } + + public List getPrintServices(int selectionFlags) { + return mPrintManager.getPrintServices(selectionFlags); + } + + public void addPrintJobStateChanegListener(PrintManager.PrintJobStateChangeListener listener) { + mPrintManager.addPrintJobStateChangeListener(listener); + } + + public void removePrintJobStateChangeListener( + PrintManager.PrintJobStateChangeListener listener) { + mPrintManager.removePrintJobStateChangeListener(listener); + } + + public List getPrintJobs() { + return mPrintManager.getPrintJobs(); + } +} diff --git a/tests/robotests/src/com/android/settings/connecteddevice/AdvancedConnectedDeviceDashboardFragmentTest.java b/tests/robotests/src/com/android/settings/connecteddevice/AdvancedConnectedDeviceDashboardFragmentTest.java index 24cb9b3c5c0..9f1409cda2e 100644 --- a/tests/robotests/src/com/android/settings/connecteddevice/AdvancedConnectedDeviceDashboardFragmentTest.java +++ b/tests/robotests/src/com/android/settings/connecteddevice/AdvancedConnectedDeviceDashboardFragmentTest.java @@ -16,7 +16,6 @@ package com.android.settings.connecteddevice; import static com.google.common.truth.Truth.assertThat; - import static org.mockito.Mockito.when; import android.content.Context; @@ -24,9 +23,6 @@ import android.content.pm.PackageManager; import android.provider.SearchIndexableResource; import com.android.settings.TestConfig; -import com.android.settings.core.PreferenceControllerMixin; -import com.android.settings.nfc.NfcPreferenceController; -import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.testutils.XmlTestUtils; import com.android.settingslib.drawer.CategoryKey; @@ -52,16 +48,14 @@ public class AdvancedConnectedDeviceDashboardFragmentTest { @Mock private PackageManager mManager; - private FakeFeatureFactory mFeatureFactory; private AdvancedConnectedDeviceDashboardFragment mFragment; @Before public void setUp() { MockitoAnnotations.initMocks(this); - mFeatureFactory = FakeFeatureFactory.setupForTest(); mFragment = new AdvancedConnectedDeviceDashboardFragment(); - when(mContext.getPackageManager()).thenReturn(mManager); + when(mContext.getApplicationContext().getPackageManager()).thenReturn(mManager); } @Test @@ -79,28 +73,6 @@ public class AdvancedConnectedDeviceDashboardFragmentTest { assertThat(indexRes.get(0).xmlResId).isEqualTo(mFragment.getPreferenceScreenResId()); } - @Test - public void testSearchIndexProvider_NoNfc_KeyAdded() { - when(mManager.hasSystemFeature(PackageManager.FEATURE_NFC)).thenReturn(false); - final List keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).contains(NfcPreferenceController.KEY_TOGGLE_NFC); - assertThat(keys).contains(NfcPreferenceController.KEY_ANDROID_BEAM_SETTINGS); - } - - @Test - public void testSearchIndexProvider_NFC_KeyNotAdded() { - when(mManager.hasSystemFeature(PackageManager.FEATURE_NFC)).thenReturn(true); - final List keys = mFragment.SEARCH_INDEX_DATA_PROVIDER.getNonIndexableKeys( - mContext); - - assertThat(keys).isNotNull(); - assertThat(keys).doesNotContain(NfcPreferenceController.KEY_TOGGLE_NFC); - assertThat(keys).doesNotContain(NfcPreferenceController.KEY_ANDROID_BEAM_SETTINGS); - } - @Test public void testGetCategoryKey_returnCategoryDevice() { assertThat(mFragment.getCategoryKey()).isEqualTo(CategoryKey.CATEGORY_DEVICE); diff --git a/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbModePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbModePreferenceControllerTest.java index d15a57f5560..a1c599ffdf7 100644 --- a/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbModePreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbModePreferenceControllerTest.java @@ -1,12 +1,15 @@ package com.android.settings.connecteddevice.usb; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Answers.RETURNS_DEEP_STUBS; +import static org.mockito.Mockito.when; + import android.content.Context; import android.support.v7.preference.Preference; -import android.support.v7.preference.PreferenceScreen; import com.android.settings.R; -import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.TestConfig; +import com.android.settings.testutils.SettingsRobolectricTestRunner; import org.junit.Before; import org.junit.Test; @@ -16,20 +19,12 @@ import org.mockito.MockitoAnnotations; import org.robolectric.annotation.Config; import org.robolectric.shadows.ShadowApplication; -import static com.google.common.truth.Truth.assertThat; -import static org.mockito.Answers.RETURNS_DEEP_STUBS; -import static org.mockito.Matchers.any; -import static org.mockito.Mockito.when; -import static org.mockito.Mockito.verify; - @RunWith(SettingsRobolectricTestRunner.class) @Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) public class UsbModePreferenceControllerTest { @Mock(answer = RETURNS_DEEP_STUBS) private UsbBackend mUsbBackend; - @Mock(answer = RETURNS_DEEP_STUBS) - private PreferenceScreen mScreen; @Mock private UsbConnectionBroadcastReceiver mUsbConnectionBroadcastReceiver; @@ -40,7 +35,7 @@ public class UsbModePreferenceControllerTest { public void setUp() { MockitoAnnotations.initMocks(this); mContext = ShadowApplication.getInstance().getApplicationContext(); - mController = new UsbModePreferenceController(mContext, mUsbBackend); + mController = new UsbModePreferenceController(mContext, mUsbBackend, null /* lifecycle */); mController.mUsbReceiver = mUsbConnectionBroadcastReceiver; } diff --git a/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java index da2197c93b5..c0ac961e07e 100644 --- a/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java @@ -16,14 +16,11 @@ package com.android.settings.core; import static com.android.settings.core.BasePreferenceController.AVAILABLE; -import static com.android.settings.core.BasePreferenceController - .DISABLED_DEPENDENT_SETTING; +import static com.android.settings.core.BasePreferenceController.DISABLED_DEPENDENT_SETTING; import static com.android.settings.core.BasePreferenceController.DISABLED_FOR_USER; import static com.android.settings.core.BasePreferenceController.DISABLED_UNSUPPORTED; import static com.android.settings.core.BasePreferenceController.UNAVAILABLE_UNKNOWN; - import static com.google.common.truth.Truth.assertThat; - import static org.mockito.Mockito.when; import com.android.settings.TestConfig; @@ -41,7 +38,7 @@ import org.robolectric.annotation.Config; public class BasePreferenceControllerTest { @Mock - BasePreferenceController mPreferenceController; + private BasePreferenceController mPreferenceController; @Before public void setUp() { diff --git a/tests/robotests/src/com/android/settings/print/PrintSettingsFragmentTest.java b/tests/robotests/src/com/android/settings/print/PrintSettingsFragmentTest.java deleted file mode 100644 index cf34f452d14..00000000000 --- a/tests/robotests/src/com/android/settings/print/PrintSettingsFragmentTest.java +++ /dev/null @@ -1,102 +0,0 @@ -/* - * Copyright (C) 2017 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.print; - -import static org.mockito.Mockito.mock; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.when; - -import android.app.Activity; -import android.content.res.Resources; -import android.print.PrintJob; -import android.print.PrintJobInfo; -import android.print.PrintManager; -import android.printservice.PrintServiceInfo; - -import com.android.settings.R; -import com.android.settings.TestConfig; -import com.android.settings.dashboard.SummaryLoader; -import com.android.settings.testutils.SettingsRobolectricTestRunner; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.Mockito; -import org.mockito.MockitoAnnotations; -import org.robolectric.annotation.Config; - -import java.util.ArrayList; -import java.util.List; - - -@RunWith(SettingsRobolectricTestRunner.class) -@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) -public class PrintSettingsFragmentTest { - - @Mock - private PrintSettingsFragment.PrintSummaryProvider.PrintManagerWrapper mPrintManager; - @Mock - private Activity mActivity; - @Mock - private Resources mRes; - @Mock - private SummaryLoader mSummaryLoader; - private SummaryLoader.SummaryProvider mSummaryProvider; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - when(mActivity.getResources()).thenReturn(mRes); - mSummaryProvider = new PrintSettingsFragment.PrintSummaryProvider(mActivity, mSummaryLoader, - mPrintManager); - } - - @Test - public void testSummary_hasActiveJob_shouldSetSummaryToNumberOfJobs() { - final List printJobs = new ArrayList<>(); - final PrintJob job = mock(PrintJob.class, Mockito.RETURNS_DEEP_STUBS); - printJobs.add(job); - when(job.getInfo().getState()).thenReturn(PrintJobInfo.STATE_STARTED); - when(mPrintManager.getPrintJobs()).thenReturn(printJobs); - - mSummaryProvider.setListening(true); - - verify(mRes).getQuantityString(R.plurals.print_jobs_summary, 1, 1); - } - - @Test - public void testSummary_shouldSetSummaryToNumberOfPrintServices() { - final List printServices = mock(List.class); - when(printServices.isEmpty()).thenReturn(false); - when(printServices.size()).thenReturn(2); - // 2 services - when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES)) - .thenReturn(printServices); - - mSummaryProvider.setListening(true); - - verify(mRes).getQuantityString(R.plurals.print_settings_summary, 2, 2); - - // No service - when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES)).thenReturn(null); - - mSummaryProvider.setListening(true); - - verify(mActivity).getString(R.string.print_settings_summary_no_service); - } -} diff --git a/tests/robotests/src/com/android/settings/print/PrintSettingsPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/print/PrintSettingsPreferenceControllerTest.java new file mode 100644 index 00000000000..de1625b3bad --- /dev/null +++ b/tests/robotests/src/com/android/settings/print/PrintSettingsPreferenceControllerTest.java @@ -0,0 +1,125 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.print; + +import static android.arch.lifecycle.Lifecycle.Event.ON_START; +import static android.arch.lifecycle.Lifecycle.Event.ON_STOP; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; + +import android.arch.lifecycle.LifecycleOwner; +import android.content.Context; +import android.print.PrintJob; +import android.print.PrintJobInfo; +import android.print.PrintManager; +import android.printservice.PrintServiceInfo; +import android.support.v7.preference.Preference; + +import com.android.settings.R; +import com.android.settings.TestConfig; +import com.android.settings.testutils.SettingsRobolectricTestRunner; +import com.android.settings.wrapper.PrintManagerWrapper; +import com.android.settingslib.core.lifecycle.Lifecycle; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.Mock; +import org.mockito.Mockito; +import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; +import org.robolectric.annotation.Config; +import org.robolectric.util.ReflectionHelpers; + +import java.util.ArrayList; +import java.util.List; + + +@RunWith(SettingsRobolectricTestRunner.class) +@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) +public class PrintSettingsPreferenceControllerTest { + + @Mock + private PrintManagerWrapper mPrintManager; + private Context mContext; + private Preference mPreference; + private PrintSettingPreferenceController mController; + private LifecycleOwner mLifecycleOwner; + private Lifecycle mLifecycle; + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + mContext = RuntimeEnvironment.application; + mPreference = new Preference(mContext); + mController = new PrintSettingPreferenceController(mContext); + mLifecycleOwner = () -> mLifecycle; + mLifecycle = new Lifecycle(mLifecycleOwner); + ReflectionHelpers.setField(mController, "mPrintManager", mPrintManager); + mLifecycle.addObserver(mController); + } + + @Test + public void onStartStop_shouldRegisterPrintStateListener() { + mLifecycle.handleLifecycleEvent(ON_START); + mLifecycle.handleLifecycleEvent(ON_STOP); + + verify(mPrintManager).addPrintJobStateChanegListener(mController); + verify(mPrintManager).removePrintJobStateChangeListener(mController); + } + + @Test + public void updateState_hasActiveJob_shouldSetSummaryToNumberOfJobs() { + final List printJobs = new ArrayList<>(); + final PrintJob job = mock(PrintJob.class, Mockito.RETURNS_DEEP_STUBS); + printJobs.add(job); + when(job.getInfo().getState()).thenReturn(PrintJobInfo.STATE_STARTED); + when(mPrintManager.getPrintJobs()).thenReturn(printJobs); + + mController.updateState(mPreference); + + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getResources() + .getQuantityString(R.plurals.print_jobs_summary, 1, 1)); + } + + @Test + public void updateState_shouldSetSummaryToNumberOfPrintServices() { + final List printServices = mock(List.class); + when(printServices.isEmpty()).thenReturn(false); + when(printServices.size()).thenReturn(2); + // 2 services + when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES)) + .thenReturn(printServices); + + mController.updateState(mPreference); + + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getResources() + .getQuantityString(R.plurals.print_settings_summary, 2, 2)); + + // No service + when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES)).thenReturn(null); + + mController.updateState(mPreference); + + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getString(R.string.print_settings_summary_no_service)); + } +} From 8e490b40390f3d5361d32a5884ec841f7c3b2da4 Mon Sep 17 00:00:00 2001 From: Lucas Dupin Date: Sat, 10 Feb 2018 18:18:19 -0800 Subject: [PATCH 5/5] Disable "double tap to check" when "always on" "Double tap to check" has no effect when AOD is enabled. Double tapping will take you to the lock screen anyway. Test: manual Test: make RunSettingsRoboTests ROBOTEST_FILTER=DoubleTapScreenPreferenceControllerTest Change-Id: Ia97b7ecb00a9d83b867959d83642d476841e2f13 Fixes: 73096311 --- .../settings/display/AmbientDisplaySettings.java | 2 +- .../DoubleTapScreenPreferenceController.java | 5 +++++ .../DoubleTapScreenPreferenceControllerTest.java | 12 ++++++++++++ 3 files changed, 18 insertions(+), 1 deletion(-) diff --git a/src/com/android/settings/display/AmbientDisplaySettings.java b/src/com/android/settings/display/AmbientDisplaySettings.java index 187325c0c7f..3cac078e5a3 100644 --- a/src/com/android/settings/display/AmbientDisplaySettings.java +++ b/src/com/android/settings/display/AmbientDisplaySettings.java @@ -79,7 +79,7 @@ public class AmbientDisplaySettings extends DashboardFragment { protected List getPreferenceControllers(Context context) { return buildPreferenceControllers(context, getLifecycle(), new AmbientDisplayConfiguration(context), mMetricsFeatureProvider, - () -> { updatePreferenceStates(); }); + this::updatePreferenceStates); } @Override diff --git a/src/com/android/settings/gestures/DoubleTapScreenPreferenceController.java b/src/com/android/settings/gestures/DoubleTapScreenPreferenceController.java index 5412f368ad5..aa08e6f21d7 100644 --- a/src/com/android/settings/gestures/DoubleTapScreenPreferenceController.java +++ b/src/com/android/settings/gestures/DoubleTapScreenPreferenceController.java @@ -102,4 +102,9 @@ public class DoubleTapScreenPreferenceController extends GesturePreferenceContro return new InlineSwitchPayload(SECURE_KEY, ResultPayload.SettingsSource.SECURE, ON /* onValue */, intent, isAvailable(), ON /* defaultValue */); } + + @Override + protected boolean canHandleClicks() { + return !mAmbientConfig.alwaysOnEnabled(mUserId); + } } \ No newline at end of file diff --git a/tests/robotests/src/com/android/settings/gestures/DoubleTapScreenPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/gestures/DoubleTapScreenPreferenceControllerTest.java index 8f06c40481a..74e1e5defd4 100644 --- a/tests/robotests/src/com/android/settings/gestures/DoubleTapScreenPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/gestures/DoubleTapScreenPreferenceControllerTest.java @@ -161,4 +161,16 @@ public class DoubleTapScreenPreferenceControllerTest { assertThat(DoubleTapScreenPreferenceController.isSuggestionComplete( mAmbientDisplayConfiguration, prefs)).isTrue(); } + + @Test + public void canHandleClicks_falseWhenAlwaysOnEnabled() { + when(mAmbientDisplayConfiguration.alwaysOnEnabled(anyInt())).thenReturn(true); + assertThat(mController.canHandleClicks()).isFalse(); + } + + @Test + public void canHandleClicks_trueWhenAlwaysOnDisabled() { + when(mAmbientDisplayConfiguration.alwaysOnEnabled(anyInt())).thenReturn(false); + assertThat(mController.canHandleClicks()).isTrue(); + } }