diff --git a/color-check-baseline.xml b/color-check-baseline.xml index 3b2cb815e20..f9629544a44 100644 --- a/color-check-baseline.xml +++ b/color-check-baseline.xml @@ -525,7 +525,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -541,7 +541,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -557,7 +557,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -573,7 +573,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -589,7 +589,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -605,7 +605,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -621,7 +621,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -637,7 +637,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -653,7 +653,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -669,7 +669,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -685,7 +685,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -701,7 +701,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -717,7 +717,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -733,7 +733,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -749,7 +749,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -765,7 +765,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -781,7 +781,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -797,7 +797,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -813,7 +813,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -829,7 +829,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -845,7 +845,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -861,7 +861,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -877,7 +877,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -893,23 +893,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> - - - - @@ -925,7 +909,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -941,7 +925,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -957,7 +941,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -973,7 +957,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -989,7 +973,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1005,7 +989,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1021,7 +1005,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1037,7 +1021,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1053,7 +1037,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1069,7 +1053,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1085,7 +1069,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1101,7 +1085,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1117,7 +1101,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1133,7 +1117,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1149,7 +1133,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1165,7 +1149,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1181,7 +1165,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1197,7 +1181,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1213,7 +1197,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1229,7 +1213,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -1243,6 +1227,22 @@ explanation="Hardcoded color values are bad because theme changes cannot be uniformly applied.Instead use the theme specific colors such as `?android:attr/textColorPrimary` in attributes. This ensures that a theme change from a light to a dark theme can be uniformlyapplied across the app." errorLine1=" <color name="homepage_generic_icon_background">#1A73E8</color>" errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> + + + + + + + + + + + + + + + + + + + + @@ -2173,7 +2237,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -2189,7 +2253,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~"> @@ -2337,22 +2401,6 @@ column="17"/> - - - - + + + + @@ -2445,7 +2509,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~"> @@ -2461,7 +2525,7 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~"> @@ -2477,26 +2541,10 @@ errorLine2=" ~~~~~~~~~~~~~~~~~~~"> - - - - @@ -2541,7 +2589,7 @@ errorLine2=" ^"> @@ -2557,7 +2605,7 @@ errorLine2=" ^"> @@ -2573,7 +2621,7 @@ errorLine2=" ^"> @@ -2589,7 +2637,7 @@ errorLine2=" ^"> @@ -2605,7 +2653,7 @@ errorLine2=" ^"> @@ -2621,7 +2669,7 @@ errorLine2=" ^"> @@ -2637,7 +2685,7 @@ errorLine2=" ^"> @@ -2653,7 +2701,7 @@ errorLine2=" ^"> @@ -2669,7 +2717,7 @@ errorLine2=" ^"> @@ -2685,7 +2733,7 @@ errorLine2=" ^"> @@ -2701,7 +2749,7 @@ errorLine2=" ^"> @@ -2717,7 +2765,7 @@ errorLine2=" ^"> @@ -2733,10 +2781,58 @@ errorLine2=" ^"> + + + + + + + + + + + + @@ -2765,7 +2861,7 @@ errorLine2=" ^"> @@ -2781,7 +2877,7 @@ errorLine2=" ^"> @@ -2797,7 +2893,7 @@ errorLine2=" ^"> @@ -2813,7 +2909,7 @@ errorLine2=" ^"> diff --git a/res/values/ids.xml b/res/values/ids.xml index 57031e1e27b..66af163e2b8 100644 --- a/res/values/ids.xml +++ b/res/values/ids.xml @@ -18,9 +18,6 @@ --> - - - diff --git a/res/values/integers.xml b/res/values/integers.xml new file mode 100644 index 00000000000..ac9a9737bd3 --- /dev/null +++ b/res/values/integers.xml @@ -0,0 +1,22 @@ + + + + + 100 + 101 + 102 + \ No newline at end of file diff --git a/res/values/strings.xml b/res/values/strings.xml index 16b8b20c139..26210d9f48a 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -5711,9 +5711,6 @@ Other options are disabled by your admin More details - - Untitled - General Notification log diff --git a/res/xml/accessibility_magnification_settings.xml b/res/xml/accessibility_magnification_settings.xml index 4083360a396..bac01bd901e 100644 --- a/res/xml/accessibility_magnification_settings.xml +++ b/res/xml/accessibility_magnification_settings.xml @@ -14,14 +14,17 @@ limitations under the License. --> + android:title="@string/accessibility_screen_magnification_gestures_title" + settings:controller="com.android.settings.accessibility.MagnificationGesturesPreferenceController"/> + android:title="@string/accessibility_screen_magnification_navbar_title" + settings:controller="com.android.settings.accessibility.MagnificationNavbarPreferenceController"/> diff --git a/res/xml/network_and_internet.xml b/res/xml/network_and_internet.xml index a28b1e6b268..ee99998d293 100644 --- a/res/xml/network_and_internet.xml +++ b/res/xml/network_and_internet.xml @@ -18,7 +18,8 @@ xmlns:android="http://schemas.android.com/apk/res/android" xmlns:settings="http://schemas.android.com/apk/res-auto" android:key="network_and_internet_screen" - android:title="@string/network_dashboard_title"> + android:title="@string/network_dashboard_title" + settings:initialExpandedChildrenCount="5"> - - @@ -88,4 +80,22 @@ android:key="proxy_settings" android:title="@string/proxy_settings_title" /> - \ No newline at end of file + + + + + diff --git a/src/com/android/settings/ApnEditor.java b/src/com/android/settings/ApnEditor.java index fbc4ba92126..15edbf4ccf8 100644 --- a/src/com/android/settings/ApnEditor.java +++ b/src/com/android/settings/ApnEditor.java @@ -18,11 +18,9 @@ package com.android.settings; import android.app.AlertDialog; import android.app.Dialog; -import android.content.ContentUris; import android.content.ContentValues; import android.content.Context; import android.content.Intent; -import android.content.res.Resources; import android.database.Cursor; import android.net.Uri; import android.os.Bundle; @@ -52,17 +50,17 @@ import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.settings.core.instrumentation.InstrumentedDialogFragment; import com.android.internal.telephony.PhoneConstants; import com.android.internal.util.ArrayUtils; +import com.android.settingslib.utils.ThreadUtils; import java.util.Arrays; import java.util.HashSet; import java.util.List; import java.util.Set; -import static android.app.Activity.RESULT_OK; import static android.content.Context.TELEPHONY_SERVICE; /** - * TODO: After loading all changes, please move this to network package. + * TODO(b/77339683): After loading all changes, please move this to network package. */ public class ApnEditor extends SettingsPreferenceFragment implements OnPreferenceChangeListener, OnKeyListener { @@ -70,7 +68,6 @@ public class ApnEditor extends SettingsPreferenceFragment private final static String TAG = ApnEditor.class.getSimpleName(); private final static boolean VDBG = false; // STOPSHIP if true - private final static String SAVED_POS = "pos"; private final static String KEY_AUTH_TYPE = "auth_type"; private final static String KEY_PROTOCOL = "apn_protocol"; private final static String KEY_ROAMING_PROTOCOL = "apn_roaming_protocol"; @@ -83,37 +80,57 @@ public class ApnEditor extends SettingsPreferenceFragment private static final int MENU_SAVE = Menu.FIRST + 1; private static final int MENU_CANCEL = Menu.FIRST + 2; - private static String sNotSet; - private EditTextPreference mName; - private EditTextPreference mApn; - private EditTextPreference mProxy; - private EditTextPreference mPort; - private EditTextPreference mUser; - private EditTextPreference mServer; - private EditTextPreference mPassword; - private EditTextPreference mMmsc; - private EditTextPreference mMcc; - private EditTextPreference mMnc; - private EditTextPreference mMmsProxy; - private EditTextPreference mMmsPort; - private ListPreference mAuthType; - private EditTextPreference mApnType; - private ListPreference mProtocol; - private ListPreference mRoamingProtocol; - private SwitchPreference mCarrierEnabled; - private MultiSelectListPreference mBearerMulti; - private ListPreference mMvnoType; - private EditTextPreference mMvnoMatchData; + @VisibleForTesting + static String sNotSet; + @VisibleForTesting + EditTextPreference mName; + @VisibleForTesting + EditTextPreference mApn; + @VisibleForTesting + EditTextPreference mProxy; + @VisibleForTesting + EditTextPreference mPort; + @VisibleForTesting + EditTextPreference mUser; + @VisibleForTesting + EditTextPreference mServer; + @VisibleForTesting + EditTextPreference mPassword; + @VisibleForTesting + EditTextPreference mMmsc; + @VisibleForTesting + EditTextPreference mMcc; + @VisibleForTesting + EditTextPreference mMnc; + @VisibleForTesting + EditTextPreference mMmsProxy; + @VisibleForTesting + EditTextPreference mMmsPort; + @VisibleForTesting + ListPreference mAuthType; + @VisibleForTesting + EditTextPreference mApnType; + @VisibleForTesting + ListPreference mProtocol; + @VisibleForTesting + ListPreference mRoamingProtocol; + @VisibleForTesting + SwitchPreference mCarrierEnabled; + @VisibleForTesting + MultiSelectListPreference mBearerMulti; + @VisibleForTesting + ListPreference mMvnoType; + @VisibleForTesting + EditTextPreference mMvnoMatchData; + + @VisibleForTesting + ApnData mApnData; private String mCurMnc; private String mCurMcc; - private Uri mUri; - private Cursor mCursor; private boolean mNewApn; - private boolean mFirstTime; private int mSubId; - private Resources mRes; private TelephonyManager mTelephonyManager; private int mBearerInitialVal = 0; private String mMvnoTypeStr; @@ -121,6 +138,7 @@ public class ApnEditor extends SettingsPreferenceFragment private String[] mReadOnlyApnTypes; private String[] mReadOnlyApnFields; private boolean mReadOnlyApn; + private Uri mCarrierUri; /** * Standard projection for the interesting columns of a normal note. @@ -154,22 +172,27 @@ public class ApnEditor extends SettingsPreferenceFragment }; private static final int ID_INDEX = 0; - private static final int NAME_INDEX = 1; - private static final int APN_INDEX = 2; + @VisibleForTesting + static final int NAME_INDEX = 1; + @VisibleForTesting + static final int APN_INDEX = 2; private static final int PROXY_INDEX = 3; private static final int PORT_INDEX = 4; private static final int USER_INDEX = 5; private static final int SERVER_INDEX = 6; private static final int PASSWORD_INDEX = 7; private static final int MMSC_INDEX = 8; - private static final int MCC_INDEX = 9; - private static final int MNC_INDEX = 10; + @VisibleForTesting + static final int MCC_INDEX = 9; + @VisibleForTesting + static final int MNC_INDEX = 10; private static final int MMSPROXY_INDEX = 12; private static final int MMSPORT_INDEX = 13; private static final int AUTH_TYPE_INDEX = 14; private static final int TYPE_INDEX = 15; private static final int PROTOCOL_INDEX = 16; - private static final int CARRIER_ENABLED_INDEX = 17; + @VisibleForTesting + static final int CARRIER_ENABLED_INDEX = 17; private static final int BEARER_INDEX = 18; private static final int BEARER_BITMASK_INDEX = 19; private static final int ROAMING_PROTOCOL_INDEX = 20; @@ -178,7 +201,6 @@ public class ApnEditor extends SettingsPreferenceFragment private static final int EDITED_INDEX = 23; private static final int USER_EDITABLE_INDEX = 24; - @Override public void onCreate(Bundle icicle) { super.onCreate(icicle); @@ -207,14 +229,11 @@ public class ApnEditor extends SettingsPreferenceFragment mMvnoType = (ListPreference) findPreference(KEY_MVNO_TYPE); mMvnoMatchData = (EditTextPreference) findPreference("mvno_match_data"); - mRes = getResources(); - final Intent intent = getIntent(); final String action = intent.getAction(); mSubId = intent.getIntExtra(ApnSettings.SUB_ID, SubscriptionManager.INVALID_SUBSCRIPTION_ID); - mFirstTime = icicle == null; mReadOnlyApn = false; mReadOnlyApnTypes = null; mReadOnlyApnFields = null; @@ -236,61 +255,47 @@ public class ApnEditor extends SettingsPreferenceFragment } } + Uri uri = null; if (action.equals(Intent.ACTION_EDIT)) { - Uri uri = intent.getData(); + uri = intent.getData(); if (!uri.isPathPrefixMatch(Telephony.Carriers.CONTENT_URI)) { Log.e(TAG, "Edit request not for carrier table. Uri: " + uri); finish(); return; } - mUri = uri; } else if (action.equals(Intent.ACTION_INSERT)) { - if (mFirstTime || icicle.getInt(SAVED_POS) == 0) { - Uri uri = intent.getData(); - if (!uri.isPathPrefixMatch(Telephony.Carriers.CONTENT_URI)) { - Log.e(TAG, "Insert request not for carrier table. Uri: " + uri); - finish(); - return; - } - ContentValues contentValues = new ContentValues(); - contentValues.put(Telephony.Carriers.EDITED, Telephony.Carriers.USER_EDITED); - mUri = getContentResolver().insert(uri, contentValues); - } else { - mUri = ContentUris.withAppendedId(Telephony.Carriers.CONTENT_URI, - icicle.getInt(SAVED_POS)); + mCarrierUri = intent.getData(); + if (!mCarrierUri.isPathPrefixMatch(Telephony.Carriers.CONTENT_URI)) { + Log.e(TAG, "Insert request not for carrier table. Uri: " + mCarrierUri); + finish(); + return; } mNewApn = true; mMvnoTypeStr = intent.getStringExtra(ApnSettings.MVNO_TYPE); mMvnoMatchDataStr = intent.getStringExtra(ApnSettings.MVNO_MATCH_DATA); - // If we were unable to create a new note, then just finish - // this activity. A RESULT_CANCELED will be sent back to the - // original activity if they requested a result. - if (mUri == null) { - Log.w(TAG, "Failed to insert new telephony provider into " - + getIntent().getData()); - finish(); - return; - } - - // The new entry was created, so assume all will end well and - // set the result to be returned. - setResult(RESULT_OK, (new Intent()).setAction(mUri.toString())); - } else { finish(); return; } - mCursor = getActivity().managedQuery(mUri, sProjection, null, null); - mCursor.moveToFirst(); + // Creates an ApnData to store the apn data temporary, so that we don't need the cursor to + // get the apn data. The uri is null if the action is ACTION_INSERT, that mean there is no + // record in the database, so create a empty ApnData to represent a empty row of database. + if (uri != null) { + mApnData = getApnDataFromUri(uri); + } else { + mApnData = new ApnData(sProjection.length); + } mTelephonyManager = (TelephonyManager) getSystemService(TELEPHONY_SERVICE); - Log.d(TAG, "onCreate: EDITED " + mCursor.getInt(EDITED_INDEX)); + boolean isUserEdited = mApnData.getInteger(EDITED_INDEX, Telephony.Carriers.USER_EDITED) + == Telephony.Carriers.USER_EDITED; + + Log.d(TAG, "onCreate: EDITED " + isUserEdited); // if it's not a USER_EDITED apn, check if it's read-only - if (mCursor.getInt(EDITED_INDEX) != Telephony.Carriers.USER_EDITED && - (mCursor.getInt(USER_EDITABLE_INDEX) == 0 || - apnTypesMatch(mReadOnlyApnTypes, mCursor.getString(TYPE_INDEX)))) { + if (!isUserEdited && (mApnData.getInteger(USER_EDITABLE_INDEX, 1) == 0 + || apnTypesMatch(mReadOnlyApnTypes, mApnData.getString(TYPE_INDEX)))) { Log.d(TAG, "onCreate: apnTypesMatch; read-only APN"); mReadOnlyApn = true; disableAllFields(); @@ -302,12 +307,7 @@ public class ApnEditor extends SettingsPreferenceFragment getPreferenceScreen().getPreference(i).setOnPreferenceChangeListener(this); } - } - - @Override - public void onActivityCreated(Bundle savedInstanceState) { - super.onActivityCreated(savedInstanceState); - fillUi(); + fillUI(icicle == null); } /** @@ -462,50 +462,23 @@ public class ApnEditor extends SettingsPreferenceFragment return MetricsEvent.APN_EDITOR; } - @Override - public void onResume() { - super.onResume(); - - if (mUri == null && mNewApn) { - // The URI could have been deleted when activity is paused, - // therefore, it needs to be restored. - ContentValues contentValues = new ContentValues(); - contentValues.put(Telephony.Carriers.EDITED, Telephony.Carriers.USER_EDITED); - mUri = getContentResolver().insert(getIntent().getData(), contentValues); - if (mUri == null) { - Log.w(TAG, "Failed to insert new telephony provider into " - + getIntent().getData()); - finish(); - return; - } - mCursor = getActivity().managedQuery(mUri, sProjection, null, null); - mCursor.moveToFirst(); - } - - } - - @Override - public void onPause() { - super.onPause(); - } - - private void fillUi() { - if (mFirstTime) { - mFirstTime = false; + @VisibleForTesting + void fillUI(boolean firstTime) { + if (firstTime) { // Fill in all the values from the db in both text editor and summary - mName.setText(mCursor.getString(NAME_INDEX)); - mApn.setText(mCursor.getString(APN_INDEX)); - mProxy.setText(mCursor.getString(PROXY_INDEX)); - mPort.setText(mCursor.getString(PORT_INDEX)); - mUser.setText(mCursor.getString(USER_INDEX)); - mServer.setText(mCursor.getString(SERVER_INDEX)); - mPassword.setText(mCursor.getString(PASSWORD_INDEX)); - mMmsProxy.setText(mCursor.getString(MMSPROXY_INDEX)); - mMmsPort.setText(mCursor.getString(MMSPORT_INDEX)); - mMmsc.setText(mCursor.getString(MMSC_INDEX)); - mMcc.setText(mCursor.getString(MCC_INDEX)); - mMnc.setText(mCursor.getString(MNC_INDEX)); - mApnType.setText(mCursor.getString(TYPE_INDEX)); + mName.setText(mApnData.getString(NAME_INDEX)); + mApn.setText(mApnData.getString(APN_INDEX)); + mProxy.setText(mApnData.getString(PROXY_INDEX)); + mPort.setText(mApnData.getString(PORT_INDEX)); + mUser.setText(mApnData.getString(USER_INDEX)); + mServer.setText(mApnData.getString(SERVER_INDEX)); + mPassword.setText(mApnData.getString(PASSWORD_INDEX)); + mMmsProxy.setText(mApnData.getString(MMSPROXY_INDEX)); + mMmsPort.setText(mApnData.getString(MMSPORT_INDEX)); + mMmsc.setText(mApnData.getString(MMSC_INDEX)); + mMcc.setText(mApnData.getString(MCC_INDEX)); + mMnc.setText(mApnData.getString(MNC_INDEX)); + mApnType.setText(mApnData.getString(TYPE_INDEX)); if (mNewApn) { String numeric = mTelephonyManager.getSimOperator(mSubId); // MCC is first 3 chars and then in 2 - 3 chars of MNC @@ -521,20 +494,20 @@ public class ApnEditor extends SettingsPreferenceFragment mCurMcc = mcc; } } - int authVal = mCursor.getInt(AUTH_TYPE_INDEX); + int authVal = mApnData.getInteger(AUTH_TYPE_INDEX, -1); if (authVal != -1) { mAuthType.setValueIndex(authVal); } else { mAuthType.setValue(null); } - mProtocol.setValue(mCursor.getString(PROTOCOL_INDEX)); - mRoamingProtocol.setValue(mCursor.getString(ROAMING_PROTOCOL_INDEX)); - mCarrierEnabled.setChecked(mCursor.getInt(CARRIER_ENABLED_INDEX)==1); - mBearerInitialVal = mCursor.getInt(BEARER_INDEX); + mProtocol.setValue(mApnData.getString(PROTOCOL_INDEX)); + mRoamingProtocol.setValue(mApnData.getString(ROAMING_PROTOCOL_INDEX)); + mCarrierEnabled.setChecked(mApnData.getInteger(CARRIER_ENABLED_INDEX, 1) == 1); + mBearerInitialVal = mApnData.getInteger(BEARER_INDEX, 0); HashSet bearers = new HashSet(); - int bearerBitmask = mCursor.getInt(BEARER_BITMASK_INDEX); + int bearerBitmask = mApnData.getInteger(BEARER_BITMASK_INDEX, 0); if (bearerBitmask == 0) { if (mBearerInitialVal == 0) { bearers.add("" + 0); @@ -556,9 +529,9 @@ public class ApnEditor extends SettingsPreferenceFragment } mBearerMulti.setValues(bearers); - mMvnoType.setValue(mCursor.getString(MVNO_TYPE_INDEX)); + mMvnoType.setValue(mApnData.getString(MVNO_TYPE_INDEX)); mMvnoMatchData.setEnabled(false); - mMvnoMatchData.setText(mCursor.getString(MVNO_MATCH_DATA_INDEX)); + mMvnoMatchData.setText(mApnData.getString(MVNO_MATCH_DATA_INDEX)); if (mNewApn && mMvnoTypeStr != null && mMvnoMatchDataStr != null) { mMvnoType.setValue(mMvnoTypeStr); mMvnoMatchData.setText(mMvnoMatchDataStr); @@ -584,7 +557,7 @@ public class ApnEditor extends SettingsPreferenceFragment int authValIndex = Integer.parseInt(authVal); mAuthType.setValueIndex(authValIndex); - String []values = mRes.getStringArray(R.array.apn_auth_entries); + String[] values = getResources().getStringArray(R.array.apn_auth_entries); mAuthType.setSummary(values[authValIndex]); } else { mAuthType.setSummary(sNotSet); @@ -617,7 +590,7 @@ public class ApnEditor extends SettingsPreferenceFragment if (protocolIndex == -1) { return null; } else { - String[] values = mRes.getStringArray(R.array.apn_protocol_entries); + String[] values = getResources().getStringArray(R.array.apn_protocol_entries); try { return values[protocolIndex]; } catch (ArrayIndexOutOfBoundsException e) { @@ -631,7 +604,7 @@ public class ApnEditor extends SettingsPreferenceFragment if (mBearerIndex == -1) { return null; } else { - String[] values = mRes.getStringArray(R.array.bearer_entries); + String[] values = getResources().getStringArray(R.array.bearer_entries); try { return values[mBearerIndex]; } catch (ArrayIndexOutOfBoundsException e) { @@ -641,7 +614,7 @@ public class ApnEditor extends SettingsPreferenceFragment } private String bearerMultiDescription(Set raw) { - String[] values = mRes.getStringArray(R.array.bearer_entries); + String[] values = getResources().getStringArray(R.array.bearer_entries); StringBuilder retVal = new StringBuilder(); boolean first = true; for (String bearer : raw) { @@ -671,7 +644,7 @@ public class ApnEditor extends SettingsPreferenceFragment if (mvnoIndex == -1) { return null; } else { - String[] values = mRes.getStringArray(R.array.mvno_type_entries); + String[] values = getResources().getStringArray(R.array.mvno_type_entries); boolean mvnoMatchDataUneditable = mReadOnlyApn || (mReadOnlyApnFields != null && Arrays.asList(mReadOnlyApnFields) @@ -703,7 +676,7 @@ public class ApnEditor extends SettingsPreferenceFragment int index = Integer.parseInt((String) newValue); mAuthType.setValueIndex(index); - String[] values = mRes.getStringArray(R.array.apn_auth_entries); + String[] values = getResources().getStringArray(R.array.apn_auth_entries); mAuthType.setSummary(values[index]); } catch (NumberFormatException e) { return false; @@ -764,22 +737,21 @@ public class ApnEditor extends SettingsPreferenceFragment @Override public boolean onOptionsItemSelected(MenuItem item) { switch (item.getItemId()) { - case MENU_DELETE: - deleteApn(); - return true; - case MENU_SAVE: - if (validateAndSave(false)) { + case MENU_DELETE: + deleteApn(); finish(); - } - return true; - case MENU_CANCEL: - if (mNewApn) { - getContentResolver().delete(mUri, null, null); - } - finish(); - return true; + return true; + case MENU_SAVE: + if (validateAndSaveApnData()) { + finish(); + } + return true; + case MENU_CANCEL: + finish(); + return true; + default: + return super.onOptionsItemSelected(item); } - return super.onOptionsItemSelected(item); } @Override @@ -790,11 +762,20 @@ public class ApnEditor extends SettingsPreferenceFragment view.requestFocus(); } + /** + * Try to save the apn data when pressed the back button. An error message will be displayed if + * the apn data is invalid. + * + * TODO(b/77339593): Try to keep the same behavior between back button and up navigate button. + * We will save the valid apn data to the database when pressed the back button, but discard all + * user changed when pressed the up navigate button. + */ + @Override public boolean onKey(View v, int keyCode, KeyEvent event) { if (event.getAction() != KeyEvent.ACTION_DOWN) return false; switch (keyCode) { case KeyEvent.KEYCODE_BACK: { - if (validateAndSave(false)) { + if (validateAndSaveApnData()) { finish(); } return true; @@ -803,62 +784,70 @@ public class ApnEditor extends SettingsPreferenceFragment return false; } - @Override - public void onSaveInstanceState(Bundle icicle) { - super.onSaveInstanceState(icicle); - if (validateAndSave(true)) { - icicle.putInt(SAVED_POS, mCursor.getInt(ID_INDEX)); - } - } - /** - * Add key, value to cv and compare the value against the value at index in mCursor. Return true - * if values are different. assumeDiff indicates if values can be assumed different in which - * case no comparison is needed. - * @return true if value is different from the value at index in mCursor + * Add key, value to {@code cv} and compare the value against the value at index in + * {@link #mApnData}. + * + *

+ * The key, value will not add to {@code cv} if value is null. + * + * @return true if values are different. {@code assumeDiff} indicates if values can be assumed + * different in which case no comparison is needed. */ - boolean setStringValueAndCheckIfDiff(ContentValues cv, String key, String value, - boolean assumeDiff, int index) { - cv.put(key, value); - String valueFromCursor = mCursor.getString(index); + boolean setStringValueAndCheckIfDiff( + ContentValues cv, String key, String value, boolean assumeDiff, int index) { + String valueFromLocalCache = mApnData.getString(index); if (VDBG) { Log.d(TAG, "setStringValueAndCheckIfDiff: assumeDiff: " + assumeDiff + " key: " + key + " value: '" + value - + "' valueFromCursor: '" + valueFromCursor + "'"); + + "' valueFromDb: '" + valueFromLocalCache + "'"); } - return assumeDiff - || !((TextUtils.isEmpty(value) && TextUtils.isEmpty(valueFromCursor)) - || (value != null && value.equals(valueFromCursor))); + boolean isDiff = assumeDiff + || !((TextUtils.isEmpty(value) && TextUtils.isEmpty(valueFromLocalCache)) + || (value != null && value.equals(valueFromLocalCache))); + + if (isDiff && value != null) { + cv.put(key, value); + } + return isDiff; } /** - * Add key, value to cv and compare the value against the value at index in mCursor. Return true - * if values are different. assumeDiff indicates if values can be assumed different in which - * case no comparison is needed. - * @return true if value is different from the value at index in mCursor + * Add key, value to {@code cv} and compare the value against the value at index in + * {@link #mApnData}. + * + * @return true if values are different. {@code assumeDiff} indicates if values can be assumed + * different in which case no comparison is needed. */ - boolean setIntValueAndCheckIfDiff(ContentValues cv, String key, int value, - boolean assumeDiff, int index) { - cv.put(key, value); - int valueFromCursor = mCursor.getInt(index); + boolean setIntValueAndCheckIfDiff( + ContentValues cv, String key, int value, boolean assumeDiff, int index) { + Integer valueFromLocalCache = mApnData.getInteger(index); if (VDBG) { Log.d(TAG, "setIntValueAndCheckIfDiff: assumeDiff: " + assumeDiff + " key: " + key + " value: '" + value - + "' valueFromCursor: '" + valueFromCursor + "'"); + + "' valueFromDb: '" + valueFromLocalCache + "'"); } - return assumeDiff || value != valueFromCursor; + + boolean isDiff = assumeDiff || value != valueFromLocalCache; + if (isDiff) { + cv.put(key, value); + } + return isDiff; } /** - * Check the key fields' validity and save if valid. - * @param force save even if the fields are not valid, if the app is - * being suspended - * @return true if there's no error + * Validates the apn data and save it to the database if it's valid. + * + *

+ * A dialog with error message will be displayed if the APN data is invalid. + * + * @return true if there is no error */ - private boolean validateAndSave(boolean force) { - // nothing to do if it's a read only APN + @VisibleForTesting + boolean validateAndSaveApnData() { + // Nothing to do if it's a read only APN if (mReadOnlyApn) { return true; } @@ -868,21 +857,9 @@ public class ApnEditor extends SettingsPreferenceFragment String mcc = checkNotSet(mMcc.getText()); String mnc = checkNotSet(mMnc.getText()); - if (getErrorMsg() != null && !force) { - ErrorDialog.showError(this); - return false; - } - - if (!mCursor.moveToFirst()) { - Log.w(TAG, - "Could not go to the first row in the Cursor when saving data."); - return false; - } - - // If it's a new APN and a name or apn haven't been entered, then erase the entry - if (force && mNewApn && name.length() < 1 && apn.length() < 1) { - getContentResolver().delete(mUri, null, null); - mUri = null; + String errorMsg = validateApnData(); + if (errorMsg != null) { + showError(); return false; } @@ -890,12 +867,9 @@ public class ApnEditor extends SettingsPreferenceFragment // call update() if it's a new APN. If not, check if any field differs from the db value; // if any diff is found update() should be called boolean callUpdate = mNewApn; - - // Add a dummy name "Untitled", if the user exits the screen without adding a name but - // entered other information worth keeping. callUpdate = setStringValueAndCheckIfDiff(values, Telephony.Carriers.NAME, - name.length() < 1 ? getResources().getString(R.string.untitled_apn) : name, + name, callUpdate, NAME_INDEX); @@ -1054,15 +1028,38 @@ public class ApnEditor extends SettingsPreferenceFragment values.put(Telephony.Carriers.EDITED, Telephony.Carriers.USER_EDITED); if (callUpdate) { - getContentResolver().update(mUri, values, null, null); + final Uri uri = mApnData.getUri() == null ? mCarrierUri : mApnData.getUri(); + updateApnDataToDatabase(uri, values); } else { - if (VDBG) Log.d(TAG, "validateAndSave: not calling update()"); + if (VDBG) Log.d(TAG, "validateAndSaveApnData: not calling update()"); } return true; } - private String getErrorMsg() { + private void updateApnDataToDatabase(Uri uri, ContentValues values) { + ThreadUtils.postOnBackgroundThread(() -> { + if (uri.equals(mCarrierUri)) { + // Add a new apn to the database + final Uri newUri = getContentResolver().insert(mCarrierUri, values); + if (newUri == null) { + Log.e(TAG, "Can't add a new apn to database " + mCarrierUri); + } + } else { + // Update the existing apn + getContentResolver().update( + uri, values, null /* where */, null /* selection Args */); + } + }); + } + + /** + * Validates whether the apn data is valid. + * + * @return An error message if the apn data is invalid, otherwise return null. + */ + @VisibleForTesting + String validateApnData() { String errorMsg = null; String name = checkNotSet(mName.getText()); @@ -1070,14 +1067,14 @@ public class ApnEditor extends SettingsPreferenceFragment String mcc = checkNotSet(mMcc.getText()); String mnc = checkNotSet(mMnc.getText()); - if (name.length() < 1) { - errorMsg = mRes.getString(R.string.error_name_empty); - } else if (apn.length() < 1) { - errorMsg = mRes.getString(R.string.error_apn_empty); - } else if (mcc.length() != 3) { - errorMsg = mRes.getString(R.string.error_mcc_not3); - } else if ((mnc.length() & 0xFFFE) != 2) { - errorMsg = mRes.getString(R.string.error_mnc_not23); + if (TextUtils.isEmpty(name)) { + errorMsg = getResources().getString(R.string.error_name_empty); + } else if (TextUtils.isEmpty(apn)) { + errorMsg = getResources().getString(R.string.error_apn_empty); + } else if (mcc == null || mcc.length() != 3) { + errorMsg = getResources().getString(R.string.error_mcc_not3); + } else if ((mnc == null || (mnc.length() & 0xFFFE) != 2)) { + errorMsg = getResources().getString(R.string.error_mnc_not23); } if (errorMsg == null) { @@ -1088,13 +1085,13 @@ public class ApnEditor extends SettingsPreferenceFragment StringBuilder stringBuilder = new StringBuilder(); for (String type : mReadOnlyApnTypes) { stringBuilder.append(type).append(", "); - Log.d(TAG, "getErrorMsg: appending type: " + type); + Log.d(TAG, "validateApnData: appending type: " + type); } // remove last ", " if (stringBuilder.length() >= 2) { stringBuilder.delete(stringBuilder.length() - 2, stringBuilder.length()); } - errorMsg = String.format(mRes.getString(R.string.error_adding_apn_type), + errorMsg = String.format(getResources().getString(R.string.error_adding_apn_type), stringBuilder); } } @@ -1102,9 +1099,16 @@ public class ApnEditor extends SettingsPreferenceFragment return errorMsg; } + @VisibleForTesting + void showError() { + ErrorDialog.showError(this); + } + private void deleteApn() { - getContentResolver().delete(mUri, null, null); - finish(); + if (mApnData.getUri() != null) { + getContentResolver().delete(mApnData.getUri(), null, null); + mApnData = new ApnData(sProjection.length); + } } private String starify(String value) { @@ -1119,20 +1123,21 @@ public class ApnEditor extends SettingsPreferenceFragment } } + /** + * Returns {@link #sNotSet} if the given string {@code value} is null or empty. The string + * {@link #sNotSet} typically used as the default display when an entry in the preference is + * null or empty. + */ private String checkNull(String value) { - if (value == null || value.length() == 0) { - return sNotSet; - } else { - return value; - } + return TextUtils.isEmpty(value) ? sNotSet : value; } + /** + * Returns null if the given string {@code value} equals to {@link #sNotSet}. This method + * should be used when convert a string value from preference to database. + */ private String checkNotSet(String value) { - if (value == null || value.equals(sNotSet)) { - return ""; - } else { - return value; - } + return sNotSet.equals(value) ? null : value; } private String getUserEnteredApnType() { @@ -1176,7 +1181,7 @@ public class ApnEditor extends SettingsPreferenceFragment @Override public Dialog onCreateDialog(Bundle savedInstanceState) { - String msg = ((ApnEditor) getTargetFragment()).getErrorMsg(); + String msg = ((ApnEditor) getTargetFragment()).validateApnData(); return new AlertDialog.Builder(getContext()) .setTitle(R.string.error_title) @@ -1191,10 +1196,19 @@ public class ApnEditor extends SettingsPreferenceFragment } } - public static class InvalidTypeException extends RuntimeException { - InvalidTypeException(String msg) { - super(msg); + private ApnData getApnDataFromUri(Uri uri) { + ApnData apnData; + try (Cursor cursor = getActivity().managedQuery( + uri, sProjection, null /* selection */, null /* sortOrder */)) { + cursor.moveToFirst(); + apnData = new ApnData(uri, cursor); } + + if (apnData == null) { + Log.d(TAG, "Can't get apnData from Uri " + uri); + } + + return apnData; } @VisibleForTesting @@ -1243,34 +1257,17 @@ public class ApnEditor extends SettingsPreferenceFragment mUri = uri; } - Integer getInteger(int index) throws InvalidTypeException { - if (!isValidTypeOrNull(mData[index], Integer.class)) { - throwInvalidTypeException(Integer.class, mData[index].getClass()); - } + Integer getInteger(int index) { return (Integer) mData[index]; } - Integer getInteger(int index, Integer defaultValue) throws InvalidTypeException { + Integer getInteger(int index, Integer defaultValue) { Integer val = getInteger(index); return val == null ? defaultValue : val; } - String getString(int index) throws InvalidTypeException { - if (!isValidTypeOrNull(mData[index], String.class)) { - throwInvalidTypeException(String.class, mData[index].getClass()); - } + String getString(int index) { return (String) mData[index]; } - - private boolean isValidTypeOrNull(Object obj, Class expectedClass) { - return obj == null || expectedClass.isInstance(obj); - } - - private void throwInvalidTypeException(Class expectedClass, Class actualClass) { - throw new InvalidTypeException( - String.format( - "Type mismatched, want %s, but is %s", expectedClass, actualClass)); - } } - } diff --git a/src/com/android/settings/Utils.java b/src/com/android/settings/Utils.java index 2ba54d21ff7..b1ed38f6c49 100644 --- a/src/com/android/settings/Utils.java +++ b/src/com/android/settings/Utils.java @@ -94,7 +94,6 @@ import com.android.internal.app.UnlaunchableAppActivity; import com.android.internal.util.ArrayUtils; import com.android.internal.widget.LockPatternUtils; import com.android.settings.password.ChooseLockSettingsHelper; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import java.net.InetAddress; import java.util.Iterator; @@ -874,7 +873,7 @@ public final class Utils extends com.android.settingslib.Utils { * @param packageName package to check about */ public static boolean isProfileOrDeviceOwner(UserManager userManager, - DevicePolicyManagerWrapper devicePolicyManager, String packageName) { + DevicePolicyManager devicePolicyManager, String packageName) { List userInfos = userManager.getUsers(); if (devicePolicyManager.isDeviceOwnerAppOnAnyUser(packageName)) { return true; diff --git a/src/com/android/settings/accessibility/AccessibilitySettings.java b/src/com/android/settings/accessibility/AccessibilitySettings.java index ae36e0a3cce..e0e8e4e0df9 100644 --- a/src/com/android/settings/accessibility/AccessibilitySettings.java +++ b/src/com/android/settings/accessibility/AccessibilitySettings.java @@ -813,8 +813,8 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements if (!MagnificationPreferenceFragment.isApplicable(context.getResources())) { preference.setFragment(ToggleScreenMagnificationPreferenceFragment.class.getName()); final Bundle extras = preference.getExtras(); - MagnificationPreferenceFragment.populateMagnificationGesturesPreferenceExtras(extras, - context); + MagnificationGesturesPreferenceController + .populateMagnificationGesturesPreferenceExtras(extras, context); } } diff --git a/src/com/android/settings/accessibility/AccessibilitySettingsForSetupWizard.java b/src/com/android/settings/accessibility/AccessibilitySettingsForSetupWizard.java index 55b79ba8ef8..137a9e43cdd 100644 --- a/src/com/android/settings/accessibility/AccessibilitySettingsForSetupWizard.java +++ b/src/com/android/settings/accessibility/AccessibilitySettingsForSetupWizard.java @@ -156,8 +156,8 @@ public class AccessibilitySettingsForSetupWizard extends SettingsPreferenceFragm preference.setFragment( ToggleScreenMagnificationPreferenceFragmentForSetupWizard.class.getName()); final Bundle extras = preference.getExtras(); - MagnificationPreferenceFragment.populateMagnificationGesturesPreferenceExtras(extras, - context); + MagnificationGesturesPreferenceController + .populateMagnificationGesturesPreferenceExtras(extras, context); } } } diff --git a/src/com/android/settings/accessibility/MagnificationGesturesPreferenceController.java b/src/com/android/settings/accessibility/MagnificationGesturesPreferenceController.java new file mode 100644 index 00000000000..98f6672b339 --- /dev/null +++ b/src/com/android/settings/accessibility/MagnificationGesturesPreferenceController.java @@ -0,0 +1,80 @@ +/* + * 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.accessibility; + +import android.content.Context; +import android.os.Bundle; +import android.provider.Settings; +import android.support.v7.preference.Preference; + +import com.android.settings.R; +import com.android.settings.core.BasePreferenceController; + +public class MagnificationGesturesPreferenceController extends BasePreferenceController { + + private boolean mIsFromSUW = false; + + public MagnificationGesturesPreferenceController(Context context, String key) { + super(context, key); + } + + public void setIsFromSUW(boolean fromSUW) { + mIsFromSUW = fromSUW; + } + + @Override + public boolean handlePreferenceTreeClick(Preference preference) { + if (getPreferenceKey().equals(preference.getKey())) { + Bundle extras = preference.getExtras(); + populateMagnificationGesturesPreferenceExtras(extras, mContext); + extras.putBoolean(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW, mIsFromSUW); + } + return false; + } + + @Override + public int getAvailabilityStatus() { + return AVAILABLE; + } + + @Override + public CharSequence getSummary() { + int resId = 0; + if (mIsFromSUW) { + resId = R.string.accessibility_screen_magnification_short_summary; + } else { + final boolean enabled = Settings.Secure.getInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, 0) == 1; + resId = (enabled ? R.string.accessibility_feature_state_on : + R.string.accessibility_feature_state_off); + } + return mContext.getString(resId); + } + + static void populateMagnificationGesturesPreferenceExtras(Bundle extras, Context context) { + extras.putString(AccessibilitySettings.EXTRA_PREFERENCE_KEY, + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED); + extras.putString(AccessibilitySettings.EXTRA_TITLE, context.getString( + R.string.accessibility_screen_magnification_gestures_title)); + extras.putInt(AccessibilitySettings.EXTRA_TITLE_RES, + R.string.accessibility_screen_magnification_gestures_title); + extras.putCharSequence(AccessibilitySettings.EXTRA_SUMMARY, context.getResources().getText( + R.string.accessibility_screen_magnification_summary)); + extras.putBoolean(AccessibilitySettings.EXTRA_CHECKED, + Settings.Secure.getInt(context.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, 0) == 1); + extras.putInt(AccessibilitySettings.EXTRA_VIDEO_RAW_RESOURCE_ID, + R.raw.accessibility_screen_magnification); + } +} diff --git a/src/com/android/settings/accessibility/MagnificationNavbarPreferenceController.java b/src/com/android/settings/accessibility/MagnificationNavbarPreferenceController.java new file mode 100644 index 00000000000..e0ea6f27c9f --- /dev/null +++ b/src/com/android/settings/accessibility/MagnificationNavbarPreferenceController.java @@ -0,0 +1,78 @@ +/* + * 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.accessibility; + +import android.content.Context; +import android.os.Bundle; +import android.provider.Settings; +import android.support.v7.preference.Preference; + +import com.android.settings.R; +import com.android.settings.core.BasePreferenceController; + +public class MagnificationNavbarPreferenceController extends BasePreferenceController { + + private boolean mIsFromSUW = false; + + public MagnificationNavbarPreferenceController(Context context, String key) { + super(context, key); + } + + public void setIsFromSUW(boolean fromSUW) { + mIsFromSUW = fromSUW; + } + + @Override + public boolean handlePreferenceTreeClick(Preference preference) { + if (getPreferenceKey().equals(preference.getKey())) { + Bundle extras = preference.getExtras(); + extras.putString(AccessibilitySettings.EXTRA_PREFERENCE_KEY, + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED); + extras.putString(AccessibilitySettings.EXTRA_TITLE, mContext.getString( + R.string.accessibility_screen_magnification_navbar_title)); + extras.putInt(AccessibilitySettings.EXTRA_TITLE_RES, + R.string.accessibility_screen_magnification_navbar_title); + extras.putCharSequence(AccessibilitySettings.EXTRA_SUMMARY, + mContext.getResources().getText( + R.string.accessibility_screen_magnification_navbar_summary)); + extras.putBoolean(AccessibilitySettings.EXTRA_CHECKED, + Settings.Secure.getInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, 0) + == 1); + extras.putBoolean(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW, mIsFromSUW); + } + return false; + } + + @Override + public int getAvailabilityStatus() { + return MagnificationPreferenceFragment.isApplicable(mContext.getResources()) + ? AVAILABLE + : DISABLED_UNSUPPORTED; + } + + @Override + public CharSequence getSummary() { + int resId = 0; + if (mIsFromSUW) { + resId = R.string.accessibility_screen_magnification_navbar_short_summary; + } else { + final boolean enabled = Settings.Secure.getInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, 0) == 1; + resId = (enabled ? R.string.accessibility_feature_state_on : + R.string.accessibility_feature_state_off); + } + return mContext.getText(resId); + } +} diff --git a/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java b/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java index 24e87fc5adc..05cb46b4d8f 100644 --- a/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java +++ b/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java @@ -29,40 +29,39 @@ import android.view.View; import android.view.accessibility.AccessibilityManager; import com.android.internal.logging.nano.MetricsProto.MetricsEvent; +import com.android.settings.dashboard.DashboardFragment; import com.android.settings.R; import com.android.settings.SettingsPreferenceFragment; import com.android.settings.search.BaseSearchIndexProvider; import com.android.settings.search.Indexable; +import com.android.settingslib.core.AbstractPreferenceController; +import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.List; -public final class MagnificationPreferenceFragment extends SettingsPreferenceFragment implements - Indexable { +public final class MagnificationPreferenceFragment extends DashboardFragment { + + private static final String TAG = "MagnificationPreferenceFragment"; // Settings App preference keys private static final String PREFERENCE_TITLE_KEY = "magnification_preference_screen_title"; - private static final String MAGNIFICATION_GESTURES_PREFERENCE_SCREEN_KEY = - "screen_magnification_gestures_preference_screen"; - private static final String MAGNIFICATION_NAVBAR_PREFERENCE_SCREEN_KEY = - "screen_magnification_navbar_preference_screen"; // Pseudo ComponentName used to represent navbar magnification in Settings.Secure. private static final String MAGNIFICATION_COMPONENT_ID = "com.android.server.accessibility.MagnificationController"; - private Preference mMagnificationGesturesPreference; - private Preference mMagnificationNavbarPreference; - private boolean mLaunchedFromSuw = false; @Override - public void onCreatePreferences(Bundle bundle, String s) { - addPreferencesFromResource(R.xml.accessibility_magnification_settings); - mMagnificationGesturesPreference = findPreference( - MAGNIFICATION_GESTURES_PREFERENCE_SCREEN_KEY); - mMagnificationNavbarPreference = findPreference(MAGNIFICATION_NAVBAR_PREFERENCE_SCREEN_KEY); + public int getMetricsCategory() { + return MetricsEvent.ACCESSIBILITY_SCREEN_MAGNIFICATION_SETTINGS; + } + + @Override + protected String getLogTag() { + return TAG; } @Override @@ -71,28 +70,21 @@ public final class MagnificationPreferenceFragment extends SettingsPreferenceFra } @Override - public void onViewCreated(View view, Bundle savedInstanceState) { - super.onViewCreated(view, savedInstanceState); + protected int getPreferenceScreenResId() { + return R.xml.accessibility_magnification_settings; + } + @Override + public void onAttach(Context context) { + super.onAttach(context); final Bundle args = getArguments(); if ((args != null) && args.containsKey(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW)) { mLaunchedFromSuw = args.getBoolean(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW); } - } - - @Override - public void onResume() { - super.onResume(); - getActivity().setTitle(R.string.accessibility_screen_magnification_title); - updateFeatureSummary(Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, - mMagnificationGesturesPreference); - updateFeatureSummary(Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, - mMagnificationNavbarPreference); - } - - @Override - public int getMetricsCategory() { - return MetricsEvent.ACCESSIBILITY_SCREEN_MAGNIFICATION_SETTINGS; + use(MagnificationGesturesPreferenceController.class) + .setIsFromSUW(mLaunchedFromSuw); + use(MagnificationNavbarPreferenceController.class) + .setIsFromSUW(mLaunchedFromSuw); } @Override @@ -102,57 +94,9 @@ public final class MagnificationPreferenceFragment extends SettingsPreferenceFra preference.setFragment( ToggleScreenMagnificationPreferenceFragmentForSetupWizard.class.getName()); } - if (mMagnificationGesturesPreference == preference) { - handleMagnificationGesturesPreferenceScreenClick(); - super.onPreferenceTreeClick(mMagnificationGesturesPreference); - return true; - } else if (mMagnificationNavbarPreference == preference) { - handleMagnificationNavbarPreferenceScreenClick(); - super.onPreferenceTreeClick(mMagnificationNavbarPreference); - return true; - } return super.onPreferenceTreeClick(preference); } - private void updateFeatureSummary(String prefKey, Preference pref) { - if (!mLaunchedFromSuw) { - final boolean enabled = Settings.Secure.getInt(getContentResolver(), prefKey, 0) == 1; - pref.setSummary(enabled ? R.string.accessibility_feature_state_on - : R.string.accessibility_feature_state_off); - } else { - if (Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED.equals(prefKey)) { - pref.setSummary(R.string.accessibility_screen_magnification_short_summary); - } else if (Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED.equals( - prefKey)) { - pref.setSummary(R.string.accessibility_screen_magnification_navbar_short_summary); - } - } - } - - private void handleMagnificationGesturesPreferenceScreenClick() { - Bundle extras = mMagnificationGesturesPreference.getExtras(); - populateMagnificationGesturesPreferenceExtras(extras, getContext()); - extras.putBoolean(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW, mLaunchedFromSuw); - } - - private void handleMagnificationNavbarPreferenceScreenClick() { - Bundle extras = mMagnificationNavbarPreference.getExtras(); - extras.putString(AccessibilitySettings.EXTRA_PREFERENCE_KEY, - Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED); - extras.putString(AccessibilitySettings.EXTRA_TITLE, getString( - R.string.accessibility_screen_magnification_navbar_title)); - extras.putInt(AccessibilitySettings.EXTRA_TITLE_RES, - R.string.accessibility_screen_magnification_navbar_title); - extras.putCharSequence(AccessibilitySettings.EXTRA_SUMMARY, - getActivity().getResources().getText( - R.string.accessibility_screen_magnification_navbar_summary)); - extras.putBoolean(AccessibilitySettings.EXTRA_CHECKED, - Settings.Secure.getInt(getContentResolver(), - Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, 0) - == 1); - extras.putBoolean(AccessibilitySettings.EXTRA_LAUNCHED_FROM_SUW, mLaunchedFromSuw); - } - static CharSequence getConfigurationWarningStringForSecureSettingsKey(String key, Context context) { if (!Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED.equals(key)) { @@ -187,22 +131,6 @@ public final class MagnificationPreferenceFragment extends SettingsPreferenceFra return null; } - static void populateMagnificationGesturesPreferenceExtras(Bundle extras, Context context) { - extras.putString(AccessibilitySettings.EXTRA_PREFERENCE_KEY, - Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED); - extras.putString(AccessibilitySettings.EXTRA_TITLE, context.getString( - R.string.accessibility_screen_magnification_gestures_title)); - extras.putInt(AccessibilitySettings.EXTRA_TITLE_RES, - R.string.accessibility_screen_magnification_gestures_title); - extras.putCharSequence(AccessibilitySettings.EXTRA_SUMMARY, context.getResources().getText( - R.string.accessibility_screen_magnification_summary)); - extras.putBoolean(AccessibilitySettings.EXTRA_CHECKED, - Settings.Secure.getInt(context.getContentResolver(), - Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, 0) == 1); - extras.putInt(AccessibilitySettings.EXTRA_VIDEO_RAW_RESOURCE_ID, - R.raw.accessibility_screen_magnification); - } - /** * @return {@code true} if this fragment should be shown, {@code false} otherwise. This * fragment is shown in the case that more than one magnification mode is available. diff --git a/src/com/android/settings/accounts/RemoveAccountPreferenceController.java b/src/com/android/settings/accounts/RemoveAccountPreferenceController.java index 98ab504432a..24d3ea15b1e 100644 --- a/src/com/android/settings/accounts/RemoveAccountPreferenceController.java +++ b/src/com/android/settings/accounts/RemoveAccountPreferenceController.java @@ -25,7 +25,6 @@ import android.app.Activity; import android.app.AlertDialog; import android.app.Dialog; import android.app.Fragment; -import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; @@ -37,13 +36,11 @@ import android.view.View; import android.view.View.OnClickListener; import android.widget.Button; -import com.android.internal.annotations.VisibleForTesting; import com.android.internal.logging.nano.MetricsProto; import com.android.settings.R; import com.android.settings.applications.LayoutPreference; import com.android.settings.core.PreferenceControllerMixin; import com.android.settings.core.instrumentation.InstrumentedDialogFragment; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.RestrictedLockUtils.EnforcedAdmin; import com.android.settingslib.core.AbstractPreferenceController; @@ -58,26 +55,17 @@ public class RemoveAccountPreferenceController extends AbstractPreferenceControl private Account mAccount; private Fragment mParentFragment; private UserHandle mUserHandle; - private DevicePolicyManagerWrapper mDpm; public RemoveAccountPreferenceController(Context context, Fragment parent) { - this(context, parent, new DevicePolicyManagerWrapper( - (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE))); - } - - @VisibleForTesting - RemoveAccountPreferenceController(Context context, Fragment parent, - DevicePolicyManagerWrapper dpm) { super(context); mParentFragment = parent; - mDpm = dpm; } @Override public void displayPreference(PreferenceScreen screen) { super.displayPreference(screen); final LayoutPreference removeAccountPreference = - (LayoutPreference) screen.findPreference(KEY_REMOVE_ACCOUNT); + (LayoutPreference) screen.findPreference(KEY_REMOVE_ACCOUNT); Button removeAccountButton = (Button) removeAccountPreference.findViewById(R.id.button); removeAccountButton.setOnClickListener(this); } @@ -96,7 +84,7 @@ public class RemoveAccountPreferenceController extends AbstractPreferenceControl public void onClick(View v) { if (mUserHandle != null) { final EnforcedAdmin admin = RestrictedLockUtils.checkIfRestrictionEnforced(mContext, - UserManager.DISALLOW_MODIFY_ACCOUNTS, mUserHandle.getIdentifier()); + UserManager.DISALLOW_MODIFY_ACCOUNTS, mUserHandle.getIdentifier()); if (admin != null) { RestrictedLockUtils.sendShowAdminSupportDetailsIntent(mContext, admin); return; @@ -148,11 +136,11 @@ public class RemoveAccountPreferenceController extends AbstractPreferenceControl public Dialog onCreateDialog(Bundle savedInstanceState) { final Context context = getActivity(); return new AlertDialog.Builder(context) - .setTitle(R.string.really_remove_account_title) - .setMessage(R.string.really_remove_account_message) - .setNegativeButton(android.R.string.cancel, null) - .setPositiveButton(R.string.remove_account_label, this) - .create(); + .setTitle(R.string.really_remove_account_title) + .setMessage(R.string.really_remove_account_message) + .setNegativeButton(android.R.string.cancel, null) + .setPositiveButton(R.string.remove_account_label, this) + .create(); } @Override @@ -174,7 +162,7 @@ public class RemoveAccountPreferenceController extends AbstractPreferenceControl boolean failed = true; try { if (future.getResult() - .getBoolean(AccountManager.KEY_BOOLEAN_RESULT)) { + .getBoolean(AccountManager.KEY_BOOLEAN_RESULT)) { failed = false; } } catch (OperationCanceledException e) { @@ -216,10 +204,10 @@ public class RemoveAccountPreferenceController extends AbstractPreferenceControl final Context context = getActivity(); return new AlertDialog.Builder(context) - .setTitle(R.string.really_remove_account_title) - .setMessage(R.string.remove_account_failed) - .setPositiveButton(android.R.string.ok, null) - .create(); + .setTitle(R.string.really_remove_account_title) + .setMessage(R.string.remove_account_failed) + .setPositiveButton(android.R.string.ok, null) + .create(); } @Override diff --git a/src/com/android/settings/applications/AppInfoBase.java b/src/com/android/settings/applications/AppInfoBase.java index fb63df2d4e9..f8ed315bfd5 100644 --- a/src/com/android/settings/applications/AppInfoBase.java +++ b/src/com/android/settings/applications/AppInfoBase.java @@ -47,7 +47,6 @@ import com.android.settings.applications.manageapplications.ManageApplications; import com.android.settings.core.SubSettingLauncher; import com.android.settings.core.instrumentation.InstrumentedDialogFragment; import com.android.settings.overlay.FeatureFactory; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.applications.ApplicationsState; import com.android.settingslib.applications.ApplicationsState.AppEntry; @@ -75,7 +74,7 @@ public abstract class AppInfoBase extends SettingsPreferenceFragment protected String mPackageName; protected IUsbManager mUsbManager; - protected DevicePolicyManagerWrapper mDpm; + protected DevicePolicyManager mDpm; protected UserManager mUserManager; protected PackageManager mPm; @@ -94,8 +93,7 @@ public abstract class AppInfoBase extends SettingsPreferenceFragment .getApplicationFeatureProvider(activity); mState = ApplicationsState.getInstance(activity.getApplication()); mSession = mState.newSession(this, getLifecycle()); - mDpm = new DevicePolicyManagerWrapper( - (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE)); + mDpm = (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE); mUserManager = (UserManager) activity.getSystemService(Context.USER_SERVICE); mPm = activity.getPackageManager(); IBinder b = ServiceManager.getService(Context.USB_SERVICE); @@ -161,10 +159,10 @@ public abstract class AppInfoBase extends SettingsPreferenceFragment } protected void setIntentAndFinish(boolean finish, boolean appChanged) { - if (localLOGV) Log.i(TAG, "appChanged="+appChanged); + if (localLOGV) Log.i(TAG, "appChanged=" + appChanged); Intent intent = new Intent(); intent.putExtra(ManageApplications.APP_CHG, appChanged); - SettingsActivity sa = (SettingsActivity)getActivity(); + SettingsActivity sa = (SettingsActivity) getActivity(); sa.finishPreferencePanel(Activity.RESULT_OK, intent); mFinishing = true; } @@ -176,6 +174,7 @@ public abstract class AppInfoBase extends SettingsPreferenceFragment } protected abstract boolean refreshUi(); + protected abstract AlertDialog createDialog(int id, int errorCode); @Override diff --git a/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounter.java b/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounter.java index a1bf14edb52..77cecd28059 100644 --- a/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounter.java +++ b/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounter.java @@ -22,7 +22,6 @@ import android.os.Build; import android.os.RemoteException; import android.os.UserHandle; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -34,11 +33,11 @@ public abstract class AppWithAdminGrantedPermissionsCounter extends AppCounter { private final String[] mPermissions; private final IPackageManagerWrapper mPackageManagerService; - private final DevicePolicyManagerWrapper mDevicePolicyManager; + private final DevicePolicyManager mDevicePolicyManager; public AppWithAdminGrantedPermissionsCounter(Context context, String[] permissions, PackageManagerWrapper packageManager, IPackageManagerWrapper packageManagerService, - DevicePolicyManagerWrapper devicePolicyManager) { + DevicePolicyManager devicePolicyManager) { super(context, packageManager); mPermissions = permissions; mPackageManagerService = packageManagerService; @@ -52,7 +51,7 @@ public abstract class AppWithAdminGrantedPermissionsCounter extends AppCounter { } public static boolean includeInCount(String[] permissions, - DevicePolicyManagerWrapper devicePolicyManager, PackageManagerWrapper packageManager, + DevicePolicyManager devicePolicyManager, PackageManagerWrapper packageManager, IPackageManagerWrapper packageManagerService, ApplicationInfo info) { if (info.targetSdkVersion >= Build.VERSION_CODES.M) { // The app uses run-time permissions. Check whether one or more of the permissions were @@ -70,7 +69,7 @@ public abstract class AppWithAdminGrantedPermissionsCounter extends AppCounter { // permissions and was installed by enterprise policy, implicitly granting permissions. if (packageManager.getInstallReason(info.packageName, new UserHandle(UserHandle.getUserId(info.uid))) - != PackageManager.INSTALL_REASON_POLICY) { + != PackageManager.INSTALL_REASON_POLICY) { return false; } try { diff --git a/src/com/android/settings/applications/AppWithAdminGrantedPermissionsLister.java b/src/com/android/settings/applications/AppWithAdminGrantedPermissionsLister.java index dd5a8076462..655758aa12c 100644 --- a/src/com/android/settings/applications/AppWithAdminGrantedPermissionsLister.java +++ b/src/com/android/settings/applications/AppWithAdminGrantedPermissionsLister.java @@ -16,9 +16,10 @@ package com.android.settings.applications; +import android.app.admin.DevicePolicyManager; import android.content.pm.ApplicationInfo; import android.os.UserManager; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; + import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -29,11 +30,11 @@ import com.android.settingslib.wrapper.PackageManagerWrapper; public abstract class AppWithAdminGrantedPermissionsLister extends AppLister { private final String[] mPermissions; private final IPackageManagerWrapper mPackageManagerService; - private final DevicePolicyManagerWrapper mDevicePolicyManager; + private final DevicePolicyManager mDevicePolicyManager; public AppWithAdminGrantedPermissionsLister(String[] permissions, PackageManagerWrapper packageManager, IPackageManagerWrapper packageManagerService, - DevicePolicyManagerWrapper devicePolicyManager, UserManager userManager) { + DevicePolicyManager devicePolicyManager, UserManager userManager) { super(packageManager, userManager); mPermissions = permissions; mPackageManagerService = packageManagerService; diff --git a/src/com/android/settings/applications/ApplicationFeatureProviderImpl.java b/src/com/android/settings/applications/ApplicationFeatureProviderImpl.java index e1f434e8683..cd54f797bdb 100644 --- a/src/com/android/settings/applications/ApplicationFeatureProviderImpl.java +++ b/src/com/android/settings/applications/ApplicationFeatureProviderImpl.java @@ -16,6 +16,7 @@ package com.android.settings.applications; +import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.Intent; import android.content.pm.ComponentInfo; @@ -26,7 +27,6 @@ import android.os.RemoteException; import android.os.UserManager; import android.util.ArraySet; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -39,11 +39,11 @@ public class ApplicationFeatureProviderImpl implements ApplicationFeatureProvide private final Context mContext; private final PackageManagerWrapper mPm; private final IPackageManagerWrapper mPms; - private final DevicePolicyManagerWrapper mDpm; + private final DevicePolicyManager mDpm; private final UserManager mUm; public ApplicationFeatureProviderImpl(Context context, PackageManagerWrapper pm, - IPackageManagerWrapper pms, DevicePolicyManagerWrapper dpm) { + IPackageManagerWrapper pms, DevicePolicyManager dpm) { mContext = context.getApplicationContext(); mPm = pm; mPms = pms; @@ -150,7 +150,7 @@ public class ApplicationFeatureProviderImpl implements ApplicationFeatureProvide CurrentUserAndManagedProfileAppWithAdminGrantedPermissionsCounter(Context context, String[] permissions, PackageManagerWrapper packageManager, IPackageManagerWrapper packageManagerService, - DevicePolicyManagerWrapper devicePolicyManager, NumberOfAppsCallback callback) { + DevicePolicyManager devicePolicyManager, NumberOfAppsCallback callback) { super(context, permissions, packageManager, packageManagerService, devicePolicyManager); mCallback = callback; } @@ -182,7 +182,7 @@ public class ApplicationFeatureProviderImpl implements ApplicationFeatureProvide CurrentUserAppWithAdminGrantedPermissionsLister(String[] permissions, PackageManagerWrapper packageManager, IPackageManagerWrapper packageManagerService, - DevicePolicyManagerWrapper devicePolicyManager, UserManager userManager, + DevicePolicyManager devicePolicyManager, UserManager userManager, ListOfAppsCallback callback) { super(permissions, packageManager, packageManagerService, devicePolicyManager, userManager); diff --git a/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceController.java b/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceController.java index 6e978dcbc71..da9090928e5 100644 --- a/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceController.java +++ b/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceController.java @@ -44,7 +44,6 @@ import com.android.settings.applications.ApplicationFeatureProvider; import com.android.settings.core.BasePreferenceController; import com.android.settings.overlay.FeatureFactory; import com.android.settings.widget.ActionButtonPreference; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState.AppEntry; @@ -67,7 +66,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle private final ApplicationFeatureProvider mApplicationFeatureProvider; private int mUserId; - private DevicePolicyManagerWrapper mDpm; + private DevicePolicyManager mDpm; private UserManager mUserManager; private PackageManager mPm; @@ -94,7 +93,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle @Override public int getAvailabilityStatus() { return AppUtils.isInstant(mParent.getPackageInfo().applicationInfo) - ? DISABLED_FOR_USER : AVAILABLE; + ? DISABLED_FOR_USER : AVAILABLE; } @Override @@ -112,8 +111,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle mPm = mContext.getPackageManager(); } if (mDpm == null) { - mDpm = new DevicePolicyManagerWrapper( - (DevicePolicyManager) mContext.getSystemService(Context.DEVICE_POLICY_SERVICE)); + mDpm = (DevicePolicyManager) mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); } if (mUserManager == null) { mUserManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE); @@ -125,7 +123,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle final List homeActivities = new ArrayList(); mPm.getHomeActivities(homeActivities); mHomePackages.clear(); - for (int i = 0; i< homeActivities.size(); i++) { + for (int i = 0; i < homeActivities.size(); i++) { final ResolveInfo ri = homeActivities.get(i); final String activityPkg = ri.activityInfo.packageName; mHomePackages.add(activityPkg); @@ -187,7 +185,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle enabled = false; } else { ArrayList homeActivities = new ArrayList(); - ComponentName currentDefaultHome = mPm.getHomeActivities(homeActivities); + ComponentName currentDefaultHome = mPm.getHomeActivities(homeActivities); if (currentDefaultHome == null) { // No preferred default, so permit uninstall only when // there is more than one candidate @@ -284,7 +282,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle Log.w(TAG, "User can't force stop device admin"); updateForceStopButton(false); } else if (mPm.isPackageStateProtected(packageInfo.packageName, - UserHandle.getUserId(appEntry.info.uid))) { + UserHandle.getUserId(appEntry.info.uid))) { Log.w(TAG, "User can't force stop protected packages"); updateForceStopButton(false); } else if (AppUtils.isInstant(packageInfo.applicationInfo)) { @@ -298,7 +296,7 @@ public class AppActionButtonPreferenceController extends BasePreferenceControlle } else { final Intent intent = new Intent(Intent.ACTION_QUERY_PACKAGE_RESTART, Uri.fromParts("package", appEntry.info.packageName, null)); - intent.putExtra(Intent.EXTRA_PACKAGES, new String[] { appEntry.info.packageName }); + intent.putExtra(Intent.EXTRA_PACKAGES, new String[] {appEntry.info.packageName}); intent.putExtra(Intent.EXTRA_UID, appEntry.info.uid); intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(appEntry.info.uid)); Log.d(TAG, "Sending broadcast to query restart status for " diff --git a/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java b/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java index eddbd963981..4a0db4ef4ea 100755 --- a/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java +++ b/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java @@ -55,7 +55,6 @@ import com.android.settings.applications.manageapplications.ManageApplications; import com.android.settings.core.SubSettingLauncher; import com.android.settings.core.instrumentation.InstrumentedDialogFragment; import com.android.settings.dashboard.DashboardFragment; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState; @@ -122,7 +121,7 @@ public class AppInfoDashboardFragment extends DashboardFragment private int mUserId; private String mPackageName; - private DevicePolicyManagerWrapper mDpm; + private DevicePolicyManager mDpm; private UserManager mUserManager; private PackageManager mPm; @@ -198,8 +197,7 @@ public class AppInfoDashboardFragment extends DashboardFragment super.onCreate(icicle); mFinishing = false; final Activity activity = getActivity(); - mDpm = new DevicePolicyManagerWrapper( - (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE)); + mDpm = (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE); mUserManager = (UserManager) activity.getSystemService(Context.USER_SERVICE); mPm = activity.getPackageManager(); diff --git a/src/com/android/settings/applications/appinfo/AppMemoryPreferenceController.java b/src/com/android/settings/applications/appinfo/AppMemoryPreferenceController.java index 265754cad8d..daf3992c3c2 100644 --- a/src/com/android/settings/applications/appinfo/AppMemoryPreferenceController.java +++ b/src/com/android/settings/applications/appinfo/AppMemoryPreferenceController.java @@ -109,7 +109,7 @@ public class AppMemoryPreferenceController extends BasePreferenceController } return DevelopmentSettingsEnabler.isDevelopmentSettingsEnabled(mContext) - ? AVAILABLE : DISABLED_DEPENDENT_SETTING; + ? AVAILABLE : DISABLED_UNSUPPORTED; } @Override diff --git a/src/com/android/settings/applications/appinfo/PictureInPictureSettings.java b/src/com/android/settings/applications/appinfo/PictureInPictureSettings.java index e2caa4198aa..ef2c7a9742c 100644 --- a/src/com/android/settings/applications/appinfo/PictureInPictureSettings.java +++ b/src/com/android/settings/applications/appinfo/PictureInPictureSettings.java @@ -40,7 +40,6 @@ import com.android.settings.R; import com.android.settings.applications.AppInfoBase; import com.android.settings.notification.EmptyTextSettings; import com.android.settings.widget.AppPreference; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; import java.text.Collator; @@ -88,7 +87,7 @@ public class PictureInPictureSettings extends EmptyTextSettings { private Context mContext; private PackageManagerWrapper mPackageManager; - private UserManagerWrapper mUserManager; + private UserManager mUserManager; private IconDrawableFactory mIconDrawableFactory; /** @@ -119,7 +118,7 @@ public class PictureInPictureSettings extends EmptyTextSettings { // Do nothing } - public PictureInPictureSettings(PackageManagerWrapper pm, UserManagerWrapper um) { + public PictureInPictureSettings(PackageManagerWrapper pm, UserManager um) { mPackageManager = pm; mUserManager = um; } @@ -130,7 +129,7 @@ public class PictureInPictureSettings extends EmptyTextSettings { mContext = getActivity(); mPackageManager = new PackageManagerWrapper(mContext.getPackageManager()); - mUserManager = new UserManagerWrapper(mContext.getSystemService(UserManager.class)); + mUserManager = (UserManager) mContext.getSystemService(Context.USER_SERVICE); mIconDrawableFactory = IconDrawableFactory.newInstance(mContext); } diff --git a/src/com/android/settings/connecteddevice/usb/UsbBackend.java b/src/com/android/settings/connecteddevice/usb/UsbBackend.java index 333449f9420..54811c8d5db 100644 --- a/src/com/android/settings/connecteddevice/usb/UsbBackend.java +++ b/src/com/android/settings/connecteddevice/usb/UsbBackend.java @@ -22,11 +22,10 @@ import android.hardware.usb.UsbManager; import android.hardware.usb.UsbPort; import android.hardware.usb.UsbPortStatus; import android.net.ConnectivityManager; +import android.os.UserHandle; import android.os.UserManager; import android.support.annotation.VisibleForTesting; -import com.android.settings.wrapper.UserManagerWrapper; - /** * Provides access to underlying system USB functionality. */ @@ -50,17 +49,17 @@ public class UsbBackend { private UsbPortStatus mPortStatus; public UsbBackend(Context context) { - this(context, new UserManagerWrapper(UserManager.get(context))); + this(context, (UserManager) context.getSystemService(Context.USER_SERVICE)); } @VisibleForTesting - public UsbBackend(Context context, UserManagerWrapper userManagerWrapper) { + public UsbBackend(Context context, UserManager userManager) { mUsbManager = context.getSystemService(UsbManager.class); - mFileTransferRestricted = userManagerWrapper.isUsbFileTransferRestricted(); - mFileTransferRestrictedBySystem = userManagerWrapper.isUsbFileTransferRestrictedBySystem(); - mTetheringRestricted = userManagerWrapper.isUsbTetheringRestricted(); - mTetheringRestrictedBySystem = userManagerWrapper.isUsbTetheringRestrictedBySystem(); + mFileTransferRestricted = isUsbFileTransferRestricted(userManager); + mFileTransferRestrictedBySystem = isUsbFileTransferRestrictedBySystem(userManager); + mTetheringRestricted = isUsbTetheringRestricted(userManager); + mTetheringRestrictedBySystem = isUsbTetheringRestrictedBySystem(userManager); mMidiSupported = context.getPackageManager().hasSystemFeature(PackageManager.FEATURE_MIDI); ConnectivityManager cm = @@ -172,6 +171,24 @@ public class UsbBackend { return Integer.parseInt(role); } + private static boolean isUsbFileTransferRestricted(UserManager userManager) { + return userManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER); + } + + private static boolean isUsbTetheringRestricted(UserManager userManager) { + return userManager.hasUserRestriction(UserManager.DISALLOW_CONFIG_TETHERING); + } + + private static boolean isUsbFileTransferRestrictedBySystem(UserManager userManager) { + return userManager.hasBaseUserRestriction( + UserManager.DISALLOW_USB_FILE_TRANSFER, UserHandle.of(UserHandle.myUserId())); + } + + private static boolean isUsbTetheringRestrictedBySystem(UserManager userManager) { + return userManager.hasBaseUserRestriction( + UserManager.DISALLOW_CONFIG_TETHERING, UserHandle.of(UserHandle.myUserId())); + } + private boolean areFunctionDisallowed(long functions) { return (mFileTransferRestricted && ((functions & UsbManager.FUNCTION_MTP) != 0 || (functions & UsbManager.FUNCTION_PTP) != 0)) diff --git a/src/com/android/settings/core/BasePreferenceController.java b/src/com/android/settings/core/BasePreferenceController.java index fd17012d574..44305dd897e 100644 --- a/src/com/android/settings/core/BasePreferenceController.java +++ b/src/com/android/settings/core/BasePreferenceController.java @@ -22,7 +22,6 @@ import com.android.settings.search.ResultPayload; import com.android.settings.search.SearchIndexableRaw; import com.android.settings.slices.SliceData; import com.android.settingslib.core.AbstractPreferenceController; -import com.android.settingslib.core.lifecycle.Lifecycle; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; @@ -30,6 +29,10 @@ import java.lang.reflect.Constructor; import java.lang.reflect.InvocationTargetException; import java.util.List; +import android.support.v7.preference.Preference; +import android.support.v7.preference.PreferenceGroup; +import android.support.v7.preference.PreferenceScreen; + /** * Abstract class to consolidate utility between preference controllers and act as an interface * for Slices. The abstract classes that inherit from this class will act as the direct interfaces @@ -39,6 +42,12 @@ public abstract class BasePreferenceController extends AbstractPreferenceControl private static final String TAG = "SettingsPrefController"; + /** + * Denotes the availability of the Setting. + *

+ * Used both explicitly and by the convenience methods {@link #isAvailable()} and + * {@link #isSupported()}. + */ @Retention(RetentionPolicy.SOURCE) @IntDef({AVAILABLE, DISABLED_UNSUPPORTED, DISABLED_FOR_USER, DISABLED_DEPENDENT_SETTING, UNAVAILABLE_UNKNOWN}) @@ -52,21 +61,42 @@ public abstract class BasePreferenceController extends AbstractPreferenceControl /** * The setting is not supported by the device. + *

+ * There is no guarantee that the setting page exists, and any links to the Setting should take + * you to the home page of Settings. */ public static final int DISABLED_UNSUPPORTED = 1; /** * The setting cannot be changed by the current user. + *

+ * Links to the Setting should take you to the page of the Setting, even if it cannot be + * changed. */ public static final int DISABLED_FOR_USER = 2; /** * The setting has a dependency in the Settings App which is currently blocking access. + *

+ * It must be possible for the Setting to be enabled by changing the configuration of the device + * settings. That is, a setting that cannot be changed because of the state of another setting. + * This should not be used for a setting that would be hidden from the UI entirely. + *

+ * Correct use: Intensity of night display should be {@link #DISABLED_DEPENDENT_SETTING} when + * night display is off. + * Incorrect use: Mobile Data is {@link #DISABLED_DEPENDENT_SETTING} when there is no + * data-enabled sim. + *

+ * Links to the Setting should take you to the page of the Setting, even if it cannot be + * changed. */ public static final int DISABLED_DEPENDENT_SETTING = 3; /** * A catch-all case for internal errors and inexplicable unavailability. + *

+ * There is no guarantee that the setting page exists, and any links to the Setting should take + * you to the home page of Settings. */ public static final int UNAVAILABLE_UNKNOWN = 4; @@ -134,9 +164,25 @@ public abstract class BasePreferenceController extends AbstractPreferenceControl return mPreferenceKey; } + /** + * @return {@code true} when the controller can be changed on the device. + * + *

+ * Will return true for {@link #AVAILABLE} and {@link #DISABLED_DEPENDENT_SETTING}. + *

+ * When the availability status returned by {@link #getAvailabilityStatus()} is + * {@link #DISABLED_DEPENDENT_SETTING}, then the setting will be disabled by default in the + * DashboardFragment, and it is up to the {@link BasePreferenceController} to enable the + * preference at the right time. + * + * TODO (mfritze) Build a dependency mechanism to allow a controller to easily define the + * dependent setting. + */ @Override public final boolean isAvailable() { - return getAvailabilityStatus() == AVAILABLE; + final int availabilityStatus = getAvailabilityStatus(); + return (availabilityStatus == AVAILABLE) || + (availabilityStatus == DISABLED_DEPENDENT_SETTING); } /** @@ -150,6 +196,21 @@ public abstract class BasePreferenceController extends AbstractPreferenceControl return getAvailabilityStatus() != DISABLED_UNSUPPORTED; } + /** + * Displays preference in this controller. + */ + @Override + public void displayPreference(PreferenceScreen screen) { + super.displayPreference(screen); + if (getAvailabilityStatus() == DISABLED_DEPENDENT_SETTING) { + // Disable preference if it depends on another setting. + final Preference preference = screen.findPreference(getPreferenceKey()); + if (preference != null) { + preference.setEnabled(false); + } + } + } + /** * @return the UI type supported by the controller. */ diff --git a/src/com/android/settings/deviceinfo/StorageDashboardFragment.java b/src/com/android/settings/deviceinfo/StorageDashboardFragment.java index ead941f75b3..8e56b12ec8f 100644 --- a/src/com/android/settings/deviceinfo/StorageDashboardFragment.java +++ b/src/com/android/settings/deviceinfo/StorageDashboardFragment.java @@ -47,7 +47,6 @@ import com.android.settings.deviceinfo.storage.VolumeSizesLoader; import com.android.settings.search.BaseSearchIndexProvider; import com.android.settings.search.Indexable; import com.android.settings.widget.EntityHeaderController; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.core.AbstractPreferenceController; import com.android.settingslib.deviceinfo.PrivateStorageInfo; @@ -185,8 +184,7 @@ public class StorageDashboardFragment extends DashboardFragment mVolume, new StorageManagerVolumeProvider(sm)); controllers.add(mPreferenceController); - UserManagerWrapper userManager = - new UserManagerWrapper(context.getSystemService(UserManager.class)); + final UserManager userManager = context.getSystemService(UserManager.class); mSecondaryUsers = SecondaryUserController.getSecondaryUserControllers(context, userManager); controllers.addAll(mSecondaryUsers); @@ -235,8 +233,7 @@ public class StorageDashboardFragment extends DashboardFragment public List createPreferenceControllers( Context context) { final StorageManager sm = context.getSystemService(StorageManager.class); - final UserManagerWrapper userManager = - new UserManagerWrapper(context.getSystemService(UserManager.class)); + final UserManager userManager = context.getSystemService(UserManager.class); final List controllers = new ArrayList<>(); controllers.add(new StorageSummaryDonutPreferenceController(context)); controllers.add(new StorageItemPreferenceController(context, null /* host */, @@ -251,9 +248,8 @@ public class StorageDashboardFragment extends DashboardFragment @Override public Loader> onCreateLoader(int id, Bundle args) { - Context context = getContext(); - return new StorageAsyncLoader(context, - new UserManagerWrapper(context.getSystemService(UserManager.class)), + final Context context = getContext(); + return new StorageAsyncLoader(context, context.getSystemService(UserManager.class), mVolume.fsUuid, new StorageStatsSource(context), new PackageManagerWrapper(context.getPackageManager())); diff --git a/src/com/android/settings/deviceinfo/StorageProfileFragment.java b/src/com/android/settings/deviceinfo/StorageProfileFragment.java index 3f75f5c6472..a312a818394 100644 --- a/src/com/android/settings/deviceinfo/StorageProfileFragment.java +++ b/src/com/android/settings/deviceinfo/StorageProfileFragment.java @@ -34,7 +34,6 @@ import com.android.settings.dashboard.DashboardFragment; import com.android.settings.deviceinfo.storage.StorageAsyncLoader; import com.android.settings.deviceinfo.storage.StorageAsyncLoader.AppsStorageResult; import com.android.settings.deviceinfo.storage.StorageItemPreferenceController; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.core.AbstractPreferenceController; import com.android.settingslib.deviceinfo.StorageManagerVolumeProvider; @@ -114,9 +113,9 @@ public class StorageProfileFragment extends DashboardFragment @Override public Loader> onCreateLoader(int id, Bundle args) { - Context context = getContext(); + final Context context = getContext(); return new StorageAsyncLoader(context, - new UserManagerWrapper(context.getSystemService(UserManager.class)), + context.getSystemService(UserManager.class), mVolume.fsUuid, new StorageStatsSource(context), new PackageManagerWrapper(context.getPackageManager())); diff --git a/src/com/android/settings/deviceinfo/storage/SecondaryUserController.java b/src/com/android/settings/deviceinfo/storage/SecondaryUserController.java index 4aeb78299bf..d63436f483e 100644 --- a/src/com/android/settings/deviceinfo/storage/SecondaryUserController.java +++ b/src/com/android/settings/deviceinfo/storage/SecondaryUserController.java @@ -19,6 +19,7 @@ package com.android.settings.deviceinfo.storage; import android.content.Context; import android.content.pm.UserInfo; import android.graphics.drawable.Drawable; +import android.os.UserManager; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.support.annotation.VisibleForTesting; @@ -29,7 +30,6 @@ import android.util.SparseArray; import com.android.settings.Utils; import com.android.settings.core.PreferenceControllerMixin; import com.android.settings.deviceinfo.StorageItemPreference; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.core.AbstractPreferenceController; import java.util.ArrayList; @@ -61,7 +61,7 @@ public class SecondaryUserController extends AbstractPreferenceController implem * @param userManager UserManagerWrapper for figuring out which controllers to add. */ public static List getSecondaryUserControllers( - Context context, UserManagerWrapper userManager) { + Context context, UserManager userManager) { List controllers = new ArrayList<>(); UserInfo primaryUser = userManager.getPrimaryUser(); boolean addedUser = false; @@ -74,8 +74,7 @@ public class SecondaryUserController extends AbstractPreferenceController implem if (info == null || Utils.isProfileOf(primaryUser, info)) { controllers.add( - new UserProfileController( - context, info, userManager, USER_PROFILE_INSERTION_LOCATION)); + new UserProfileController(context, info, USER_PROFILE_INSERTION_LOCATION)); continue; } diff --git a/src/com/android/settings/deviceinfo/storage/StorageAsyncLoader.java b/src/com/android/settings/deviceinfo/storage/StorageAsyncLoader.java index 0b9b697f473..affcbc9c1a1 100644 --- a/src/com/android/settings/deviceinfo/storage/StorageAsyncLoader.java +++ b/src/com/android/settings/deviceinfo/storage/StorageAsyncLoader.java @@ -26,11 +26,11 @@ import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager.NameNotFoundException; import android.content.pm.UserInfo; import android.os.UserHandle; +import android.os.UserManager; import android.util.ArraySet; import android.util.Log; import android.util.SparseArray; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.utils.AsyncLoader; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -46,7 +46,7 @@ import java.util.List; */ public class StorageAsyncLoader extends AsyncLoader> { - private UserManagerWrapper mUserManager; + private UserManager mUserManager; private static final String TAG = "StorageAsyncLoader"; private String mUuid; @@ -54,7 +54,7 @@ public class StorageAsyncLoader private PackageManagerWrapper mPackageManager; private ArraySet mSeenPackages; - public StorageAsyncLoader(Context context, UserManagerWrapper userManager, + public StorageAsyncLoader(Context context, UserManager userManager, String uuid, StorageStatsSource source, PackageManagerWrapper pm) { super(context); mUserManager = userManager; diff --git a/src/com/android/settings/deviceinfo/storage/UserProfileController.java b/src/com/android/settings/deviceinfo/storage/UserProfileController.java index 081a0be0771..510b0c0390e 100644 --- a/src/com/android/settings/deviceinfo/storage/UserProfileController.java +++ b/src/com/android/settings/deviceinfo/storage/UserProfileController.java @@ -32,7 +32,6 @@ import com.android.settings.core.PreferenceControllerMixin; import com.android.settings.core.SubSettingLauncher; import com.android.settings.deviceinfo.StorageItemPreference; import com.android.settings.deviceinfo.StorageProfileFragment; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.core.AbstractPreferenceController; /** @@ -44,16 +43,13 @@ public class UserProfileController extends AbstractPreferenceController implemen UserIconLoader.UserIconHandler { private static final String PREFERENCE_KEY_BASE = "pref_profile_"; private StorageItemPreference mStoragePreference; - private UserManagerWrapper mUserManager; private UserInfo mUser; private long mTotalSizeBytes; private final int mPreferenceOrder; - public UserProfileController( - Context context, UserInfo info, UserManagerWrapper userManager, int preferenceOrder) { + public UserProfileController(Context context, UserInfo info, int preferenceOrder) { super(context); mUser = Preconditions.checkNotNull(info); - mUserManager = userManager; mPreferenceOrder = preferenceOrder; } diff --git a/src/com/android/settings/display/TimeoutPreferenceController.java b/src/com/android/settings/display/TimeoutPreferenceController.java index 84f9641c5fa..07146f9a1d3 100644 --- a/src/com/android/settings/display/TimeoutPreferenceController.java +++ b/src/com/android/settings/display/TimeoutPreferenceController.java @@ -15,6 +15,7 @@ package com.android.settings.display; import static android.provider.Settings.System.SCREEN_OFF_TIMEOUT; +import android.app.admin.DevicePolicyManager; import android.content.Context; import android.os.UserHandle; import android.os.UserManager; @@ -25,7 +26,6 @@ import android.util.Log; import com.android.settings.R; import com.android.settings.TimeoutListPreference; import com.android.settings.core.PreferenceControllerMixin; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.RestrictedLockUtils.EnforcedAdmin; import com.android.settingslib.core.AbstractPreferenceController; @@ -61,7 +61,8 @@ public class TimeoutPreferenceController extends AbstractPreferenceController im final long currentTimeout = Settings.System.getLong(mContext.getContentResolver(), SCREEN_OFF_TIMEOUT, FALLBACK_SCREEN_TIMEOUT_VALUE); timeoutListPreference.setValue(String.valueOf(currentTimeout)); - final DevicePolicyManagerWrapper dpm = DevicePolicyManagerWrapper.from(mContext); + final DevicePolicyManager dpm = + (DevicePolicyManager) mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); if (dpm != null) { final RestrictedLockUtils.EnforcedAdmin admin = RestrictedLockUtils.checkIfMaximumTimeToLockIsSet(mContext); diff --git a/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java b/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java index 8876d2556fb..17d7f0dcb0c 100644 --- a/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java +++ b/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java @@ -16,6 +16,7 @@ package com.android.settings.enterprise; +import android.app.admin.DevicePolicyManager; import android.content.ComponentName; import android.content.Context; import android.content.Intent; @@ -32,7 +33,6 @@ import android.view.View; import com.android.settings.R; import com.android.settings.vpn2.VpnUtils; import com.android.settings.wrapper.ConnectivityManagerWrapper; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; import java.util.Date; @@ -41,7 +41,7 @@ import java.util.List; public class EnterprisePrivacyFeatureProviderImpl implements EnterprisePrivacyFeatureProvider { private final Context mContext; - private final DevicePolicyManagerWrapper mDpm; + private final DevicePolicyManager mDpm; private final PackageManagerWrapper mPm; private final UserManager mUm; private final ConnectivityManagerWrapper mCm; @@ -49,7 +49,7 @@ public class EnterprisePrivacyFeatureProviderImpl implements EnterprisePrivacyFe private static final int MY_USER_ID = UserHandle.myUserId(); - public EnterprisePrivacyFeatureProviderImpl(Context context, DevicePolicyManagerWrapper dpm, + public EnterprisePrivacyFeatureProviderImpl(Context context, DevicePolicyManager dpm, PackageManagerWrapper pm, UserManager um, ConnectivityManagerWrapper cm, Resources resources) { mContext = context.getApplicationContext(); diff --git a/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java b/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java index 1ecb2a86cf7..0c82faa0e66 100644 --- a/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java +++ b/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java @@ -54,7 +54,6 @@ import com.android.settings.fuelgauge.anomaly.AnomalyUtils; import com.android.settings.fuelgauge.batterytip.BatteryTipPreferenceController; import com.android.settings.fuelgauge.batterytip.tips.BatteryTip; import com.android.settings.widget.EntityHeaderController; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState; import com.android.settingslib.core.AbstractPreferenceController; @@ -116,7 +115,7 @@ public class AdvancedPowerUsageDetail extends DashboardFragment implements private AppButtonsPreferenceController mAppButtonsPreferenceController; private BackgroundActivityPreferenceController mBackgroundActivityPreferenceController; - private DevicePolicyManagerWrapper mDpm; + private DevicePolicyManager mDpm; private UserManager mUserManager; private PackageManager mPackageManager; private List mAnomalies; @@ -167,7 +166,8 @@ public class AdvancedPowerUsageDetail extends DashboardFragment implements .launch(); } - private static @UserIdInt int getUserIdToLaunchAdvancePowerUsageDetail(BatterySipper bs) { + private static @UserIdInt + int getUserIdToLaunchAdvancePowerUsageDetail(BatterySipper bs) { if (bs.drainType == BatterySipper.DrainType.USER) { return ActivityManager.getCurrentUser(); } @@ -206,8 +206,7 @@ public class AdvancedPowerUsageDetail extends DashboardFragment implements super.onAttach(activity); mState = ApplicationsState.getInstance(getActivity().getApplication()); - mDpm = new DevicePolicyManagerWrapper( - (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE)); + mDpm = (DevicePolicyManager) activity.getSystemService(Context.DEVICE_POLICY_SERVICE); mUserManager = (UserManager) activity.getSystemService(Context.USER_SERVICE); mPackageManager = activity.getPackageManager(); mBatteryUtils = BatteryUtils.getInstance(getContext()); diff --git a/src/com/android/settings/fuelgauge/AppButtonsPreferenceController.java b/src/com/android/settings/fuelgauge/AppButtonsPreferenceController.java index 854b855a2c3..8c4b4d88b2c 100644 --- a/src/com/android/settings/fuelgauge/AppButtonsPreferenceController.java +++ b/src/com/android/settings/fuelgauge/AppButtonsPreferenceController.java @@ -19,6 +19,7 @@ package com.android.settings.fuelgauge; import android.app.Activity; import android.app.ActivityManager; import android.app.Fragment; +import android.app.admin.DevicePolicyManager; import android.content.BroadcastReceiver; import android.content.ComponentName; import android.content.Context; @@ -50,7 +51,6 @@ import com.android.settings.Utils; import com.android.settings.core.PreferenceControllerMixin; import com.android.settings.overlay.FeatureFactory; import com.android.settings.widget.ActionButtonPreference; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState; @@ -102,7 +102,7 @@ public class AppButtonsPreferenceController extends AbstractPreferenceController private final int mRequestRemoveDeviceAdmin; private ApplicationsState.Session mSession; - private DevicePolicyManagerWrapper mDpm; + private DevicePolicyManager mDpm; private UserManager mUserManager; private PackageManager mPm; private SettingsActivity mActivity; @@ -118,7 +118,7 @@ public class AppButtonsPreferenceController extends AbstractPreferenceController public AppButtonsPreferenceController(SettingsActivity activity, Fragment fragment, Lifecycle lifecycle, String packageName, ApplicationsState state, - DevicePolicyManagerWrapper dpm, UserManager userManager, + DevicePolicyManager dpm, UserManager userManager, PackageManager packageManager, int requestUninstall, int requestRemoveDeviceAdmin) { super(activity); @@ -477,7 +477,7 @@ public class AppButtonsPreferenceController extends AbstractPreferenceController } else { Intent intent = new Intent(Intent.ACTION_QUERY_PACKAGE_RESTART, Uri.fromParts("package", mAppEntry.info.packageName, null)); - intent.putExtra(Intent.EXTRA_PACKAGES, new String[]{mAppEntry.info.packageName}); + intent.putExtra(Intent.EXTRA_PACKAGES, new String[] {mAppEntry.info.packageName}); intent.putExtra(Intent.EXTRA_UID, mAppEntry.info.uid); intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(mAppEntry.info.uid)); Log.d(TAG, "Sending broadcast to query restart status for " diff --git a/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceController.java b/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceController.java index c117b9a22da..3675a8392e9 100644 --- a/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceController.java +++ b/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceController.java @@ -30,7 +30,6 @@ import com.android.settings.fuelgauge.batterytip.BatteryTipDialogFragment; import com.android.settings.fuelgauge.batterytip.tips.BatteryTip; import com.android.settings.fuelgauge.batterytip.tips.RestrictAppTip; import com.android.settings.fuelgauge.batterytip.tips.UnrestrictAppTip; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.core.AbstractPreferenceController; import com.android.settingslib.fuelgauge.PowerWhitelistBackend; @@ -48,7 +47,7 @@ public class BackgroundActivityPreferenceController extends AbstractPreferenceCo private final UserManager mUserManager; private final int mUid; @VisibleForTesting - DevicePolicyManagerWrapper mDpm; + DevicePolicyManager mDpm; @VisibleForTesting BatteryUtils mBatteryUtils; private InstrumentedPreferenceFragment mFragment; @@ -66,8 +65,7 @@ public class BackgroundActivityPreferenceController extends AbstractPreferenceCo super(context); mPowerWhitelistBackend = backend; mUserManager = (UserManager) context.getSystemService(Context.USER_SERVICE); - mDpm = new DevicePolicyManagerWrapper( - (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE)); + mDpm = (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); mAppOpsManager = (AppOpsManager) context.getSystemService(Context.APP_OPS_SERVICE); mUid = uid; mFragment = fragment; diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobService.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobService.java index 46744f7e7a0..9e57433bcb7 100644 --- a/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobService.java +++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobService.java @@ -42,12 +42,17 @@ public class AnomalyCleanupJobService extends JobService { final ComponentName component = new ComponentName(context, AnomalyCleanupJobService.class); final JobInfo.Builder jobBuilder = - new JobInfo.Builder(R.id.job_anomaly_clean_up, component) + new JobInfo.Builder(R.integer.job_anomaly_clean_up, component) .setPeriodic(CLEAN_UP_FREQUENCY_MS) .setRequiresDeviceIdle(true) - .setRequiresCharging(true); + .setRequiresCharging(true) + .setPersisted(true); + final JobInfo pending = jobScheduler.getPendingJob(R.integer.job_anomaly_clean_up); - if (jobScheduler.schedule(jobBuilder.build()) != JobScheduler.RESULT_SUCCESS) { + // Don't schedule it if it already exists, to make sure it runs periodically even after + // reboot + if (pending == null && jobScheduler.schedule(jobBuilder.build()) + != JobScheduler.RESULT_SUCCESS) { Log.i(TAG, "Anomaly clean up job service schedule failed."); } } diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java index 1a650880eac..98eb23e3632 100644 --- a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java +++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java @@ -52,12 +52,17 @@ public class AnomalyConfigJobService extends JobService { final ComponentName component = new ComponentName(context, AnomalyConfigJobService.class); final JobInfo.Builder jobBuilder = - new JobInfo.Builder(R.id.job_anomaly_config_update, component) + new JobInfo.Builder(R.integer.job_anomaly_config_update, component) .setPeriodic(CONFIG_UPDATE_FREQUENCY_MS) .setRequiresDeviceIdle(true) - .setRequiresCharging(true); + .setRequiresCharging(true) + .setPersisted(true); + final JobInfo pending = jobScheduler.getPendingJob(R.integer.job_anomaly_config_update); - if (jobScheduler.schedule(jobBuilder.build()) != JobScheduler.RESULT_SUCCESS) { + // Don't schedule it if it already exists, to make sure it runs periodically even after + // reboot + if (pending == null && jobScheduler.schedule(jobBuilder.build()) + != JobScheduler.RESULT_SUCCESS) { Log.i(TAG, "Anomaly config update job service schedule failed."); } } diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java index a12d31e5a2c..52555783df8 100644 --- a/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java +++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java @@ -70,7 +70,7 @@ public class AnomalyDetectionJobService extends JobService { final ComponentName component = new ComponentName(context, AnomalyDetectionJobService.class); final JobInfo.Builder jobBuilder = - new JobInfo.Builder(R.id.job_anomaly_detection, component) + new JobInfo.Builder(R.integer.job_anomaly_detection, component) .setOverrideDeadline(MAX_DELAY_MS); if (jobScheduler.enqueue(jobBuilder.build(), new JobWorkItem(intent)) diff --git a/src/com/android/settings/network/NetworkDashboardFragment.java b/src/com/android/settings/network/NetworkDashboardFragment.java index 7d8ea18c7a4..955c50390ee 100644 --- a/src/com/android/settings/network/NetworkDashboardFragment.java +++ b/src/com/android/settings/network/NetworkDashboardFragment.java @@ -49,10 +49,8 @@ public class NetworkDashboardFragment extends DashboardFragment implements private static final String TAG = "NetworkDashboardFrag"; private static final int MENU_NETWORK_RESET = Menu.FIRST; - private static final int MENU_PRIVATE_DNS = Menu.FIRST + 1; private NetworkResetActionMenuController mNetworkResetController; - private PrivateDnsMenuController mPrivateDnsMenuController; @Override public int getMetricsCategory() { @@ -73,8 +71,6 @@ public class NetworkDashboardFragment extends DashboardFragment implements public void onAttach(Context context) { super.onAttach(context); mNetworkResetController = new NetworkResetActionMenuController(context, MENU_NETWORK_RESET); - mPrivateDnsMenuController = new PrivateDnsMenuController(getFragmentManager(), - MENU_PRIVATE_DNS); } @Override @@ -86,7 +82,6 @@ public class NetworkDashboardFragment extends DashboardFragment implements public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { super.onCreateOptionsMenu(menu, inflater); mNetworkResetController.buildMenuItem(menu); - mPrivateDnsMenuController.buildMenuItem(menu); } @Override @@ -109,6 +104,8 @@ public class NetworkDashboardFragment extends DashboardFragment implements new MobileNetworkPreferenceController(context); final VpnPreferenceController vpnPreferenceController = new VpnPreferenceController(context); + final PrivateDnsPreferenceController privateDnsPreferenceController = + new PrivateDnsPreferenceController(context); if (lifecycle != null) { lifecycle.addObserver(airplaneModePreferenceController); @@ -116,6 +113,7 @@ public class NetworkDashboardFragment extends DashboardFragment implements lifecycle.addObserver(wifiPreferenceController); lifecycle.addObserver(mobileNetworkPreferenceController); lifecycle.addObserver(vpnPreferenceController); + lifecycle.addObserver(privateDnsPreferenceController); } final List controllers = new ArrayList<>(); @@ -126,6 +124,7 @@ public class NetworkDashboardFragment extends DashboardFragment implements controllers.add(new ProxyPreferenceController(context)); controllers.add(mobilePlanPreferenceController); controllers.add(wifiPreferenceController); + controllers.add(privateDnsPreferenceController); return controllers; } diff --git a/src/com/android/settings/network/PrivateDnsModeDialogFragment.java b/src/com/android/settings/network/PrivateDnsModeDialogPreference.java similarity index 71% rename from src/com/android/settings/network/PrivateDnsModeDialogFragment.java rename to src/com/android/settings/network/PrivateDnsModeDialogPreference.java index 00950c3adc7..3b09cc2e560 100644 --- a/src/com/android/settings/network/PrivateDnsModeDialogFragment.java +++ b/src/com/android/settings/network/PrivateDnsModeDialogPreference.java @@ -20,19 +20,18 @@ import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC; import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_PROVIDER_HOSTNAME; import android.app.AlertDialog; -import android.app.Dialog; -import android.app.FragmentManager; +import android.content.ActivityNotFoundException; import android.content.ContentResolver; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; -import android.os.Bundle; import android.provider.Settings; import android.support.annotation.VisibleForTesting; import android.text.Editable; import android.text.TextWatcher; import android.text.method.LinkMovementMethod; -import android.view.LayoutInflater; +import android.util.AttributeSet; +import android.util.Log; import android.view.View; import android.widget.Button; import android.widget.EditText; @@ -41,8 +40,9 @@ import android.widget.TextView; import com.android.internal.logging.nano.MetricsProto; import com.android.settings.R; -import com.android.settings.core.instrumentation.InstrumentedDialogFragment; +import com.android.settings.overlay.FeatureFactory; import com.android.settings.utils.AnnotationSpan; +import com.android.settingslib.CustomDialogPreference; import com.android.settingslib.HelpUtils; import java.util.HashMap; @@ -51,7 +51,7 @@ import java.util.Map; /** * Dialog to set the private dns */ -public class PrivateDnsModeDialogFragment extends InstrumentedDialogFragment implements +public class PrivateDnsModeDialogPreference extends CustomDialogPreference implements DialogInterface.OnClickListener, RadioGroup.OnCheckedChangeListener, TextWatcher { public static final String ANNOTATION_URL = "url"; @@ -77,41 +77,44 @@ public class PrivateDnsModeDialogFragment extends InstrumentedDialogFragment imp @VisibleForTesting RadioGroup mRadioGroup; @VisibleForTesting - Button mSaveButton; - @VisibleForTesting String mMode; - public static void show(FragmentManager fragmentManager) { - if (fragmentManager.findFragmentByTag(TAG) == null) { - final PrivateDnsModeDialogFragment fragment = new PrivateDnsModeDialogFragment(); - fragment.show(fragmentManager, TAG); - } + public PrivateDnsModeDialogPreference(Context context) { + super(context); } + public PrivateDnsModeDialogPreference(Context context, AttributeSet attrs) { + super(context, attrs); + } + + public PrivateDnsModeDialogPreference(Context context, AttributeSet attrs, int defStyleAttr) { + super(context, attrs, defStyleAttr); + } + + public PrivateDnsModeDialogPreference(Context context, AttributeSet attrs, int defStyleAttr, + int defStyleRes) { + super(context, attrs, defStyleAttr, defStyleRes); + } + + private final AnnotationSpan.LinkInfo mUrlLinkInfo = new AnnotationSpan.LinkInfo( + ANNOTATION_URL, (widget) -> { + final Context context = widget.getContext(); + final Intent intent = HelpUtils.getHelpIntent(context, + context.getString(R.string.help_uri_private_dns), + context.getClass().getName()); + if (intent != null) { + try { + widget.startActivityForResult(intent, 0); + } catch (ActivityNotFoundException e) { + Log.w(TAG, "Activity was not found for intent, " + intent.toString()); + } + } + }); + @Override - public Dialog onCreateDialog(Bundle savedInstanceState) { + protected void onBindDialogView(View view) { final Context context = getContext(); - - final AlertDialog dialog = new AlertDialog.Builder(context) - .setTitle(R.string.select_private_dns_configuration_title) - .setView(buildPrivateDnsView(context)) - .setPositiveButton(R.string.save, this) - .setNegativeButton(R.string.dlg_cancel, null) - .create(); - - dialog.setOnShowListener(dialogInterface -> { - mSaveButton = dialog.getButton(DialogInterface.BUTTON_POSITIVE); - updateDialogInfo(); - }); - return dialog; - } - - private View buildPrivateDnsView(final Context context) { final ContentResolver contentResolver = context.getContentResolver(); - mMode = Settings.Global.getString(contentResolver, MODE_KEY); - final View view = LayoutInflater.from(context).inflate(R.layout.private_dns_mode_dialog, - null); - mEditText = view.findViewById(R.id.private_dns_mode_provider_hostname); mEditText.addTextChangedListener(this); mEditText.setText(Settings.Global.getString(contentResolver, HOSTNAME_KEY)); @@ -131,26 +134,20 @@ public class PrivateDnsModeDialogFragment extends InstrumentedDialogFragment imp helpTextView.setText(AnnotationSpan.linkify( context.getText(R.string.private_dns_help_message), linkInfo)); } - - return view; } @Override public void onClick(DialogInterface dialog, int which) { + final Context context = getContext(); if (mMode.equals(PRIVATE_DNS_MODE_PROVIDER_HOSTNAME)) { // Only clickable if hostname is valid, so we could save it safely - Settings.Global.putString(getContext().getContentResolver(), HOSTNAME_KEY, + Settings.Global.putString(context.getContentResolver(), HOSTNAME_KEY, mEditText.getText().toString()); } - mMetricsFeatureProvider.action(getContext(), + FeatureFactory.getFactory(context).getMetricsFeatureProvider().action(context, MetricsProto.MetricsEvent.ACTION_PRIVATE_DNS_MODE, mMode); - Settings.Global.putString(getContext().getContentResolver(), MODE_KEY, mMode); - } - - @Override - public int getMetricsCategory() { - return MetricsProto.MetricsEvent.DIALOG_PRIVATE_DNS; + Settings.Global.putString(context.getContentResolver(), MODE_KEY, mMode); } @Override @@ -179,9 +176,7 @@ public class PrivateDnsModeDialogFragment extends InstrumentedDialogFragment imp @Override public void afterTextChanged(Editable s) { - if (mSaveButton != null) { - mSaveButton.setEnabled(isWeaklyValidatedHostname(mEditText.getText().toString())); - } + updateDialogInfo(); } private boolean isWeaklyValidatedHostname(String hostname) { @@ -193,17 +188,24 @@ public class PrivateDnsModeDialogFragment extends InstrumentedDialogFragment imp return hostname.matches(WEAK_HOSTNAME_REGEX); } + private Button getSaveButton() { + final AlertDialog dialog = (AlertDialog) getDialog(); + if (dialog == null) { + return null; + } + return dialog.getButton(DialogInterface.BUTTON_POSITIVE); + } + private void updateDialogInfo() { final boolean modeProvider = PRIVATE_DNS_MODE_PROVIDER_HOSTNAME.equals(mMode); if (mEditText != null) { mEditText.setEnabled(modeProvider); } - if (mSaveButton != null) { - mSaveButton.setEnabled( - modeProvider - ? isWeaklyValidatedHostname(mEditText.getText().toString()) - : true); + final Button saveButton = getSaveButton(); + if (saveButton != null) { + saveButton.setEnabled(modeProvider + ? isWeaklyValidatedHostname(mEditText.getText().toString()) + : true); } } - } diff --git a/src/com/android/settings/network/PrivateDnsMenuController.java b/src/com/android/settings/network/PrivateDnsPreferenceController.java similarity index 50% rename from src/com/android/settings/network/PrivateDnsMenuController.java rename to src/com/android/settings/network/PrivateDnsPreferenceController.java index a8117755565..e3175300792 100644 --- a/src/com/android/settings/network/PrivateDnsMenuController.java +++ b/src/com/android/settings/network/PrivateDnsPreferenceController.java @@ -16,29 +16,28 @@ package com.android.settings.network; -import android.app.FragmentManager; -import android.view.Menu; -import android.view.MenuItem; +import android.content.Context; import com.android.settings.R; +import com.android.settings.core.BasePreferenceController; +import com.android.settings.core.PreferenceControllerMixin; +import com.android.settingslib.core.lifecycle.LifecycleObserver; -public class PrivateDnsMenuController { - private final FragmentManager mFragmentManager; - private final int mMenuId; +public class PrivateDnsPreferenceController extends BasePreferenceController + implements PreferenceControllerMixin, LifecycleObserver { + private static final String KEY_PRIVATE_DNS_SETTINGS = "private_dns_settings"; - public PrivateDnsMenuController(FragmentManager fragmentManager, int menuId) { - mFragmentManager = fragmentManager; - mMenuId = menuId; + public PrivateDnsPreferenceController(Context context) { + super(context, KEY_PRIVATE_DNS_SETTINGS); } - public void buildMenuItem(Menu menu) { - if (menu != null) { - MenuItem item = menu.add(0 /* groupId */, mMenuId, 0 /* order */, - R.string.select_private_dns_configuration_title); - item.setOnMenuItemClickListener(target -> { - PrivateDnsModeDialogFragment.show(mFragmentManager); - return true; - }); - } + @Override + public String getPreferenceKey() { + return KEY_PRIVATE_DNS_SETTINGS; + } + + @Override + public int getAvailabilityStatus() { + return AVAILABLE; } } diff --git a/src/com/android/settings/network/VpnPreferenceController.java b/src/com/android/settings/network/VpnPreferenceController.java index 95513e08624..c4ecf4f7111 100644 --- a/src/com/android/settings/network/VpnPreferenceController.java +++ b/src/com/android/settings/network/VpnPreferenceController.java @@ -180,13 +180,11 @@ public class VpnPreferenceController extends AbstractPreferenceController mNetworkCallback = new ConnectivityManager.NetworkCallback() { @Override public void onAvailable(Network network) { - Log.d(TAG, "onAvailable " + network.netId); updateSummary(); } @Override public void onLost(Network network) { - Log.d(TAG, "onLost " + network.netId); updateSummary(); } }; diff --git a/src/com/android/settings/overlay/FeatureFactoryImpl.java b/src/com/android/settings/overlay/FeatureFactoryImpl.java index c521eb80d53..f0bbe2e646d 100644 --- a/src/com/android/settings/overlay/FeatureFactoryImpl.java +++ b/src/com/android/settings/overlay/FeatureFactoryImpl.java @@ -52,7 +52,6 @@ import com.android.settings.slices.SlicesFeatureProviderImpl; import com.android.settings.users.UserFeatureProvider; import com.android.settings.users.UserFeatureProviderImpl; import com.android.settings.wrapper.ConnectivityManagerWrapper; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.core.instrumentation.MetricsFeatureProvider; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -114,8 +113,8 @@ public class FeatureFactoryImpl extends FeatureFactory { mApplicationFeatureProvider = new ApplicationFeatureProviderImpl(context, new PackageManagerWrapper(context.getPackageManager()), new IPackageManagerWrapper(AppGlobals.getPackageManager()), - new DevicePolicyManagerWrapper((DevicePolicyManager) context - .getSystemService(Context.DEVICE_POLICY_SERVICE))); + (DevicePolicyManager) context + .getSystemService(Context.DEVICE_POLICY_SERVICE)); } return mApplicationFeatureProvider; } @@ -132,8 +131,7 @@ public class FeatureFactoryImpl extends FeatureFactory { public EnterprisePrivacyFeatureProvider getEnterprisePrivacyFeatureProvider(Context context) { if (mEnterprisePrivacyFeatureProvider == null) { mEnterprisePrivacyFeatureProvider = new EnterprisePrivacyFeatureProviderImpl(context, - new DevicePolicyManagerWrapper((DevicePolicyManager) context - .getSystemService(Context.DEVICE_POLICY_SERVICE)), + (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE), new PackageManagerWrapper(context.getPackageManager()), UserManager.get(context), new ConnectivityManagerWrapper((ConnectivityManager) context diff --git a/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceController.java b/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceController.java index 08e244e3450..71a33f7d91c 100644 --- a/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceController.java +++ b/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceController.java @@ -32,7 +32,6 @@ import com.android.settings.TimeoutListPreference; import com.android.settings.core.PreferenceControllerMixin; import com.android.settings.overlay.FeatureFactory; import com.android.settings.security.trustagent.TrustAgentManager; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.RestrictedLockUtils; import com.android.settingslib.core.AbstractPreferenceController; @@ -44,14 +43,14 @@ public class LockAfterTimeoutPreferenceController extends AbstractPreferenceCont private final int mUserId; private final LockPatternUtils mLockPatternUtils; private final TrustAgentManager mTrustAgentManager; - private final DevicePolicyManagerWrapper mDPM; + private final DevicePolicyManager mDPM; public LockAfterTimeoutPreferenceController(Context context, int userId, LockPatternUtils lockPatternUtils) { super(context); mUserId = userId; mLockPatternUtils = lockPatternUtils; - mDPM = DevicePolicyManagerWrapper.from(context); + mDPM = (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); mTrustAgentManager = FeatureFactory.getFactory(context) .getSecurityFeatureProvider().getTrustAgentManager(); } diff --git a/src/com/android/settings/wallpaper/WallpaperSuggestionActivity.java b/src/com/android/settings/wallpaper/WallpaperSuggestionActivity.java index 0874ceaecc2..22835f3fce3 100644 --- a/src/com/android/settings/wallpaper/WallpaperSuggestionActivity.java +++ b/src/com/android/settings/wallpaper/WallpaperSuggestionActivity.java @@ -27,7 +27,6 @@ import android.support.annotation.VisibleForTesting; import com.android.internal.logging.nano.MetricsProto; import com.android.settings.R; import com.android.settings.core.SubSettingLauncher; -import com.android.settings.wrapper.WallpaperManagerWrapper; public class WallpaperSuggestionActivity extends Activity { @@ -61,9 +60,16 @@ public class WallpaperSuggestionActivity extends Activity { @VisibleForTesting public static boolean isSuggestionComplete(Context context) { - final WallpaperManagerWrapper manager = new WallpaperManagerWrapper(context); - return manager.isWallpaperServiceEnabled() ? manager.getWallpaperId( - WallpaperManager.FLAG_SYSTEM) > 0 : false; + if (!isWallpaperServiceEnabled(context)) { + return true; + } + final WallpaperManager manager = (WallpaperManager) context.getSystemService( + WALLPAPER_SERVICE); + return manager.getWallpaperId(WallpaperManager.FLAG_SYSTEM) > 0; } + private static boolean isWallpaperServiceEnabled(Context context) { + return context.getResources().getBoolean( + com.android.internal.R.bool.config_enableWallpaperService); + } } diff --git a/src/com/android/settings/widget/PreferenceCategoryController.java b/src/com/android/settings/widget/PreferenceCategoryController.java index cdd814c1d8f..c6477f3b321 100644 --- a/src/com/android/settings/widget/PreferenceCategoryController.java +++ b/src/com/android/settings/widget/PreferenceCategoryController.java @@ -43,7 +43,7 @@ public class PreferenceCategoryController extends BasePreferenceController { @Override public int getAvailabilityStatus() { if (mChildren == null || mChildren.isEmpty()) { - return DISABLED_DEPENDENT_SETTING; + return DISABLED_UNSUPPORTED; } // Category is available if any child is available for (AbstractPreferenceController controller : mChildren) { @@ -51,7 +51,7 @@ public class PreferenceCategoryController extends BasePreferenceController { return AVAILABLE; } } - return DISABLED_DEPENDENT_SETTING; + return DISABLED_UNSUPPORTED; } @Override diff --git a/src/com/android/settings/wifi/WifiUtils.java b/src/com/android/settings/wifi/WifiUtils.java index 5ef66c046d3..0477280c8e0 100644 --- a/src/com/android/settings/wifi/WifiUtils.java +++ b/src/com/android/settings/wifi/WifiUtils.java @@ -16,6 +16,7 @@ package com.android.settings.wifi; +import android.app.admin.DevicePolicyManager; import android.content.ComponentName; import android.content.ContentResolver; import android.content.Context; @@ -25,7 +26,6 @@ import android.net.wifi.WifiConfiguration; import android.provider.Settings; import android.text.TextUtils; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; public class WifiUtils { @@ -69,7 +69,8 @@ public class WifiUtils { return false; } - final DevicePolicyManagerWrapper dpm = DevicePolicyManagerWrapper.from(context); + final DevicePolicyManager dpm = + (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); final PackageManagerWrapper pm = new PackageManagerWrapper(context.getPackageManager()); // Check if device has DPM capability. If it has and dpm is still null, then we diff --git a/src/com/android/settings/wrapper/DevicePolicyManagerWrapper.java b/src/com/android/settings/wrapper/DevicePolicyManagerWrapper.java deleted file mode 100644 index ccf6c53d082..00000000000 --- a/src/com/android/settings/wrapper/DevicePolicyManagerWrapper.java +++ /dev/null @@ -1,229 +0,0 @@ -/* - * Copyright (C) 2016 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.annotation.NonNull; -import android.annotation.Nullable; -import android.annotation.UserIdInt; -import android.app.admin.DevicePolicyManager; -import android.content.ComponentName; -import android.content.Context; -import android.content.Intent; -import android.os.UserHandle; - -import java.util.List; - -/** - * This class replicates a subset of the android.app.admin.DevicePolicyManager (DPM). The - * class exists so that we can use a thin wrapper around the DPM in production code and a mock - * in tests. We cannot directly mock or shadow the DPM, because some of the methods we rely on are - * newer than the API version supported by Robolectric. - */ -public class DevicePolicyManagerWrapper { - private final DevicePolicyManager mDpm; - - public DevicePolicyManagerWrapper(DevicePolicyManager dpm) { - mDpm = dpm; - } - - public static @Nullable DevicePolicyManagerWrapper from(Context context) { - DevicePolicyManager dpm = - (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE); - return dpm == null ? null : new DevicePolicyManagerWrapper(dpm); - } - - /** - * Calls {@code DevicePolicyManager.getActiveAdminsAsUser()}. - * - * @see DevicePolicyManager#getActiveAdminsAsUser - */ - public @Nullable List getActiveAdminsAsUser(int userId) { - return mDpm.getActiveAdminsAsUser(userId); - } - - /** - * Calls {@code DevicePolicyManager.getMaximumFailedPasswordsForWipe()}. - * - * @see DevicePolicyManager#getMaximumFailedPasswordsForWipe - */ - public int getMaximumFailedPasswordsForWipe(@Nullable ComponentName admin, int userHandle) { - return mDpm.getMaximumFailedPasswordsForWipe(admin, userHandle); - } - - /** - * Calls {@code DevicePolicyManager.getDeviceOwnerComponentOnCallingUser()}. - * - * @see DevicePolicyManager#getDeviceOwnerComponentOnCallingUser - */ - public ComponentName getDeviceOwnerComponentOnCallingUser() { - return mDpm.getDeviceOwnerComponentOnCallingUser(); - } - - /** - * Calls {@code DevicePolicyManager.getDeviceOwnerComponentOnAnyUser()}. - * - * @see DevicePolicyManager#getDeviceOwnerComponentOnAnyUser - */ - public ComponentName getDeviceOwnerComponentOnAnyUser() { - return mDpm.getDeviceOwnerComponentOnAnyUser(); - } - - /** - * Calls {@code DevicePolicyManager.getProfileOwnerAsUser()}. - * - * @see DevicePolicyManager#getProfileOwnerAsUser - */ - public @Nullable ComponentName getProfileOwnerAsUser(final int userId) { - return mDpm.getProfileOwnerAsUser(userId); - } - - /** - * Calls {@code DevicePolicyManager.getDeviceOwnerNameOnAnyUser()}. - * - * @see DevicePolicyManager#getDeviceOwnerNameOnAnyUser - */ - public CharSequence getDeviceOwnerOrganizationName() { - return mDpm.getDeviceOwnerOrganizationName(); - } - - /** - * Calls {@code DevicePolicyManager.getPermissionGrantState()}. - * - * @see DevicePolicyManager#getPermissionGrantState - */ - public int getPermissionGrantState(@Nullable ComponentName admin, String packageName, - String permission) { - return mDpm.getPermissionGrantState(admin, packageName, permission); - } - - /** - * Calls {@code DevicePolicyManager.isSecurityLoggingEnabled()}. - * - * @see DevicePolicyManager#isSecurityLoggingEnabled - */ - public boolean isSecurityLoggingEnabled(@Nullable ComponentName admin) { - return mDpm.isSecurityLoggingEnabled(admin); - } - - /** - * Calls {@code DevicePolicyManager.isNetworkLoggingEnabled()}. - * - * @see DevicePolicyManager#isNetworkLoggingEnabled - */ - public boolean isNetworkLoggingEnabled(@Nullable ComponentName admin) { - return mDpm.isNetworkLoggingEnabled(admin); - } - - /** - * Calls {@code DevicePolicyManager.getLastSecurityLogRetrievalTime()}. - * - * @see DevicePolicyManager#getLastSecurityLogRetrievalTime - */ - public long getLastSecurityLogRetrievalTime() { - return mDpm.getLastSecurityLogRetrievalTime(); - } - - /** - * Calls {@code DevicePolicyManager.getLastBugReportRequestTime()}. - * - * @see DevicePolicyManager#getLastBugReportRequestTime - */ - public long getLastBugReportRequestTime() { - return mDpm.getLastBugReportRequestTime(); - } - - /** - * Calls {@code DevicePolicyManager.getLastNetworkLogRetrievalTime()}. - * - * @see DevicePolicyManager#getLastNetworkLogRetrievalTime - */ - public long getLastNetworkLogRetrievalTime() { - return mDpm.getLastNetworkLogRetrievalTime(); - } - - /** - * Calls {@code DevicePolicyManager.isCurrentInputMethodSetByOwner()}. - * - * @see DevicePolicyManager#isCurrentInputMethodSetByOwner - */ - public boolean isCurrentInputMethodSetByOwner() { - return mDpm.isCurrentInputMethodSetByOwner(); - } - - /** - * Calls {@code DevicePolicyManager.getOwnerInstalledCaCerts()}. - * - * @see DevicePolicyManager#getOwnerInstalledCaCerts - */ - public List getOwnerInstalledCaCerts(@NonNull UserHandle user) { - return mDpm.getOwnerInstalledCaCerts(user); - } - - /** - * Calls {@code DevicePolicyManager.isDeviceOwnerAppOnAnyUser()}. - * - * @see DevicePolicyManager#isDeviceOwnerAppOnAnyUser - */ - public boolean isDeviceOwnerAppOnAnyUser(String packageName) { - return mDpm.isDeviceOwnerAppOnAnyUser(packageName); - } - - /** - * Calls {@code DevicePolicyManager.packageHasActiveAdmins()}. - * - * @see DevicePolicyManager#packageHasActiveAdmins - */ - public boolean packageHasActiveAdmins(String packageName) { - return mDpm.packageHasActiveAdmins(packageName); - } - - /** - * Calls {@code DevicePolicyManager.isUninstallInQueue()}. - * - * @see DevicePolicyManager#isUninstallInQueue - */ - public boolean isUninstallInQueue(String packageName) { - return mDpm.isUninstallInQueue(packageName); - } - - /** - * Calls {@code DevicePolicyManager.createAdminSupportIntent()}. - * - * @see DevicePolicyManager#createAdminSupportIntent(String) - */ - public Intent createAdminSupportIntent(@NonNull String restriction) { - return mDpm.createAdminSupportIntent(restriction); - } - - /** - * Calls {@code DevicePolicyManager#getDeviceOwnerUserId()}. - * - * @see DevicePolicyManager#getDeviceOwnerUserId() - */ - public int getDeviceOwnerUserId() { - return mDpm.getDeviceOwnerUserId(); - } - - /** - * Calls {@code DevicePolicyManager#getMaximumTimeToLock()}. - * - * @see DevicePolicyManager#getMaximumTimeToLock(ComponentName, int) - */ - public long getMaximumTimeToLock(@Nullable ComponentName admin, @UserIdInt int userHandle) { - return mDpm.getMaximumTimeToLock(admin, userHandle); - } -} diff --git a/src/com/android/settings/wrapper/UserManagerWrapper.java b/src/com/android/settings/wrapper/UserManagerWrapper.java deleted file mode 100644 index 8c3a01d4267..00000000000 --- a/src/com/android/settings/wrapper/UserManagerWrapper.java +++ /dev/null @@ -1,67 +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.wrapper; - -import android.content.pm.UserInfo; -import android.os.UserHandle; -import android.os.UserManager; - -import java.util.List; - -/** - * This class replicates a subset of the android.os.UserManager. The class - * exists so that we can use a thin wrapper around the UserManager in production code and a mock in - * tests. We cannot directly mock or shadow the UserManager, because some of the methods we rely on - * are newer than the API version supported by Robolectric or are hidden. - */ -public class UserManagerWrapper { - private UserManager mUserManager; - - public UserManagerWrapper(UserManager userManager) { - mUserManager = userManager; - } - - public UserInfo getPrimaryUser() { - return mUserManager.getPrimaryUser(); - } - - public List getUsers() { - return mUserManager.getUsers(); - } - - public List getProfiles(int userHandle) { - return mUserManager.getProfiles(userHandle); - } - - public boolean isUsbFileTransferRestricted() { - return mUserManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER); - } - - public boolean isUsbTetheringRestricted() { - return mUserManager.hasUserRestriction(UserManager.DISALLOW_CONFIG_TETHERING); - } - - public boolean isUsbFileTransferRestrictedBySystem() { - return mUserManager.hasBaseUserRestriction( - UserManager.DISALLOW_USB_FILE_TRANSFER, UserHandle.of(UserHandle.myUserId())); - } - - public boolean isUsbTetheringRestrictedBySystem() { - return mUserManager.hasBaseUserRestriction( - UserManager.DISALLOW_CONFIG_TETHERING, UserHandle.of(UserHandle.myUserId())); - } -} diff --git a/src/com/android/settings/wrapper/WallpaperManagerWrapper.java b/src/com/android/settings/wrapper/WallpaperManagerWrapper.java deleted file mode 100644 index eabc5bb6e3e..00000000000 --- a/src/com/android/settings/wrapper/WallpaperManagerWrapper.java +++ /dev/null @@ -1,44 +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.wrapper; - -import android.app.WallpaperManager; -import android.content.Context; - -public class WallpaperManagerWrapper { - - private final WallpaperManager mWallpaperManager; - private final boolean mWallpaperServiceEnabled; - - public WallpaperManagerWrapper(Context context) { - mWallpaperServiceEnabled = context.getResources().getBoolean( - com.android.internal.R.bool.config_enableWallpaperService); - mWallpaperManager = mWallpaperServiceEnabled ? (WallpaperManager) context.getSystemService( - Context.WALLPAPER_SERVICE) : null; - } - - public boolean isWallpaperServiceEnabled() { - return mWallpaperServiceEnabled; - } - - public int getWallpaperId(int which) { - if (!mWallpaperServiceEnabled) { - throw new RuntimeException("This device does not have wallpaper service enabled."); - } - return mWallpaperManager.getWallpaperId(which); - } -} diff --git a/tests/robotests/src/com/android/settings/ApnEditorTest.java b/tests/robotests/src/com/android/settings/ApnEditorTest.java index eb9955adb3e..aca460f89ae 100644 --- a/tests/robotests/src/com/android/settings/ApnEditorTest.java +++ b/tests/robotests/src/com/android/settings/ApnEditorTest.java @@ -16,27 +16,73 @@ package com.android.settings; -import static junit.framework.Assert.assertEquals; -import static junit.framework.Assert.assertNull; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.ArgumentMatchers.any; +import static org.mockito.Mockito.doNothing; import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.verify; +import android.app.Activity; +import android.content.ContentResolver; +import android.content.ContentValues; +import android.content.Context; +import android.content.res.Resources; import android.database.Cursor; import android.net.Uri; +import android.support.v14.preference.MultiSelectListPreference; +import android.support.v14.preference.SwitchPreference; +import android.support.v7.preference.EditTextPreference; +import android.support.v7.preference.ListPreference; +import android.view.KeyEvent; +import android.view.Menu; +import android.view.MenuItem; +import android.view.View; import com.android.settings.ApnEditor.ApnData; -import com.android.settings.ApnEditor.InvalidTypeException; import com.android.settings.testutils.SettingsRobolectricTestRunner; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; +import org.mockito.ArgumentCaptor; +import org.mockito.Captor; import org.mockito.Mock; +import org.mockito.Mockito; import org.mockito.MockitoAnnotations; +import org.robolectric.Robolectric; +import org.robolectric.RuntimeEnvironment; @RunWith(SettingsRobolectricTestRunner.class) public class ApnEditorTest { + private static final Object[] APN_DATA = new Object[] { + 0, /* ID */ + "apn_name" /* apn name */, + "apn.com" /* apn */, + "" /* proxy */, + "" /* port */, + "" /* username */, + "" /* server */, + "" /* password */, + "" /* MMSC */, + "123" /* MCC */, + "456" /* MNC */, + "123456" /* operator numeric */, + "" /* MMS proxy */, + "" /* MMS port */, + 0 /* Authentication type */, + "default,supl,ia" /* APN type */, + "IPv6" /* APN protocol */, + 1 /* APN enable/disable */, + 0 /* Bearer */, + 0 /* Bearer BITMASK*/, + "IPv4" /* APN roaming protocol */, + "None" /* MVNO type */, + "", /* MVNO value */ + }; + private static final int CURSOR_INTEGER_INDEX = 0; private static final int CURSOR_STRING_INDEX = 1; @@ -45,10 +91,331 @@ public class ApnEditorTest { @Mock private Cursor mCursor; + @Captor + private ArgumentCaptor mUriCaptor; + + private ApnEditor mApnEditorUT; + private Activity mActivity; + private Resources mResources; + @Before public void setUp() { MockitoAnnotations.initMocks(this); + mActivity = spy(Robolectric.setupActivity(Activity.class)); + mResources = mActivity.getResources(); + mApnEditorUT = spy(new ApnEditor()); + + doReturn(mActivity).when(mApnEditorUT).getActivity(); + doReturn(mResources).when(mApnEditorUT).getResources(); + doNothing().when(mApnEditorUT).finish(); + doNothing().when(mApnEditorUT).showError(); + + setMockPreference(mActivity); + mApnEditorUT.mApnData = new FakeApnData(APN_DATA); + mApnEditorUT.sNotSet = "Not Set"; + } + + @Test + public void testSetStringValue_valueChanged_shouldSetValue() { + // GIVEN an APN value which is different than the APN value in database + final String apnKey = "apn"; + final String apnValue = "testing.com"; + final ContentValues cv = new ContentValues(); + + // WHEN try to check and set the apn value + final boolean isDiff = mApnEditorUT.setStringValueAndCheckIfDiff( + cv, apnKey, apnValue, false /* assumeDiff */, ApnEditor.APN_INDEX); + + // THEN the APN value is different than the one in database, and it has been stored in the + // given ContentValues + assertThat(isDiff).isTrue(); + assertThat(apnValue).isEqualTo(cv.getAsString(apnKey)); + } + + @Test + public void testSetStringValue_valueNotChanged_shouldNotSetValue() { + // GIVEN an APN value which is same as the APN value in database + final String apnKey = "apn"; + final String apnValue = (String) APN_DATA[ApnEditor.APN_INDEX]; + final ContentValues cv = new ContentValues(); + + // WHEN try to check and set the apn value + final boolean isDiff = mApnEditorUT.setStringValueAndCheckIfDiff( + cv, apnKey, apnValue, false /* assumeDiff */, ApnEditor.APN_INDEX); + + // THEN the APN value is same as the one in database, and the new APN value is not stored + // in the given ContentValues + assertThat(isDiff).isFalse(); + assertThat(cv.get(apnKey)).isNull(); + } + + @Test + public void testSetStringValue_nullValue_shouldNotSetValue_shouldNotSetValue() { + // GIVEN a null APN value + final String apnKey = "apn"; + final String apnValue = null; + final ContentValues cv = new ContentValues(); + + // WHEN try to check and set the apn value + final boolean isDiff = mApnEditorUT.setStringValueAndCheckIfDiff( + cv, apnKey, apnValue, false /* assumeDiff */, ApnEditor.APN_INDEX); + + // THEN the APN value is different than the one in database, but the null value is not + // stored in the given ContentValues + assertThat(isDiff).isTrue(); + assertThat(cv.get(apnKey)).isNull(); + } + + @Test + public void testSetIntValue_valueChanged_shouldSetValue() { + // GIVEN a value indicated whether the apn is enabled, and it's different than the value in + // the database + final String apnEnabledKey = "apn_enabled"; + final int apnEnabledValue = 0; + final ContentValues cv = new ContentValues(); + + // WHEN try to check and set the apn enabled + final boolean isDiff = mApnEditorUT.setIntValueAndCheckIfDiff( + cv, + apnEnabledKey, + apnEnabledValue, + false /* assumeDiff */, + ApnEditor.CARRIER_ENABLED_INDEX); + + // THEN the apn enabled field is different than the one in database, and it has been stored + // in the given ContentValues + assertThat(isDiff).isTrue(); + assertThat(cv.getAsInteger(apnEnabledKey)).isEqualTo(apnEnabledValue); + } + + @Test + public void testSetIntValue_valueNotChanged_shouldNotSetValue() { + // GIVEN a value indicated whether the apn is enabled, and it's same as the one in the + // database + final String apnEnabledKey = "apn_enabled"; + final int apnEnabledValue = (int) APN_DATA[ApnEditor.CARRIER_ENABLED_INDEX]; + final ContentValues cv = new ContentValues(); + + // WHEN try to check and set the apn enabled + final boolean isDiff = mApnEditorUT.setIntValueAndCheckIfDiff( + cv, + apnEnabledKey, + apnEnabledValue, + false /* assumeDiff */, + ApnEditor.CARRIER_ENABLED_INDEX); + + // THEN the apn enabled field is same as the one in the database, and the filed is not + // stored in the given ContentValues + assertThat(isDiff).isFalse(); + assertThat(cv.get(apnEnabledKey)).isNull(); + } + + @Test + public void testValidateApnData_validData_shouldReturnNull() { + // GIVEN a valid apn data + mApnEditorUT.mApnData = new FakeApnData(APN_DATA); + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN validate the apn data + final String errMsg = mApnEditorUT.validateApnData(); + + // THEN the error message should be null + assertThat(errMsg).isNull(); + } + + @Test + public void testValidateApn_apnNameNotSet_shouldReturnErrorMessage() { + // GIVEN a apn data without the apn name + final FakeApnData apnData = new FakeApnData(APN_DATA); + apnData.mData[ApnEditor.NAME_INDEX] = ""; + mApnEditorUT.mApnData = apnData; + mApnEditorUT.fillUI(true /* firstTime */); + + // THEN validate the apn data + final String errMsg = mApnEditorUT.validateApnData(); + + // THEN the error message indicated the apn name not set is returned + assertThat(errMsg).isEqualTo(mResources.getString(R.string.error_name_empty)); + } + + @Test + public void testValidateApnData_apnNotSet_shouldReturnErrorMessage() { + // GIVEN a apn data without the apn + final FakeApnData apnData = new FakeApnData(APN_DATA); + apnData.mData[ApnEditor.APN_INDEX] = ""; + mApnEditorUT.mApnData = apnData; + mApnEditorUT.fillUI(true /* firstTime */); + + // THEN validate the apn data + final String errMsg = mApnEditorUT.validateApnData(); + + // THEN the error message indicated the apn not set is returned + assertThat(errMsg).isEqualTo(mResources.getString(R.string.error_apn_empty)); + } + + @Test + public void testValidateApnData_mccInvalid_shouldReturnErrorMessage() { + // GIVEN a apn data with invalid mcc + final FakeApnData apnData = new FakeApnData(APN_DATA); + // The length of the mcc should be 3 + apnData.mData[ApnEditor.MCC_INDEX] = "1324"; + mApnEditorUT.mApnData = apnData; + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN validate the apn data + final String errMsg = mApnEditorUT.validateApnData(); + + // THEN the error message indicated the mcc invalid is returned + assertThat(errMsg).isEqualTo(mResources.getString(R.string.error_mcc_not3)); + } + + @Test + public void testValidateApnData_mncInvalid_shouldReturnErrorMessage() { + // GIVEN an apn data with invalid mnc + final FakeApnData apnData = new FakeApnData(APN_DATA); + // The length of the mnc should be 2 or 3 + apnData.mData[ApnEditor.MNC_INDEX] = "1324"; + mApnEditorUT.mApnData = apnData; + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN validate the apn data + final String errMsg = mApnEditorUT.validateApnData(); + + // THEN the error message indicated the mnc invalid is returned + assertThat(errMsg).isEqualTo(mResources.getString(R.string.error_mnc_not23)); + } + + @Test + public void testSaveApnData_pressBackButtonWithValidApnData_shouldSaveApnData() { + // GIVEN a valid apn data + mApnEditorUT.mApnData = new FakeApnData(APN_DATA); + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN press the back button + final KeyEvent event = new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK); + mApnEditorUT.onKey(new View(mActivity), KeyEvent.KEYCODE_BACK, event); + + // THEN the apn data is saved and the apn editor is closed + verify(mApnEditorUT).validateAndSaveApnData(); + verify(mApnEditorUT).finish(); + } + + @Test + public void testSaveApnData_pressSaveButtonWithValidApnData_shouldSaveApnData() { + // GIVEN a valid apn data + mApnEditorUT.mApnData = new FakeApnData(APN_DATA); + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN press the save button + MenuItem item = Mockito.mock(MenuItem.class); + // Menu.FIRST + 1 indicated the SAVE option in ApnEditor + doReturn(Menu.FIRST + 1).when(item).getItemId(); + mApnEditorUT.onOptionsItemSelected(item); + + // THEN the apn data is saved and the apn editor is closed + verify(mApnEditorUT).validateAndSaveApnData(); + verify(mApnEditorUT).finish(); + } + + @Test + public void testSaveApnData_apnDataInvalid_shouldNotSaveApnData() { + // GIVEN an invalid apn data + final FakeApnData apnData = new FakeApnData(APN_DATA); + // The valid apn data should contains a non-empty apn name + apnData.mData[ApnEditor.NAME_INDEX] = ""; + mApnEditorUT.mApnData = apnData; + mApnEditorUT.fillUI(true /* firstTime */); + + // WHEN press the save button + final MenuItem item = Mockito.mock(MenuItem.class); + // Menu.FIRST + 1 indicated the SAVE option in ApnEditor + doReturn(Menu.FIRST + 1).when(item).getItemId(); + mApnEditorUT.onOptionsItemSelected(item); + + // THEN the error dialog is shown + verify(mApnEditorUT).validateAndSaveApnData(); + verify(mApnEditorUT).showError(); + } + + @Test + public void testDeleteApnData_shouldDeleteData() { + // GIVEN a valid apn data correspond a row in database + final Uri apnUri = Uri.parse("content://telephony/carriers/1"); + mApnEditorUT.mApnData = new FakeApnData(APN_DATA, apnUri); + mApnEditorUT.fillUI(true /* firstTime */); + ContentResolver mockContentResolver = Mockito.mock(ContentResolver.class); + doReturn(mockContentResolver).when(mActivity).getContentResolver(); + + // WHEN press the save button + final MenuItem item = Mockito.mock(MenuItem.class); + // Menu.FIRST indicated the DELETE option in ApnEditor + doReturn(Menu.FIRST).when(item).getItemId(); + mApnEditorUT.onOptionsItemSelected(item); + + // THEN the apn data is deleted and the apn editor is closed + verify(mockContentResolver).delete(mUriCaptor.capture(), any(), any()); + assertThat(apnUri).isEqualTo(mUriCaptor.getValue()); + verify(mApnEditorUT).finish(); + } + + @Test(expected = ClassCastException.class) + public void testApnData_invalidIntegerType_throwsInvalidTypeException() { + // GIVEN a ApnData constructed from cursor initCursor(); + final ApnData data = new ApnData(mApnUri, mCursor); + + // WHEN get a string from an integer column + // THEN the InvalidTypeException is threw + data.getString(CURSOR_INTEGER_INDEX); + } + + @Test(expected = ClassCastException.class) + public void testApnData_invalidStringType_throwsInvalidTypeException() { + // GIVEN a ApnData constructed from cursor + initCursor(); + final ApnData data = new ApnData(mApnUri, mCursor); + + // WHEN get a integer from a string column + // THEN the InvalidTypeException is threw + data.getInteger(CURSOR_STRING_INDEX); + } + + @Test + public void testApnData_validIntegerType_returnCorrectValue() { + // GIVEN a ApnData constructed from cursor + initCursor(); + final ApnData data = new ApnData(mApnUri, mCursor); + + // WHEN get integer from an integer column + final int val = data.getInteger(CURSOR_INTEGER_INDEX); + + // THEN the integer is returned correctly + assertThat(val).isEqualTo(mCursor.getInt(CURSOR_INTEGER_INDEX)); + } + + @Test + public void testApnData_validStringType_returnCorrectValue() { + // GIVEN a ApnData constructed from cursor + initCursor(); + final ApnData data = new ApnData(mApnUri, mCursor); + + // WHEN get string from a string column + final String str = data.getString(CURSOR_STRING_INDEX); + + // THEN the integer is returned correctly + assertThat(str).isEqualTo(mCursor.getString(CURSOR_STRING_INDEX)); + } + + @Test + public void testApnData_nullValueColumn_returnNull() { + // GIVEN a empty ApnData + final ApnData data = new ApnData(3); + + // WHEN get string value from a null column + final String str = data.getString(0); + + // THEN the null value is returned + assertThat(str).isNull(); } private void initCursor() { @@ -59,59 +426,38 @@ public class ApnEditorTest { doReturn(Cursor.FIELD_TYPE_STRING).when(mCursor).getType(CURSOR_STRING_INDEX); } - @Test(expected = InvalidTypeException.class) - public void testApnData_invalidIntegerType_throwsInvalidTypeException() { - // GIVEN a ApnData constructed from cursor - ApnData data = new ApnData(mApnUri, mCursor); - - // WHEN get a string from an integer column - // THEN the InvalidTypeException is threw - data.getString(CURSOR_INTEGER_INDEX); + private void setMockPreference(Context context) { + mApnEditorUT.mName = new EditTextPreference(context); + mApnEditorUT.mApn = new EditTextPreference(context); + mApnEditorUT.mProxy = new EditTextPreference(context); + mApnEditorUT.mPort = new EditTextPreference(context); + mApnEditorUT.mUser = new EditTextPreference(context); + mApnEditorUT.mServer = new EditTextPreference(context); + mApnEditorUT.mPassword = new EditTextPreference(context); + mApnEditorUT.mMmsc = new EditTextPreference(context); + mApnEditorUT.mMcc = new EditTextPreference(context); + mApnEditorUT.mMnc = new EditTextPreference(context); + mApnEditorUT.mMmsProxy = new EditTextPreference(context); + mApnEditorUT.mMmsPort = new EditTextPreference(context); + mApnEditorUT.mAuthType = new ListPreference(context); + mApnEditorUT.mApnType = new EditTextPreference(context); + mApnEditorUT.mProtocol = new ListPreference(context); + mApnEditorUT.mRoamingProtocol = new ListPreference(context); + mApnEditorUT.mCarrierEnabled = new SwitchPreference(context); + mApnEditorUT.mBearerMulti = new MultiSelectListPreference(context); + mApnEditorUT.mMvnoType = new ListPreference(context); + mApnEditorUT.mMvnoMatchData = new EditTextPreference(context); } - @Test(expected = InvalidTypeException.class) - public void testApnData_invalidStringType_throwsInvalidTypeException() { - // GIVEN a ApnData constructed from cursor - ApnData data = new ApnData(mApnUri, mCursor); + private final class FakeApnData extends ApnData { + FakeApnData(Object[] data) { + super(data.length); + System.arraycopy(data, 0, mData, 0, data.length); + } - // WHEN get a integer from a string column - // THEN the InvalidTypeException is threw - data.getInteger(CURSOR_STRING_INDEX); + FakeApnData(Object[] data, Uri uri) { + this(data); + mUri = uri; + } } - - @Test - public void testApnData_validIntegerType_returnCorrectValue() { - // GIVEN a ApnData constructed from cursor - ApnData data = new ApnData(mApnUri, mCursor); - - // WHEN get integer from an integer column - int val = data.getInteger(CURSOR_INTEGER_INDEX); - - // THEN the integer is returned correctly - assertEquals(mCursor.getInt(CURSOR_INTEGER_INDEX), val); - } - - @Test - public void testApnData_validStringType_returnCorrectValue() { - // GIVEN a ApnData constructed from cursor - ApnData data = new ApnData(mApnUri, mCursor); - - // WHEN get string from a string column - String str = data.getString(CURSOR_STRING_INDEX); - - // THEN the integer is returned correctly - assertEquals(mCursor.getString(CURSOR_STRING_INDEX), str); - } - - @Test - public void testApnData_nullValueColumn_returnNull() { - // GIVEN a empty ApnData - ApnData data = new ApnData(3); - - // WHEN get string value from a null column - String str = data.getString(0); - - // THEN the null value is returned - assertNull(str); - } -} +} \ No newline at end of file diff --git a/tests/robotests/src/com/android/settings/UtilsTest.java b/tests/robotests/src/com/android/settings/UtilsTest.java index fcd40aa65c9..92aedcfe6a6 100644 --- a/tests/robotests/src/com/android/settings/UtilsTest.java +++ b/tests/robotests/src/com/android/settings/UtilsTest.java @@ -17,7 +17,6 @@ package com.android.settings; import static com.google.common.truth.Truth.assertThat; - import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.Matchers.anyString; @@ -28,6 +27,7 @@ import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; +import android.app.admin.DevicePolicyManager; import android.content.ComponentName; import android.content.Context; import android.content.pm.ApplicationInfo; @@ -48,7 +48,6 @@ import android.widget.EditText; import android.widget.TextView; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import org.junit.Before; import org.junit.Test; @@ -74,7 +73,7 @@ public class UtilsTest { @Mock private ConnectivityManager connectivityManager; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; @Mock private UserManager mUserManager; @Mock diff --git a/tests/robotests/src/com/android/settings/accessibility/MagnificationGesturesPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/accessibility/MagnificationGesturesPreferenceControllerTest.java new file mode 100644 index 00000000000..23ac795fb89 --- /dev/null +++ b/tests/robotests/src/com/android/settings/accessibility/MagnificationGesturesPreferenceControllerTest.java @@ -0,0 +1,80 @@ +/* + * 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.accessibility; + +import static com.google.common.truth.Truth.assertThat; + +import android.content.Context; +import android.provider.Settings; +import android.support.v7.preference.Preference; + +import com.android.settings.R; +import com.android.settings.core.BasePreferenceController; +import com.android.settings.testutils.SettingsRobolectricTestRunner; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; + +@RunWith(SettingsRobolectricTestRunner.class) +public class MagnificationGesturesPreferenceControllerTest { + + private Context mContext; + private MagnificationGesturesPreferenceController mController; + private Preference mPreference; + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + mContext = RuntimeEnvironment.application; + mController = new MagnificationGesturesPreferenceController(mContext, "pref_key"); + mPreference = new Preference(mContext); + mController.updateState(mPreference); + } + + @Test + public void isAlwaysAvailable() { + assertThat(mController.getAvailabilityStatus()) + .isEqualTo(BasePreferenceController.AVAILABLE); + } + + @Test + public void updateState_shouldRefreshSummary() { + Settings.System.putInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, 1); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getString(R.string.accessibility_feature_state_on)); + + Settings.System.putInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_ENABLED, 0); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getString(R.string.accessibility_feature_state_off)); + } + + @Test + public void updateState_shouldRefreshSummarySuw() { + mController.setIsFromSUW(true); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getString(R.string. + accessibility_screen_magnification_short_summary)); + } +} diff --git a/tests/robotests/src/com/android/settings/accessibility/MagnificationNavbarPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/accessibility/MagnificationNavbarPreferenceControllerTest.java new file mode 100644 index 00000000000..486ccd39e04 --- /dev/null +++ b/tests/robotests/src/com/android/settings/accessibility/MagnificationNavbarPreferenceControllerTest.java @@ -0,0 +1,123 @@ +/* + * 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.accessibility; + +import static com.android.settings.search.ResultPayload.Availability.AVAILABLE; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Mockito.spy; + +import android.content.Context; +import android.content.res.Resources; +import android.provider.Settings; +import android.support.v7.preference.Preference; + +import com.android.settings.R; +import com.android.settings.testutils.SettingsRobolectricTestRunner; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; +import org.robolectric.annotation.Config; +import org.robolectric.annotation.Implementation; +import org.robolectric.annotation.Implements; +import org.robolectric.annotation.Resetter; + +@RunWith(SettingsRobolectricTestRunner.class) +public class MagnificationNavbarPreferenceControllerTest { + + private Context mContext; + private MagnificationNavbarPreferenceController mController; + private Preference mPreference; + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + mContext = spy(RuntimeEnvironment.application); + mController = new MagnificationNavbarPreferenceController(mContext, "test_key"); + mPreference = new Preference(mContext); + mController.updateState(mPreference); + } + + @After + public void tearDown() { + ShadowMagnificationPreferenceFragment.reset(); + } + + @Test + @Config(shadows = ShadowMagnificationPreferenceFragment.class) + public void isAvailable_unsupported_shouldNotBeAvailable() { + ShadowMagnificationPreferenceFragment.setApplicable(false); + + assertThat(mController.getAvailabilityStatus()) + .isNotEqualTo(AVAILABLE); + } + + @Test + @Config(shadows = ShadowMagnificationPreferenceFragment.class) + public void isAvailable_supported_shouldBeAvailable() { + ShadowMagnificationPreferenceFragment.setApplicable(true); + + assertThat(mController.getAvailabilityStatus()) + .isEqualTo(AVAILABLE); + } + + @Test + public void updateState_shouldRefreshSummary() { + Settings.System.putInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, 1); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getText(R.string.accessibility_feature_state_on)); + + Settings.System.putInt(mContext.getContentResolver(), + Settings.Secure.ACCESSIBILITY_DISPLAY_MAGNIFICATION_NAVBAR_ENABLED, 0); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getText(R.string.accessibility_feature_state_off)); + } + + @Test + public void updateState_shouldRefreshSummarySuw() { + mController.setIsFromSUW(true); + mController.updateState(mPreference); + assertThat(mPreference.getSummary()) + .isEqualTo(mContext.getString(R.string. + accessibility_screen_magnification_navbar_short_summary)); + } + + @Implements(MagnificationPreferenceFragment.class) + public static class ShadowMagnificationPreferenceFragment { + private static boolean sIsApplicable; + + @Resetter + static void reset() { + sIsApplicable = false; + } + + @Implementation + static boolean isApplicable(Resources res) { + return sIsApplicable; + } + + static void setApplicable(boolean applicable) { + sIsApplicable = applicable; + } + } +} diff --git a/tests/robotests/src/com/android/settings/accounts/RemoveAccountPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/accounts/RemoveAccountPreferenceControllerTest.java index 3df7c9d8b11..f1635ca2a32 100644 --- a/tests/robotests/src/com/android/settings/accounts/RemoveAccountPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/accounts/RemoveAccountPreferenceControllerTest.java @@ -50,10 +50,6 @@ import com.android.settings.testutils.shadow.ShadowAccountManager; import com.android.settings.testutils.shadow.ShadowContentResolver; import com.android.settings.testutils.shadow.ShadowDevicePolicyManager; import com.android.settings.testutils.shadow.ShadowUserManager; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; - -import java.util.ArrayList; -import java.util.List; import org.junit.Before; import org.junit.Test; @@ -64,12 +60,14 @@ import org.robolectric.RuntimeEnvironment; import org.robolectric.annotation.Config; import org.robolectric.shadows.ShadowApplication; +import java.util.ArrayList; +import java.util.List; + @RunWith(SettingsRobolectricTestRunner.class) -@Config( - shadows = { +@Config(shadows = { ShadowUserManager.class, ShadowDevicePolicyManager.class - }) +}) public class RemoveAccountPreferenceControllerTest { private static final String KEY_REMOVE_ACCOUNT = "remove_account"; @@ -78,8 +76,6 @@ public class RemoveAccountPreferenceControllerTest { @Mock(answer = RETURNS_DEEP_STUBS) private AccountManager mAccountManager; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; - @Mock private PreferenceFragment mFragment; @Mock private PreferenceManager mPreferenceManager; @@ -105,10 +101,10 @@ public class RemoveAccountPreferenceControllerTest { when(mFragment.getFragmentManager()).thenReturn(mFragmentManager); when(mFragmentManager.beginTransaction()).thenReturn(mFragmentTransaction); when(mAccountManager.getAuthenticatorTypesAsUser(anyInt())) - .thenReturn(new AuthenticatorDescription[0]); + .thenReturn(new AuthenticatorDescription[0]); when(mAccountManager.getAccountsAsUser(anyInt())).thenReturn(new Account[0]); mController = new RemoveAccountPreferenceController(RuntimeEnvironment.application, - mFragment, mDevicePolicyManager); + mFragment); } @Test @@ -128,8 +124,8 @@ public class RemoveAccountPreferenceControllerTest { mController.onClick(null); verify(mFragmentTransaction).add( - any(RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.class), - eq(TAG_REMOVE_ACCOUNT_DIALOG)); + any(RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.class), + eq(TAG_REMOVE_ACCOUNT_DIALOG)); } @Test @@ -141,20 +137,20 @@ public class RemoveAccountPreferenceControllerTest { List enforcingUsers = new ArrayList<>(); enforcingUsers.add(new UserManager.EnforcingUser(userId, - UserManager.RESTRICTION_SOURCE_DEVICE_OWNER)); + UserManager.RESTRICTION_SOURCE_DEVICE_OWNER)); ComponentName componentName = new ComponentName("test", "test"); // Ensure that RestrictedLockUtils.checkIfRestrictionEnforced doesn't return null. ShadowUserManager.getShadow().setUserRestrictionSources( - UserManager.DISALLOW_MODIFY_ACCOUNTS, - UserHandle.of(userId), - enforcingUsers); + UserManager.DISALLOW_MODIFY_ACCOUNTS, + UserHandle.of(userId), + enforcingUsers); ShadowDevicePolicyManager.getShadow().setDeviceOwnerComponentOnAnyUser(componentName); mController.onClick(null); verify(mFragmentTransaction, never()).add( - any(RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.class), - eq(TAG_REMOVE_ACCOUNT_DIALOG)); + any(RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.class), + eq(TAG_REMOVE_ACCOUNT_DIALOG)); } @Test @@ -168,11 +164,11 @@ public class RemoveAccountPreferenceControllerTest { Account account = new Account("Account11", "com.acct1"); UserHandle userHandle = new UserHandle(10); RemoveAccountPreferenceController.ConfirmRemoveAccountDialog dialog = - RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.show( - mFragment, account, userHandle); + RemoveAccountPreferenceController.ConfirmRemoveAccountDialog.show( + mFragment, account, userHandle); dialog.onCreate(new Bundle()); dialog.onClick(null, 0); verify(mAccountManager).removeAccountAsUser(eq(account), nullable(Activity.class), - nullable(AccountManagerCallback.class), nullable(Handler.class), eq(userHandle)); + nullable(AccountManagerCallback.class), nullable(Handler.class), eq(userHandle)); } } diff --git a/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounterTest.java b/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounterTest.java index a784329e36f..a0bae85330d 100644 --- a/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounterTest.java +++ b/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsCounterTest.java @@ -37,7 +37,6 @@ import android.os.UserHandle; import android.os.UserManager; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -84,7 +83,7 @@ public final class AppWithAdminGrantedPermissionsCounterTest { @Mock private IPackageManagerWrapper mPackageManagerService; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; private int mAppCount = -1; private ApplicationInfo mApp1; @@ -214,13 +213,13 @@ public final class AppWithAdminGrantedPermissionsCounterTest { // * app5 uses install-time permissions. It was installed by the admin but did not request // any of the permissions. It should not be counted. when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS - | PackageManager.MATCH_ANY_USER, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS + | PackageManager.MATCH_ANY_USER, MAIN_USER_ID)).thenReturn(Arrays.asList(mApp1, mApp2, mApp3, mApp4, mApp5)); // The second user has one app installed. This app uses run-time permissions. It has been // granted both permissions by the admin. It should be counted. when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, MANAGED_PROFILE_ID)).thenReturn(Arrays.asList(mApp6)); // app3 and app5 were installed by enterprise policy. @@ -250,7 +249,7 @@ public final class AppWithAdminGrantedPermissionsCounterTest { } private class AppWithAdminGrantedPermissionsCounterTestable - extends AppWithAdminGrantedPermissionsCounter { + extends AppWithAdminGrantedPermissionsCounter { private AppWithAdminGrantedPermissionsCounterTestable(String[] permissions) { super(mContext, permissions, mPackageManager, mPackageManagerService, mDevicePolicyManager); diff --git a/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsListerTest.java b/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsListerTest.java index ffa262b1377..940fd4b8353 100644 --- a/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsListerTest.java +++ b/tests/robotests/src/com/android/settings/applications/AppWithAdminGrantedPermissionsListerTest.java @@ -34,7 +34,6 @@ import android.os.UserHandle; import android.os.UserManager; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -81,7 +80,7 @@ public final class AppWithAdminGrantedPermissionsListerTest { @Mock private IPackageManagerWrapper mPackageManagerService; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; private List mAppList = Collections.emptyList(); @@ -109,14 +108,14 @@ public final class AppWithAdminGrantedPermissionsListerTest { // * app5 uses install-time permissions. It was installed by the admin but did not request // any of the permissions. It should not be listed. when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS - | PackageManager.MATCH_ANY_USER, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS + | PackageManager.MATCH_ANY_USER, MAIN_USER_ID)).thenReturn(Arrays.asList( - buildInfo(APP_1_UID, APP_1, 0 /* flags */, Build.VERSION_CODES.M), - buildInfo(APP_2_UID, APP_2, 0 /* flags */, Build.VERSION_CODES.M), - buildInfo(APP_3_UID, APP_3, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP), - buildInfo(APP_4_UID, APP_4, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP), - buildInfo(APP_5_UID, APP_5, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP))); + buildInfo(APP_1_UID, APP_1, 0 /* flags */, Build.VERSION_CODES.M), + buildInfo(APP_2_UID, APP_2, 0 /* flags */, Build.VERSION_CODES.M), + buildInfo(APP_3_UID, APP_3, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP), + buildInfo(APP_4_UID, APP_4, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP), + buildInfo(APP_5_UID, APP_5, 0 /* flags */, Build.VERSION_CODES.LOLLIPOP))); // Grant run-time permissions as appropriate. when(mDevicePolicyManager.getPermissionGrantState(null, APP_1, PERMISSION_1)) @@ -164,9 +163,9 @@ public final class AppWithAdminGrantedPermissionsListerTest { // The second user has one app installed. This app uses run-time permissions. It has been // granted both permissions by the admin. It should be listed. when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, MANAGED_PROFILE_ID)).thenReturn(Arrays.asList( - buildInfo(APP_6_UID, APP_6, 0 /* flags */, Build.VERSION_CODES.M))); + buildInfo(APP_6_UID, APP_6, 0 /* flags */, Build.VERSION_CODES.M))); // Grant run-time permissions as appropriate. when(mDevicePolicyManager.getPermissionGrantState(eq(null), eq(APP_6), anyObject())) diff --git a/tests/robotests/src/com/android/settings/applications/ApplicationFeatureProviderImplTest.java b/tests/robotests/src/com/android/settings/applications/ApplicationFeatureProviderImplTest.java index 57b0058dccc..8afb7986183 100644 --- a/tests/robotests/src/com/android/settings/applications/ApplicationFeatureProviderImplTest.java +++ b/tests/robotests/src/com/android/settings/applications/ApplicationFeatureProviderImplTest.java @@ -33,7 +33,6 @@ import android.os.UserManager; import com.android.settings.testutils.ApplicationTestUtils; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settings.wrapper.IPackageManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -75,7 +74,7 @@ public final class ApplicationFeatureProviderImplTest { @Mock private IPackageManagerWrapper mPackageManagerService; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; private ApplicationFeatureProvider mProvider; @@ -258,16 +257,16 @@ public final class ApplicationFeatureProviderImplTest { new UserInfo(MANAGED_PROFILE_ID, "managed profile", 0))); when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS - | PackageManager.MATCH_ANY_USER, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS + | PackageManager.MATCH_ANY_USER, MAIN_USER_ID)).thenReturn(Arrays.asList( - ApplicationTestUtils.buildInfo(APP_1_UID, APP_1, 0 /* flags */, - Build.VERSION_CODES.M))); + ApplicationTestUtils.buildInfo(APP_1_UID, APP_1, 0 /* flags */, + Build.VERSION_CODES.M))); when(mPackageManager.getInstalledApplicationsAsUser(PackageManager.GET_DISABLED_COMPONENTS - | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, + | PackageManager.GET_DISABLED_UNTIL_USED_COMPONENTS, MANAGED_PROFILE_ID)).thenReturn(Arrays.asList( - ApplicationTestUtils.buildInfo(APP_2_UID, APP_2, 0 /* flags */, - Build.VERSION_CODES.LOLLIPOP))); + ApplicationTestUtils.buildInfo(APP_2_UID, APP_2, 0 /* flags */, + Build.VERSION_CODES.LOLLIPOP))); } private ResolveInfo createResolveInfo(String packageName) { diff --git a/tests/robotests/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceControllerTest.java index e571521fc63..b85464de647 100644 --- a/tests/robotests/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/applications/appinfo/AppActionButtonPreferenceControllerTest.java @@ -17,7 +17,6 @@ package com.android.settings.applications.appinfo; import static com.google.common.truth.Truth.assertThat; - import static org.mockito.ArgumentMatchers.any; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.argThat; @@ -28,6 +27,7 @@ import static org.mockito.Mockito.spy; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; +import android.app.admin.DevicePolicyManager; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; @@ -47,7 +47,6 @@ import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.widget.ActionButtonPreference; import com.android.settings.widget.ActionButtonPreferenceTest; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.Utils; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState; @@ -74,7 +73,7 @@ public class AppActionButtonPreferenceControllerTest { @Mock private UserManager mUserManager; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; @Mock private AppInfoDashboardFragment mFragment; @Mock @@ -108,7 +107,7 @@ public class AppActionButtonPreferenceControllerTest { @Test public void getAvailabilityStatus_notInstantApp_shouldReturnAvailable() { ReflectionHelpers.setStaticField(AppUtils.class, "sInstantAppDataProvider", - (InstantAppDataProvider) (i -> false)); + (InstantAppDataProvider) (i -> false)); assertThat(mController.getAvailabilityStatus()).isEqualTo(mController.AVAILABLE); } @@ -116,7 +115,7 @@ public class AppActionButtonPreferenceControllerTest { @Test public void getAvailabilityStatus_isInstantApp_shouldReturnDisabled() { ReflectionHelpers.setStaticField(AppUtils.class, "sInstantAppDataProvider", - (InstantAppDataProvider) (i -> true)); + (InstantAppDataProvider) (i -> true)); assertThat(mController.getAvailabilityStatus()).isEqualTo(mController.DISABLED_FOR_USER); } @@ -220,7 +219,7 @@ public class AppActionButtonPreferenceControllerTest { @Test public void checkForceStop_isStateProtected_shouldDisableForceStop() { ReflectionHelpers.setStaticField(AppUtils.class, "sInstantAppDataProvider", - (InstantAppDataProvider) (i -> false)); + (InstantAppDataProvider) (i -> false)); final String packageName = "Package1"; final PackageInfo packageInfo = new PackageInfo(); packageInfo.packageName = packageName; @@ -228,7 +227,7 @@ public class AppActionButtonPreferenceControllerTest { appInfo.uid = 42; appInfo.sourceDir = "source"; final ApplicationsState.AppEntry appEntry = new ApplicationsState.AppEntry( - mContext, appInfo, 0); + mContext, appInfo, 0); when(mPackageManager.isPackageStateProtected(packageName, 0)).thenReturn(true); mController.checkForceStop(appEntry, packageInfo); @@ -278,7 +277,7 @@ public class AppActionButtonPreferenceControllerTest { mController.checkForceStop(appEntry, packageInfo); - verify(mContext).sendOrderedBroadcastAsUser(argThat(intent-> intent != null + verify(mContext).sendOrderedBroadcastAsUser(argThat(intent -> intent != null && intent.getAction().equals(Intent.ACTION_QUERY_PACKAGE_RESTART)), any(UserHandle.class), nullable(String.class), any(BroadcastReceiver.class), nullable(Handler.class), anyInt(), nullable(String.class), nullable(Bundle.class)); diff --git a/tests/robotests/src/com/android/settings/applications/appinfo/AppInfoDashboardFragmentTest.java b/tests/robotests/src/com/android/settings/applications/appinfo/AppInfoDashboardFragmentTest.java index 761b7462815..3128f30f656 100644 --- a/tests/robotests/src/com/android/settings/applications/appinfo/AppInfoDashboardFragmentTest.java +++ b/tests/robotests/src/com/android/settings/applications/appinfo/AppInfoDashboardFragmentTest.java @@ -17,7 +17,8 @@ package com.android.settings.applications.appinfo; import static com.android.settings.applications.appinfo.AppInfoDashboardFragment.ARG_PACKAGE_NAME; -import static com.android.settings.applications.appinfo.AppInfoDashboardFragment.UNINSTALL_ALL_USERS_MENU; +import static com.android.settings.applications.appinfo.AppInfoDashboardFragment + .UNINSTALL_ALL_USERS_MENU; import static com.android.settings.applications.appinfo.AppInfoDashboardFragment.UNINSTALL_UPDATES; import static com.google.common.truth.Truth.assertThat; import static org.mockito.ArgumentMatchers.any; @@ -31,6 +32,7 @@ import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; +import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.Intent; import android.content.pm.ApplicationInfo; @@ -45,7 +47,6 @@ import android.view.MenuItem; import com.android.settings.SettingsActivity; import com.android.settings.SettingsPreferenceFragment; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState.AppEntry; import com.android.settingslib.applications.instantapps.InstantAppDataProvider; @@ -75,7 +76,7 @@ public final class AppInfoDashboardFragmentTest { @Mock private SettingsActivity mActivity; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManager; + private DevicePolicyManager mDevicePolicyManager; @Mock private PackageManager mPackageManager; @@ -249,7 +250,7 @@ public final class AppInfoDashboardFragmentTest { @Test public void getNumberOfUserWithPackageInstalled_twoUsersInstalled_shouldReturnTwo() - throws PackageManager.NameNotFoundException{ + throws PackageManager.NameNotFoundException { final String packageName = "Package1"; final int userID1 = 1; final int userID2 = 2; @@ -273,7 +274,7 @@ public final class AppInfoDashboardFragmentTest { @Test public void getNumberOfUserWithPackageInstalled_oneUserInstalled_shouldReturnOne() - throws PackageManager.NameNotFoundException{ + throws PackageManager.NameNotFoundException { final String packageName = "Package1"; final int userID1 = 1; final int userID2 = 2; @@ -311,7 +312,7 @@ public final class AppInfoDashboardFragmentTest { @Test public void startAppInfoFragment_noCrashOnNullArgs() { final SettingsPreferenceFragment caller = mock(SettingsPreferenceFragment.class); - final SettingsActivity sa = mock (SettingsActivity.class); + final SettingsActivity sa = mock(SettingsActivity.class); when(caller.getActivity()).thenReturn(sa); when(caller.getContext()).thenReturn(sa); final AppEntry appEntry = mock(AppEntry.class); @@ -324,7 +325,7 @@ public final class AppInfoDashboardFragmentTest { @Test public void startAppInfoFragment_includesNewAndOldArgs() { final SettingsPreferenceFragment caller = mock(SettingsPreferenceFragment.class); - final SettingsActivity sa = mock (SettingsActivity.class); + final SettingsActivity sa = mock(SettingsActivity.class); when(caller.getContext()).thenReturn(sa); final AppEntry appEntry = mock(AppEntry.class); appEntry.info = mock(ApplicationInfo.class); @@ -339,10 +340,10 @@ public final class AppInfoDashboardFragmentTest { verify(caller).startActivityForResult(intent.capture(), any(Integer.class)); assertThat(intent.getValue().getBundleExtra(SettingsActivity.EXTRA_SHOW_FRAGMENT_ARGUMENTS) - .containsKey("test")) - .isTrue(); + .containsKey("test")) + .isTrue(); assertThat(intent.getValue().getBundleExtra(SettingsActivity.EXTRA_SHOW_FRAGMENT_ARGUMENTS) - .containsKey(ARG_PACKAGE_NAME)) - .isTrue(); + .containsKey(ARG_PACKAGE_NAME)) + .isTrue(); } } diff --git a/tests/robotests/src/com/android/settings/applications/appinfo/AppMemoryPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/applications/appinfo/AppMemoryPreferenceControllerTest.java index 6a586d198e8..64ad32b8975 100644 --- a/tests/robotests/src/com/android/settings/applications/appinfo/AppMemoryPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/applications/appinfo/AppMemoryPreferenceControllerTest.java @@ -110,7 +110,7 @@ public class AppMemoryPreferenceControllerTest { Settings.Global.DEVELOPMENT_SETTINGS_ENABLED, 0); assertThat(mController.getAvailabilityStatus()) - .isEqualTo(BasePreferenceController.DISABLED_DEPENDENT_SETTING); + .isEqualTo(BasePreferenceController.DISABLED_UNSUPPORTED); } @Test diff --git a/tests/robotests/src/com/android/settings/applications/appinfo/PictureInPictureSettingsTest.java b/tests/robotests/src/com/android/settings/applications/appinfo/PictureInPictureSettingsTest.java index 3ea2a16e7c5..87dedade843 100644 --- a/tests/robotests/src/com/android/settings/applications/appinfo/PictureInPictureSettingsTest.java +++ b/tests/robotests/src/com/android/settings/applications/appinfo/PictureInPictureSettingsTest.java @@ -25,12 +25,13 @@ import android.content.pm.ActivityInfo; import android.content.pm.ApplicationInfo; import android.content.pm.PackageInfo; import android.content.pm.UserInfo; +import android.os.UserManager; import android.util.Pair; import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; + import com.google.common.collect.ImmutableList; import org.junit.Before; @@ -52,7 +53,7 @@ public class PictureInPictureSettingsTest { @Mock private PackageManagerWrapper mPackageManager; @Mock - private UserManagerWrapper mUserManager; + private UserManager mUserManager; private ArrayList mPrimaryUserPackages; private ArrayList mProfileUserPackages; diff --git a/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbBackendTest.java b/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbBackendTest.java index 0823fe0bebd..567b072fdda 100644 --- a/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbBackendTest.java +++ b/tests/robotests/src/com/android/settings/connecteddevice/usb/UsbBackendTest.java @@ -18,6 +18,8 @@ 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.ArgumentMatchers.any; +import static org.mockito.ArgumentMatchers.eq; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; @@ -27,9 +29,10 @@ import android.hardware.usb.UsbManager; import android.hardware.usb.UsbPort; import android.hardware.usb.UsbPortStatus; import android.net.ConnectivityManager; +import android.os.UserHandle; +import android.os.UserManager; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.UserManagerWrapper; import org.junit.Before; import org.junit.Test; @@ -45,7 +48,7 @@ public class UsbBackendTest { @Mock private UsbManager mUsbManager; @Mock - private UserManagerWrapper mUserManagerWrapper; + private UserManager mUserManager; @Mock private ConnectivityManager mConnectivityManager; @Mock @@ -68,7 +71,7 @@ public class UsbBackendTest { @Test public void setDataRole_allRolesSupported_shouldSetDataRole() { - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); when(mUsbPortStatus .isRoleCombinationSupported(UsbPort.POWER_ROLE_SINK, UsbPort.DATA_ROLE_DEVICE)) @@ -91,7 +94,7 @@ public class UsbBackendTest { @Test public void setDataRole_notAllRolesSupported_shouldSetDataAndPowerRole() { - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); when(mUsbPortStatus .isRoleCombinationSupported(UsbPort.POWER_ROLE_SINK, UsbPort.DATA_ROLE_DEVICE)) @@ -109,7 +112,7 @@ public class UsbBackendTest { @Test public void setPowerRole_allRolesSupported_shouldSetPowerRole() { - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); when(mUsbPortStatus .isRoleCombinationSupported(UsbPort.POWER_ROLE_SINK, UsbPort.DATA_ROLE_DEVICE)) @@ -133,7 +136,7 @@ public class UsbBackendTest { @Test public void setPowerRole_notAllRolesSupported_shouldSetDataAndPowerRole() { - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); when(mUsbPortStatus .isRoleCombinationSupported(UsbPort.POWER_ROLE_SINK, UsbPort.DATA_ROLE_DEVICE)) @@ -151,20 +154,26 @@ public class UsbBackendTest { @Test public void areFunctionsSupported_fileTransferDisallowed_shouldReturnFalse() { - when(mUserManagerWrapper.isUsbFileTransferRestricted()).thenReturn(true); - when(mUserManagerWrapper.isUsbFileTransferRestrictedBySystem()).thenReturn(true); + when(mUserManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER)) + .thenReturn(true); + when(mUserManager.hasBaseUserRestriction( + eq(UserManager.DISALLOW_USB_FILE_TRANSFER), any(UserHandle.class))) + .thenReturn(true); - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); assertThat(usbBackend.areFunctionsSupported(UsbManager.FUNCTION_MTP)).isFalse(); } @Test public void areFunctionsSupported_fileTransferAllowed_shouldReturnTrue() { - when(mUserManagerWrapper.isUsbFileTransferRestricted()).thenReturn(false); - when(mUserManagerWrapper.isUsbFileTransferRestrictedBySystem()).thenReturn(false); + when(mUserManager.hasUserRestriction(UserManager.DISALLOW_USB_FILE_TRANSFER)) + .thenReturn(false); + when(mUserManager.hasBaseUserRestriction( + eq(UserManager.DISALLOW_USB_FILE_TRANSFER), any(UserHandle.class))) + .thenReturn(false); - final UsbBackend usbBackend = new UsbBackend(mContext, mUserManagerWrapper); + final UsbBackend usbBackend = new UsbBackend(mContext, mUserManager); assertThat(usbBackend.areFunctionsSupported(UsbManager.FUNCTION_MTP)).isTrue(); } diff --git a/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java index 34fbb013595..3074d9e0d5b 100644 --- a/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/core/BasePreferenceControllerTest.java @@ -21,27 +21,37 @@ import static com.android.settings.core.BasePreferenceController.DISABLED_FOR_US 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.ArgumentMatchers.anyString; +import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; +import android.content.Context; + import com.android.settings.slices.SliceData; 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.MockitoAnnotations; import org.robolectric.RuntimeEnvironment; +import android.support.v7.preference.Preference; +import android.support.v7.preference.PreferenceGroup; +import android.support.v7.preference.PreferenceScreen; + @RunWith(SettingsRobolectricTestRunner.class) public class BasePreferenceControllerTest { - @Mock - private BasePreferenceController mPreferenceController; + private final String KEY = "fake_key"; + + private Context mContext; + private FakeBasePreferenceController mPreferenceController; @Before public void setUp() { - MockitoAnnotations.initMocks(this); + mContext = RuntimeEnvironment.application; + mPreferenceController = new FakeBasePreferenceController(mContext, KEY); } @@ -57,70 +67,70 @@ public class BasePreferenceControllerTest { @Test public void isAvailable_availableStatusAvailable_returnsTrue() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(AVAILABLE); + mPreferenceController.setAvailability(AVAILABLE); assertThat(mPreferenceController.isAvailable()).isTrue(); } @Test public void isAvailable_availableStatusUnsupported_returnsFalse() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_UNSUPPORTED); + mPreferenceController.setAvailability(DISABLED_UNSUPPORTED); assertThat(mPreferenceController.isAvailable()).isFalse(); } @Test - public void isAvailable_availableStatusDisabled_returnsFalse() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_FOR_USER); + public void isAvailable_availableStatusDisabledForUser_returnsFalse() { + mPreferenceController.setAvailability(DISABLED_FOR_USER); assertThat(mPreferenceController.isAvailable()).isFalse(); } @Test public void isAvailable_availableStatusBlockedDependent_returnsFalse() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_DEPENDENT_SETTING); + mPreferenceController.setAvailability(DISABLED_DEPENDENT_SETTING); - assertThat(mPreferenceController.isAvailable()).isFalse(); + assertThat(mPreferenceController.isAvailable()).isTrue(); } @Test public void isAvailable_availableStatusUnavailable_returnsFalse() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(UNAVAILABLE_UNKNOWN); + mPreferenceController.setAvailability(UNAVAILABLE_UNKNOWN); assertThat(mPreferenceController.isAvailable()).isFalse(); } @Test public void isSupported_availableStatusAvailable_returnsTrue() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(AVAILABLE); + mPreferenceController.setAvailability(AVAILABLE); assertThat(mPreferenceController.isSupported()).isTrue(); } @Test public void isSupported_availableStatusUnsupported_returnsFalse() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_UNSUPPORTED); + mPreferenceController.setAvailability(DISABLED_UNSUPPORTED); assertThat(mPreferenceController.isSupported()).isFalse(); } @Test - public void isSupported_availableStatusDisabled_returnsTrue() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_FOR_USER); + public void isSupported_availableStatusDisabledForUser_returnsTrue() { + mPreferenceController.setAvailability(DISABLED_FOR_USER); assertThat(mPreferenceController.isSupported()).isTrue(); } @Test public void isSupported_availableStatusDependentSetting_returnsTrue() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(DISABLED_DEPENDENT_SETTING); + mPreferenceController.setAvailability(DISABLED_DEPENDENT_SETTING); assertThat(mPreferenceController.isSupported()).isTrue(); } @Test public void isSupported_availableStatusUnavailable_returnsTrue() { - when(mPreferenceController.getAvailabilityStatus()).thenReturn(UNAVAILABLE_UNKNOWN); + mPreferenceController.setAvailability(UNAVAILABLE_UNKNOWN); assertThat(mPreferenceController.isSupported()).isTrue(); } @@ -129,4 +139,48 @@ public class BasePreferenceControllerTest { public void getSliceType_shouldReturnIntent() { assertThat(mPreferenceController.getSliceType()).isEqualTo(SliceData.SliceType.INTENT); } + + @Test + public void settingAvailable_disabledOnDisplayPreference_preferenceEnabled() { + final PreferenceScreen screen = mock(PreferenceScreen.class); + final Preference preference = new Preference(mContext); + preference.setEnabled(true); + when(screen.findPreference(anyString())).thenReturn(preference); + + mPreferenceController.displayPreference(screen); + + assertThat(preference.isEnabled()).isTrue(); + } + + @Test + public void disabledDependentSetting_disabledOnDisplayPreference_preferenceDisabled() { + final PreferenceScreen screen = mock(PreferenceScreen.class); + final Preference preference = new Preference(mContext); + preference.setEnabled(true); + when(screen.findPreference(anyString())).thenReturn(preference); + mPreferenceController.setAvailability(DISABLED_DEPENDENT_SETTING); + + mPreferenceController.displayPreference(screen); + + assertThat(preference.isEnabled()).isFalse(); + } + + private class FakeBasePreferenceController extends BasePreferenceController { + + public int mAvailable; + + public FakeBasePreferenceController(Context context, String preferenceKey) { + super(context, preferenceKey); + mAvailable = AVAILABLE; + } + + @Override + public int getAvailabilityStatus() { + return mAvailable; + } + + public void setAvailability(int availability) { + mAvailable = availability; + } + } } \ No newline at end of file diff --git a/tests/robotests/src/com/android/settings/deviceinfo/storage/SecondaryUserControllerTest.java b/tests/robotests/src/com/android/settings/deviceinfo/storage/SecondaryUserControllerTest.java index 49f03126472..bbe92add084 100644 --- a/tests/robotests/src/com/android/settings/deviceinfo/storage/SecondaryUserControllerTest.java +++ b/tests/robotests/src/com/android/settings/deviceinfo/storage/SecondaryUserControllerTest.java @@ -26,13 +26,13 @@ import static org.mockito.Mockito.when; import android.content.Context; import android.content.pm.UserInfo; import android.graphics.drawable.Drawable; +import android.os.UserManager; import android.support.v7.preference.Preference; import android.support.v7.preference.PreferenceGroup; import android.support.v7.preference.PreferenceScreen; import android.util.SparseArray; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.core.AbstractPreferenceController; import com.android.settingslib.drawable.UserIconDrawable; @@ -54,7 +54,7 @@ public class SecondaryUserControllerTest { private static final String TEST_NAME = "Fred"; private static final String TARGET_PREFERENCE_GROUP_KEY = "pref_secondary_users"; @Mock - private UserManagerWrapper mUserManager; + private UserManager mUserManager; @Mock private PreferenceScreen mScreen; @Mock diff --git a/tests/robotests/src/com/android/settings/deviceinfo/storage/UserProfileControllerTest.java b/tests/robotests/src/com/android/settings/deviceinfo/storage/UserProfileControllerTest.java index 84456ec728e..7ee62160d46 100644 --- a/tests/robotests/src/com/android/settings/deviceinfo/storage/UserProfileControllerTest.java +++ b/tests/robotests/src/com/android/settings/deviceinfo/storage/UserProfileControllerTest.java @@ -35,7 +35,6 @@ import com.android.settings.SettingsActivity; import com.android.settings.SubSettings; import com.android.settings.deviceinfo.StorageProfileFragment; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.drawable.UserIconDrawable; @@ -52,8 +51,6 @@ public class UserProfileControllerTest { private static final String TEST_NAME = "Fred"; - @Mock - private UserManagerWrapper mUserManager; @Mock private PreferenceScreen mScreen; @@ -66,7 +63,7 @@ public class UserProfileControllerTest { MockitoAnnotations.initMocks(this); mContext = spy(RuntimeEnvironment.application); mPrimaryProfile = new UserInfo(); - mController = new UserProfileController(mContext, mPrimaryProfile, mUserManager, 0); + mController = new UserProfileController(mContext, mPrimaryProfile, 0); when(mScreen.getContext()).thenReturn(mContext); mPrimaryProfile.name = TEST_NAME; mPrimaryProfile.id = 10; @@ -96,7 +93,7 @@ public class UserProfileControllerTest { final Intent intent = intentCaptor.getValue(); assertThat(intent.getComponent().getClassName()).isEqualTo(SubSettings.class.getName()); assertThat(intent.getStringExtra(SettingsActivity.EXTRA_SHOW_FRAGMENT)) - .isEqualTo(StorageProfileFragment.class.getName()); + .isEqualTo(StorageProfileFragment.class.getName()); } @Test diff --git a/tests/robotests/src/com/android/settings/display/TimeoutPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/display/TimeoutPreferenceControllerTest.java index 0362b5b93c9..8627d5f1f1e 100644 --- a/tests/robotests/src/com/android/settings/display/TimeoutPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/display/TimeoutPreferenceControllerTest.java @@ -33,7 +33,7 @@ import android.provider.Settings; import com.android.settings.TimeoutListPreference; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.testutils.shadow.ShadowDevicePolicyManagerWrapper; +import com.android.settings.testutils.shadow.ShadowDevicePolicyManager; import com.android.settingslib.RestrictedLockUtils.EnforcedAdmin; import org.junit.Before; @@ -50,7 +50,7 @@ import java.util.Collections; import java.util.List; @RunWith(SettingsRobolectricTestRunner.class) -@Config(shadows = ShadowDevicePolicyManagerWrapper.class) +@Config(shadows = ShadowDevicePolicyManager.class) public class TimeoutPreferenceControllerTest { private static final int TIMEOUT = 30; @@ -93,7 +93,7 @@ public class TimeoutPreferenceControllerTest { final int profileUserId = UserHandle.myUserId(); final long timeout = 10000; when(mUserManager.getProfiles(profileUserId)).thenReturn(Collections.emptyList()); - ShadowDevicePolicyManagerWrapper.setMaximumTimeToLock(profileUserId, timeout); + ShadowDevicePolicyManager.getShadow().setMaximumTimeToLock(profileUserId, timeout); mController.updateState(mPreference); verify(mPreference).removeUnusableTimeouts(timeout, null); @@ -104,7 +104,7 @@ public class TimeoutPreferenceControllerTest { final int profileUserId = UserHandle.myUserId(); final long timeout = 100; when(mUserManager.getProfiles(profileUserId)).thenReturn(Collections.emptyList()); - ShadowDevicePolicyManagerWrapper.setMaximumTimeToLock(profileUserId, timeout); + ShadowDevicePolicyManager.getShadow().setMaximumTimeToLock(profileUserId, timeout); int userId = UserHandle.myUserId(); List enforcingUsers = new ArrayList<>(); @@ -124,8 +124,8 @@ public class TimeoutPreferenceControllerTest { ArgumentCaptor adminCaptor = ArgumentCaptor.forClass(EnforcedAdmin.class); verify(mPreference, times(2)) - .removeUnusableTimeouts(longCaptor.capture(), adminCaptor.capture()); - assertEquals(0, (long)longCaptor.getValue()); + .removeUnusableTimeouts(longCaptor.capture(), adminCaptor.capture()); + assertEquals(0, (long) longCaptor.getValue()); assertTrue(adminCaptor.getValue() != null); } } diff --git a/tests/robotests/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelperTest.java b/tests/robotests/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelperTest.java index 981ce135d7c..32926b4cb93 100644 --- a/tests/robotests/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelperTest.java +++ b/tests/robotests/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelperTest.java @@ -94,7 +94,7 @@ public class ActionDisabledByAdminDialogHelperTest { mHelper.showAdminPolicies(admin, mActivity); final Intent intent = mActivityShadow.getNextStartedActivity(); assertEquals(intent.getComponent(), new ComponentName(mActivity, - Settings.DeviceAdminSettingsActivity.class.getName())); + Settings.DeviceAdminSettingsActivity.class.getName())); } @Test @@ -139,9 +139,7 @@ public class ActionDisabledByAdminDialogHelperTest { @Test public void testSetAdminSupportDetails() { - final DevicePolicyManager dpm = RuntimeEnvironment.application.getSystemService( - DevicePolicyManager.class); - final ShadowDevicePolicyManager dpmShadow = Shadow.extract(dpm); + final ShadowDevicePolicyManager dpmShadow = ShadowDevicePolicyManager.getShadow(); final UserManager userManager = RuntimeEnvironment.application.getSystemService( UserManager.class); final ShadowUserManager userManagerShadow = Shadow.extract(userManager); @@ -165,9 +163,7 @@ public class ActionDisabledByAdminDialogHelperTest { @Test public void testSetAdminSupportDetailsNotAdmin() { - final DevicePolicyManager dpm = RuntimeEnvironment.application.getSystemService( - DevicePolicyManager.class); - final ShadowDevicePolicyManager dpmShadow = Shadow.extract(dpm); + final ShadowDevicePolicyManager dpmShadow = ShadowDevicePolicyManager.getShadow(); final UserManager userManager = RuntimeEnvironment.application.getSystemService( UserManager.class); final ShadowUserManager userManagerShadow = Shadow.extract(userManager); diff --git a/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java b/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java index ddbd3d48ba0..b71a35eb277 100644 --- a/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java +++ b/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java @@ -21,6 +21,7 @@ import static org.mockito.Mockito.mock; import static org.mockito.Mockito.reset; import static org.mockito.Mockito.when; +import android.app.admin.DevicePolicyManager; import android.content.ComponentName; import android.content.Context; import android.content.pm.ApplicationInfo; @@ -36,7 +37,6 @@ import android.text.SpannableStringBuilder; import com.android.settings.R; import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.wrapper.ConnectivityManagerWrapper; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.wrapper.PackageManagerWrapper; import org.junit.Before; @@ -68,7 +68,7 @@ public class EnterprisePrivacyFeatureProviderImplTest { private List mProfiles = new ArrayList<>(); private @Mock Context mContext; - private @Mock DevicePolicyManagerWrapper mDevicePolicyManager; + private @Mock DevicePolicyManager mDevicePolicyManager; private @Mock PackageManagerWrapper mPackageManagerWrapper; private @Mock PackageManager mPackageManager; private @Mock UserManager mUserManager; diff --git a/tests/robotests/src/com/android/settings/fuelgauge/AppButtonsPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/fuelgauge/AppButtonsPreferenceControllerTest.java index eebccd8bfd9..551cb3e0bb0 100644 --- a/tests/robotests/src/com/android/settings/fuelgauge/AppButtonsPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/fuelgauge/AppButtonsPreferenceControllerTest.java @@ -34,6 +34,7 @@ import static org.mockito.Mockito.when; import android.app.ActivityManager; import android.app.Application; import android.app.Fragment; +import android.app.admin.DevicePolicyManager; import android.content.Context; import android.content.Intent; import android.content.pm.ApplicationInfo; @@ -46,7 +47,6 @@ import com.android.settings.SettingsActivity; import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.widget.ActionButtonPreference; import com.android.settings.widget.ActionButtonPreferenceTest; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.applications.AppUtils; import com.android.settingslib.applications.ApplicationsState; import com.android.settingslib.applications.instantapps.InstantAppDataProvider; @@ -87,7 +87,7 @@ public class AppButtonsPreferenceControllerTest { @Mock private PackageManager mPackageManger; @Mock - private DevicePolicyManagerWrapper mDpm; + private DevicePolicyManager mDpm; @Mock private ActivityManager mAm; @Mock @@ -367,7 +367,7 @@ public class AppButtonsPreferenceControllerTest { * {@link ButtonActionDialogFragment.AppButtonsDialogListener} */ public static class TestFragment extends Fragment - implements ButtonActionDialogFragment.AppButtonsDialogListener { + implements ButtonActionDialogFragment.AppButtonsDialogListener { @Override public void handleDialogClick(int type) { diff --git a/tests/robotests/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceControllerTest.java index 9cd4b8ea823..5e045c1bb1e 100644 --- a/tests/robotests/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/fuelgauge/BackgroundActivityPreferenceControllerTest.java @@ -38,7 +38,6 @@ import com.android.settings.R; import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.shadow.SettingsShadowResources; import com.android.settings.testutils.shadow.ShadowFragment; -import com.android.settings.wrapper.DevicePolicyManagerWrapper; import com.android.settingslib.fuelgauge.PowerWhitelistBackend; import org.junit.Before; @@ -74,7 +73,7 @@ public class BackgroundActivityPreferenceControllerTest { @Mock private DevicePolicyManager mDevicePolicyManager; @Mock - private DevicePolicyManagerWrapper mDevicePolicyManagerWrapper; + private DevicePolicyManager mDevicePolicyManagerWrapper; @Mock(answer = Answers.RETURNS_DEEP_STUBS) private AdvancedPowerUsageDetail mFragment; @Mock diff --git a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobServiceTest.java b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobServiceTest.java index 0e7fbc5fe2d..a39276df44f 100644 --- a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobServiceTest.java +++ b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyCleanupJobServiceTest.java @@ -18,10 +18,16 @@ package com.android.settings.fuelgauge.batterytip; import static com.google.common.truth.Truth.assertThat; import static org.junit.Assert.assertEquals; +import static org.mockito.Matchers.any; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.times; +import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; import static org.robolectric.RuntimeEnvironment.application; import android.app.job.JobInfo; import android.app.job.JobScheduler; +import android.content.Context; import com.android.settings.R; import com.android.settings.testutils.SettingsRobolectricTestRunner; @@ -30,6 +36,7 @@ import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; import org.robolectric.Shadows; import org.robolectric.shadows.ShadowJobScheduler; @@ -38,23 +45,39 @@ import java.util.concurrent.TimeUnit; @RunWith(SettingsRobolectricTestRunner.class) public class AnomalyCleanupJobServiceTest { + private Context mContext; + private JobScheduler mJobScheduler; + @Before public void setUp() { MockitoAnnotations.initMocks(this); + + mContext = spy(RuntimeEnvironment.application); + mJobScheduler = spy(mContext.getSystemService(JobScheduler.class)); + when(mContext.getSystemService(JobScheduler.class)).thenReturn(mJobScheduler); } @Test public void testScheduleCleanUp() { - AnomalyCleanupJobService.scheduleCleanUp(application); + AnomalyCleanupJobService.scheduleCleanUp(mContext); ShadowJobScheduler shadowJobScheduler = - Shadows.shadowOf(application.getSystemService(JobScheduler.class)); + Shadows.shadowOf(mContext.getSystemService(JobScheduler.class)); List pendingJobs = shadowJobScheduler.getAllPendingJobs(); assertEquals(1, pendingJobs.size()); JobInfo pendingJob = pendingJobs.get(0); - assertThat(pendingJob.getId()).isEqualTo(R.id.job_anomaly_clean_up); + assertThat(pendingJob.getId()).isEqualTo(R.integer.job_anomaly_clean_up); assertThat(pendingJob.getIntervalMillis()).isEqualTo(TimeUnit.DAYS.toMillis(1)); assertThat(pendingJob.isRequireDeviceIdle()).isTrue(); assertThat(pendingJob.isRequireCharging()).isTrue(); + assertThat(pendingJob.isPersisted()).isTrue(); + } + + @Test + public void testScheduleCleanUp_invokeTwice_onlyScheduleOnce() { + AnomalyCleanupJobService.scheduleCleanUp(mContext); + AnomalyCleanupJobService.scheduleCleanUp(mContext); + + verify(mJobScheduler, times(1)).schedule(any()); } } diff --git a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobServiceTest.java b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobServiceTest.java index e1b85aaddb1..90af7b17c2a 100644 --- a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobServiceTest.java +++ b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobServiceTest.java @@ -25,7 +25,9 @@ import static org.mockito.Matchers.anyString; import static org.mockito.Matchers.eq; import static org.mockito.Mockito.doReturn; import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; +import static org.mockito.Mockito.when; import static org.robolectric.RuntimeEnvironment.application; import android.app.StatsManager; @@ -43,6 +45,7 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; import org.robolectric.Shadows; import org.robolectric.shadows.ShadowJobScheduler; @@ -57,12 +60,18 @@ public class AnomalyConfigJobServiceTest { @Mock private StatsManager mStatsManager; + private Context mContext; + private JobScheduler mJobScheduler; private AnomalyConfigJobService mJobService; @Before public void setUp() { MockitoAnnotations.initMocks(this); + mContext = spy(RuntimeEnvironment.application); + mJobScheduler = spy(mContext.getSystemService(JobScheduler.class)); + when(mContext.getSystemService(JobScheduler.class)).thenReturn(mJobScheduler); + mJobService = spy(new AnomalyConfigJobService()); doReturn(application.getSharedPreferences(AnomalyConfigJobService.PREF_DB, Context.MODE_PRIVATE)).when(mJobService).getSharedPreferences(anyString(), @@ -71,18 +80,27 @@ public class AnomalyConfigJobServiceTest { } @Test - public void testScheduleCleanUp() { - AnomalyConfigJobService.scheduleConfigUpdate(application); + public void testScheduleConfigUpdate() { + AnomalyConfigJobService.scheduleConfigUpdate(mContext); ShadowJobScheduler shadowJobScheduler = - Shadows.shadowOf(application.getSystemService(JobScheduler.class)); + Shadows.shadowOf(mContext.getSystemService(JobScheduler.class)); List pendingJobs = shadowJobScheduler.getAllPendingJobs(); assertEquals(1, pendingJobs.size()); JobInfo pendingJob = pendingJobs.get(0); - assertThat(pendingJob.getId()).isEqualTo(R.id.job_anomaly_config_update); + assertThat(pendingJob.getId()).isEqualTo(R.integer.job_anomaly_config_update); assertThat(pendingJob.getIntervalMillis()).isEqualTo(TimeUnit.DAYS.toMillis(1)); assertThat(pendingJob.isRequireDeviceIdle()).isTrue(); assertThat(pendingJob.isRequireCharging()).isTrue(); + assertThat(pendingJob.isPersisted()).isTrue(); + } + + @Test + public void testScheduleConfigUpdate_invokeTwice_onlyScheduleOnce() { + AnomalyConfigJobService.scheduleConfigUpdate(mContext); + AnomalyConfigJobService.scheduleConfigUpdate(mContext); + + verify(mJobScheduler, times(1)).schedule(any()); } @Test diff --git a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java index efc20e957d9..0894b66719a 100644 --- a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java +++ b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java @@ -113,7 +113,7 @@ public class AnomalyDetectionJobServiceTest { assertThat(pendingJobs).hasSize(1); JobInfo pendingJob = pendingJobs.get(0); - assertThat(pendingJob.getId()).isEqualTo(R.id.job_anomaly_detection); + assertThat(pendingJob.getId()).isEqualTo(R.integer.job_anomaly_detection); assertThat(pendingJob.getMaxExecutionDelayMillis()) .isEqualTo(TimeUnit.MINUTES.toMillis(30)); } diff --git a/tests/robotests/src/com/android/settings/network/NetworkDashboardFragmentTest.java b/tests/robotests/src/com/android/settings/network/NetworkDashboardFragmentTest.java index 19c9f872eb6..51722e5e55a 100644 --- a/tests/robotests/src/com/android/settings/network/NetworkDashboardFragmentTest.java +++ b/tests/robotests/src/com/android/settings/network/NetworkDashboardFragmentTest.java @@ -76,9 +76,7 @@ public class NetworkDashboardFragmentTest { public void testPrepareActionBar_networkResetShouldBeCreated() { final NetworkResetActionMenuController resetController = mock(NetworkResetActionMenuController.class); - final PrivateDnsMenuController privateDnsController = mock(PrivateDnsMenuController.class); ReflectionHelpers.setField(mFragment, "mNetworkResetController", resetController); - ReflectionHelpers.setField(mFragment, "mPrivateDnsMenuController", privateDnsController); mFragment.onCreateOptionsMenu(null, null); diff --git a/tests/robotests/src/com/android/settings/network/PrivateDnsMenuControllerTest.java b/tests/robotests/src/com/android/settings/network/PrivateDnsMenuControllerTest.java deleted file mode 100644 index fa824d6c155..00000000000 --- a/tests/robotests/src/com/android/settings/network/PrivateDnsMenuControllerTest.java +++ /dev/null @@ -1,65 +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.network; - -import static org.mockito.Matchers.any; -import static org.mockito.Matchers.anyInt; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.when; - -import android.app.FragmentManager; -import android.view.Menu; -import android.view.MenuItem; - -import com.android.settings.R; -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.MockitoAnnotations; - -@RunWith(SettingsRobolectricTestRunner.class) -public class PrivateDnsMenuControllerTest { - private static final int MENU_ID = 0; - - private PrivateDnsMenuController mController; - @Mock - private Menu mMenu; - @Mock - private MenuItem mMenuItem; - @Mock - private FragmentManager mFragmentManager; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mController = new PrivateDnsMenuController(mFragmentManager, MENU_ID); - when(mMenu.add(anyInt(), anyInt(), anyInt(), anyInt())).thenReturn(mMenuItem); - } - - @Test - public void buildMenuItem_available_shouldAddToMenu() { - mController.buildMenuItem(mMenu); - - verify(mMenu).add(0 /* groupId */, MENU_ID, 0 /* order */, - R.string.select_private_dns_configuration_title); - verify(mMenuItem).setOnMenuItemClickListener(any(MenuItem.OnMenuItemClickListener.class)); - } -} diff --git a/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogFragmentTest.java b/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogFragmentTest.java deleted file mode 100644 index d490968ca62..00000000000 --- a/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogFragmentTest.java +++ /dev/null @@ -1,117 +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.network; - -import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_OFF; -import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC; -import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_PROVIDER_HOSTNAME; -import static com.google.common.truth.Truth.assertThat; -import static org.mockito.Mockito.doReturn; -import static org.mockito.Mockito.spy; - -import android.content.Context; -import android.provider.Settings; -import android.widget.Button; - -import com.android.settings.R; -import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.testutils.shadow.ShadowHelpUtils; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.MockitoAnnotations; -import org.robolectric.RuntimeEnvironment; -import org.robolectric.annotation.Config; - -@RunWith(SettingsRobolectricTestRunner.class) -@Config(shadows = ShadowHelpUtils.class) -public class PrivateDnsModeDialogFragmentTest { - - private static final String HOST_NAME = "192.168.1.1"; - private static final String INVALID_HOST_NAME = "...,"; - - private Context mContext; - private PrivateDnsModeDialogFragment mFragment; - private Button mSaveButton; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mContext = RuntimeEnvironment.application; - mSaveButton = new Button(mContext); - - mFragment = spy(new PrivateDnsModeDialogFragment()); - doReturn(mContext).when(mFragment).getContext(); - mFragment.onCreateDialog(null); - mFragment.mSaveButton = mSaveButton; - } - - @Test - public void testOnCheckedChanged_dnsModeOff_disableEditText() { - mFragment.onCheckedChanged(null, R.id.private_dns_mode_off); - - assertThat(mFragment.mMode).isEqualTo(PRIVATE_DNS_MODE_OFF); - assertThat(mFragment.mEditText.isEnabled()).isFalse(); - } - - @Test - public void testOnCheckedChanged_dnsModeOpportunistic_disableEditText() { - mFragment.onCheckedChanged(null, R.id.private_dns_mode_opportunistic); - - assertThat(mFragment.mMode).isEqualTo(PRIVATE_DNS_MODE_OPPORTUNISTIC); - assertThat(mFragment.mEditText.isEnabled()).isFalse(); - } - - @Test - public void testOnCheckedChanged_dnsModeProvider_enableEditText() { - mFragment.onCheckedChanged(null, R.id.private_dns_mode_provider); - - assertThat(mFragment.mMode).isEqualTo(PRIVATE_DNS_MODE_PROVIDER_HOSTNAME); - assertThat(mFragment.mEditText.isEnabled()).isTrue(); - } - - @Test - public void testOnCreateDialog_containsCorrectData() { - Settings.Global.putString(mContext.getContentResolver(), - PrivateDnsModeDialogFragment.MODE_KEY, PRIVATE_DNS_MODE_OPPORTUNISTIC); - Settings.Global.putString(mContext.getContentResolver(), - PrivateDnsModeDialogFragment.HOSTNAME_KEY, HOST_NAME); - - mFragment.onCreateDialog(null); - - assertThat(mFragment.mEditText.getText().toString()).isEqualTo(HOST_NAME); - assertThat(mFragment.mRadioGroup.getCheckedRadioButtonId()).isEqualTo( - R.id.private_dns_mode_opportunistic); - } - - @Test - public void testOnCheckedChanged_switchMode_saveButtonHasCorrectState() { - // Set invalid hostname - mFragment.mEditText.setText(INVALID_HOST_NAME); - - mFragment.onCheckedChanged(null, R.id.private_dns_mode_opportunistic); - assertThat(mSaveButton.isEnabled()).isTrue(); - - mFragment.onCheckedChanged(null, R.id.private_dns_mode_provider); - assertThat(mSaveButton.isEnabled()).isFalse(); - - mFragment.onCheckedChanged(null, R.id.private_dns_mode_off); - assertThat(mSaveButton.isEnabled()).isTrue(); - } -} diff --git a/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java b/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java new file mode 100644 index 00000000000..8a60cf3a033 --- /dev/null +++ b/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java @@ -0,0 +1,137 @@ +/* + * 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.network; + +import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_OFF; +import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC; +import static android.net.ConnectivityManager.PRIVATE_DNS_MODE_PROVIDER_HOSTNAME; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Mockito.anyInt; +import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.mock; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.when; + +import android.app.AlertDialog; +import android.app.Fragment; +import android.content.Context; +import android.provider.Settings; +import android.view.LayoutInflater; +import android.view.View; +import android.widget.Button; +import android.widget.LinearLayout; + +import com.android.settings.R; +import com.android.settingslib.CustomDialogPreference.CustomPreferenceDialogFragment; +import com.android.settings.testutils.SettingsRobolectricTestRunner; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; +import org.robolectric.util.ReflectionHelpers; + +@RunWith(SettingsRobolectricTestRunner.class) +public class PrivateDnsModeDialogPreferenceTest { + + private static final String HOST_NAME = "dns.example.com"; + private static final String INVALID_HOST_NAME = "...,"; + + private PrivateDnsModeDialogPreference mPreference; + + private Context mContext; + private Button mSaveButton; + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + + mContext = RuntimeEnvironment.application; + mSaveButton = new Button(mContext); + + final CustomPreferenceDialogFragment fragment = mock(CustomPreferenceDialogFragment.class); + final AlertDialog dialog = mock(AlertDialog.class); + when(fragment.getDialog()).thenReturn(dialog); + when(dialog.getButton(anyInt())).thenReturn(mSaveButton); + + mPreference = new PrivateDnsModeDialogPreference(mContext); + ReflectionHelpers.setField(mPreference, "mFragment", fragment); + + final LayoutInflater inflater = LayoutInflater.from(mContext); + final View view = inflater.inflate(R.layout.private_dns_mode_dialog, + new LinearLayout(mContext), false); + + mPreference.onBindDialogView(view); + } + + @Test + public void testOnCheckedChanged_dnsModeOff_disableEditText() { + mPreference.onCheckedChanged(null, R.id.private_dns_mode_off); + + assertThat(mPreference.mMode).isEqualTo(PRIVATE_DNS_MODE_OFF); + assertThat(mPreference.mEditText.isEnabled()).isFalse(); + } + + @Test + public void testOnCheckedChanged_dnsModeOpportunistic_disableEditText() { + mPreference.onCheckedChanged(null, R.id.private_dns_mode_opportunistic); + + assertThat(mPreference.mMode).isEqualTo(PRIVATE_DNS_MODE_OPPORTUNISTIC); + assertThat(mPreference.mEditText.isEnabled()).isFalse(); + } + + @Test + public void testOnCheckedChanged_dnsModeProvider_enableEditText() { + mPreference.onCheckedChanged(null, R.id.private_dns_mode_provider); + + assertThat(mPreference.mMode).isEqualTo(PRIVATE_DNS_MODE_PROVIDER_HOSTNAME); + assertThat(mPreference.mEditText.isEnabled()).isTrue(); + } + + @Test + public void testOnBindDialogView_containsCorrectData() { + Settings.Global.putString(mContext.getContentResolver(), + PrivateDnsModeDialogPreference.MODE_KEY, PRIVATE_DNS_MODE_OPPORTUNISTIC); + Settings.Global.putString(mContext.getContentResolver(), + PrivateDnsModeDialogPreference.HOSTNAME_KEY, HOST_NAME); + + final LayoutInflater inflater = LayoutInflater.from(mContext); + final View view = inflater.inflate(R.layout.private_dns_mode_dialog, + new LinearLayout(mContext), false); + mPreference.onBindDialogView(view); + + assertThat(mPreference.mEditText.getText().toString()).isEqualTo(HOST_NAME); + assertThat(mPreference.mRadioGroup.getCheckedRadioButtonId()).isEqualTo( + R.id.private_dns_mode_opportunistic); + } + + @Test + public void testOnCheckedChanged_switchMode_saveButtonHasCorrectState() { + // Set invalid hostname + mPreference.mEditText.setText(INVALID_HOST_NAME); + + mPreference.onCheckedChanged(null, R.id.private_dns_mode_opportunistic); + assertThat(mSaveButton.isEnabled()).isTrue(); + + mPreference.onCheckedChanged(null, R.id.private_dns_mode_provider); + assertThat(mSaveButton.isEnabled()).isFalse(); + + mPreference.onCheckedChanged(null, R.id.private_dns_mode_off); + assertThat(mSaveButton.isEnabled()).isTrue(); + } +} diff --git a/tests/robotests/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceControllerTest.java index 5538b4c1d4e..2a4b335cfa3 100644 --- a/tests/robotests/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/security/screenlock/LockAfterTimeoutPreferenceControllerTest.java @@ -34,7 +34,7 @@ import com.android.settings.TimeoutListPreference; import com.android.settings.security.trustagent.TrustAgentManager; import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.testutils.shadow.ShadowDevicePolicyManagerWrapper; +import com.android.settings.testutils.shadow.ShadowDevicePolicyManager; import org.junit.Before; import org.junit.Test; @@ -47,7 +47,7 @@ import org.robolectric.annotation.Config; import java.util.Collections; @RunWith(SettingsRobolectricTestRunner.class) -@Config(shadows = ShadowDevicePolicyManagerWrapper.class) +@Config(shadows = ShadowDevicePolicyManager.class) public class LockAfterTimeoutPreferenceControllerTest { private static final int TEST_USER_ID = 0; @@ -120,11 +120,11 @@ public class LockAfterTimeoutPreferenceControllerTest { when(um.getProfiles(userId)).thenReturn(Collections.emptyList()); // Fake list of timeout values. - when(mPreference.getEntries()).thenReturn(new CharSequence[] {"10"} ); - when(mPreference.getEntryValues()).thenReturn(new CharSequence[] {"10000"} ); + when(mPreference.getEntries()).thenReturn(new CharSequence[] {"10"}); + when(mPreference.getEntryValues()).thenReturn(new CharSequence[] {"10000"}); Settings.System.putInt(mContext.getContentResolver(), SCREEN_OFF_TIMEOUT, displayTimeout); - ShadowDevicePolicyManagerWrapper.setMaximumTimeToLock(userId, adminTimeout); + ShadowDevicePolicyManager.getShadow().setMaximumTimeToLock(userId, adminTimeout); mController.updateState(mPreference); diff --git a/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManager.java b/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManager.java index 7e2c3cc7e43..16ef69981fc 100644 --- a/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManager.java +++ b/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManager.java @@ -2,33 +2,35 @@ package com.android.settings.testutils.shadow; import android.annotation.NonNull; import android.annotation.Nullable; +import android.annotation.UserIdInt; import android.app.admin.DevicePolicyManager; import android.content.ComponentName; import org.robolectric.RuntimeEnvironment; import org.robolectric.annotation.Implementation; import org.robolectric.annotation.Implements; +import org.robolectric.shadow.api.Shadow; import java.util.HashMap; import java.util.Map; import java.util.Objects; -import org.robolectric.shadow.api.Shadow; -/** - * This shadow if using {@link ShadowDevicePolicyManagerWrapper} is not possible. - */ @Implements(DevicePolicyManager.class) public class ShadowDevicePolicyManager extends org.robolectric.shadows.ShadowDevicePolicyManager { + + private final Map mProfileTimeouts = new HashMap<>(); private Map mSupportMessagesMap = new HashMap<>(); private boolean mIsAdminActiveAsUser = false; ComponentName mDeviceOwnerComponentName; + private int mDeviceOwnerUserId = -1; public void setShortSupportMessageForUser(ComponentName admin, int userHandle, String message) { mSupportMessagesMap.put(Objects.hash(admin, userHandle), message); } @Implementation - public @Nullable CharSequence getShortSupportMessageForUser(@NonNull ComponentName admin, + public @Nullable + CharSequence getShortSupportMessageForUser(@NonNull ComponentName admin, int userHandle) { return mSupportMessagesMap.get(Objects.hash(admin, userHandle)); } @@ -38,20 +40,39 @@ public class ShadowDevicePolicyManager extends org.robolectric.shadows.ShadowDev return mIsAdminActiveAsUser; } + @Implementation + public int getDeviceOwnerUserId() { + return mDeviceOwnerUserId; + } + + @Implementation + public long getMaximumTimeToLock(ComponentName admin, @UserIdInt int userHandle) { + return mProfileTimeouts.getOrDefault(userHandle, 0L); + } + + @Implementation + public ComponentName getDeviceOwnerComponentOnAnyUser() { + return mDeviceOwnerComponentName; + } + public void setIsAdminActiveAsUser(boolean active) { mIsAdminActiveAsUser = active; } - public static ShadowDevicePolicyManager getShadow() { - return (ShadowDevicePolicyManager) Shadow.extract( - RuntimeEnvironment.application.getSystemService(DevicePolicyManager.class)); + public void setDeviceOwnerUserId(int id) { + mDeviceOwnerUserId = id; } - public ComponentName getDeviceOwnerComponentOnAnyUser() { - return mDeviceOwnerComponentName; + public void setMaximumTimeToLock(@UserIdInt int userHandle, Long timeout) { + mProfileTimeouts.put(userHandle, timeout); } public void setDeviceOwnerComponentOnAnyUser(ComponentName admin) { mDeviceOwnerComponentName = admin; } + + public static ShadowDevicePolicyManager getShadow() { + return (ShadowDevicePolicyManager) Shadow.extract( + RuntimeEnvironment.application.getSystemService(DevicePolicyManager.class)); + } } diff --git a/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManagerWrapper.java b/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManagerWrapper.java deleted file mode 100644 index 5502b37f966..00000000000 --- a/tests/robotests/src/com/android/settings/testutils/shadow/ShadowDevicePolicyManagerWrapper.java +++ /dev/null @@ -1,65 +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.testutils.shadow; - -import android.annotation.UserIdInt; -import android.content.ComponentName; - -import com.android.settings.wrapper.DevicePolicyManagerWrapper; - -import org.robolectric.annotation.Implementation; -import org.robolectric.annotation.Implements; - -import java.util.HashMap; -import java.util.Map; - -/** - * Shadow for {@link DevicePolicyManagerWrapper} to allow stubbing hidden methods. - */ -@Implements(DevicePolicyManagerWrapper.class) -public class ShadowDevicePolicyManagerWrapper { - private static ComponentName deviceOComponentName = null; - private static int deviceOwnerUserId = -1; - private static final Map profileTimeouts = new HashMap<>(); - - @Implementation - public ComponentName getDeviceOwnerComponentOnAnyUser() { - return deviceOComponentName; - } - - @Implementation - public int getDeviceOwnerUserId() { - return deviceOwnerUserId; - } - - @Implementation - public long getMaximumTimeToLock(ComponentName admin, @UserIdInt int userHandle) { - return profileTimeouts.getOrDefault(userHandle, 0L); - } - - public static void setDeviceOComponentName(ComponentName deviceOComponentName) { - ShadowDevicePolicyManagerWrapper.deviceOComponentName = deviceOComponentName; - } - - public static void setDeviceOwnerUserId(int deviceOwnerUserId) { - ShadowDevicePolicyManagerWrapper.deviceOwnerUserId = deviceOwnerUserId; - } - - public static void setMaximumTimeToLock(@UserIdInt int userHandle, Long timeout) { - profileTimeouts.put(userHandle, timeout); - } -} diff --git a/tests/robotests/src/com/android/settings/wallpaper/WallpaperSuggestionActivityTest.java b/tests/robotests/src/com/android/settings/wallpaper/WallpaperSuggestionActivityTest.java index 6ebbef3fb4a..fc708eff63b 100644 --- a/tests/robotests/src/com/android/settings/wallpaper/WallpaperSuggestionActivityTest.java +++ b/tests/robotests/src/com/android/settings/wallpaper/WallpaperSuggestionActivityTest.java @@ -20,15 +20,15 @@ import static com.google.common.truth.Truth.assertThat; import static org.mockito.Mockito.when; import static org.robolectric.Shadows.shadowOf; +import android.app.WallpaperManager; import android.content.Context; import android.content.Intent; -import android.content.pm.PackageManager; import android.content.res.Resources; import com.android.settings.SubSettings; import com.android.settings.testutils.SettingsRobolectricTestRunner; -import com.android.settings.wrapper.WallpaperManagerWrapper; +import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; @@ -40,6 +40,7 @@ import org.robolectric.android.controller.ActivityController; import org.robolectric.annotation.Config; import org.robolectric.annotation.Implementation; import org.robolectric.annotation.Implements; +import org.robolectric.annotation.Resetter; import org.robolectric.shadows.ShadowActivity; import org.robolectric.shadows.ShadowPackageManager; @@ -59,10 +60,15 @@ public class WallpaperSuggestionActivityTest { mController = Robolectric.buildActivity(WallpaperSuggestionActivity.class); } + @After + public void tearDown() { + ShadowWallpaperManager.reset(); + } + @Test public void launch_primarySuggestionActivityDoesNotExist_shouldFallback() { ShadowPackageManager packageManager = - shadowOf(RuntimeEnvironment.application.getPackageManager()); + shadowOf(RuntimeEnvironment.application.getPackageManager()); packageManager.removePackage("com.android.settings"); ShadowActivity activity = shadowOf(mController.setup().get()); @@ -74,32 +80,34 @@ public class WallpaperSuggestionActivityTest { } @Test - public void wallpaperServiceEnabled_no_shouldReturnFalse() { + public void wallpaperServiceEnabled_no_shouldReturnTrue() { when(mContext.getResources()).thenReturn(mResources); when(mResources.getBoolean(com.android.internal.R.bool.config_enableWallpaperService)) - .thenReturn(false); - - assertThat(WallpaperSuggestionActivity.isSuggestionComplete(mContext)).isFalse(); - } - - @Test - @Config(shadows = WallpaperSuggestionActivityTest.ShadowWallpaperManagerWrapper.class) - public void hasWallpaperSet_no_shouldReturnFalse() { - ShadowWallpaperManagerWrapper.setWallpaperId(0); - - assertThat(WallpaperSuggestionActivity.isSuggestionComplete(mContext)).isFalse(); - } - - @Test - @Config(shadows = WallpaperSuggestionActivityTest.ShadowWallpaperManagerWrapper.class) - public void hasWallpaperSet_yes_shouldReturnTrue() { - ShadowWallpaperManagerWrapper.setWallpaperId(100); + .thenReturn(false); assertThat(WallpaperSuggestionActivity.isSuggestionComplete(mContext)).isTrue(); } - @Implements(WallpaperManagerWrapper.class) - public static class ShadowWallpaperManagerWrapper { + @Test + @Config(shadows = ShadowWallpaperManager.class) + public void hasWallpaperSet_no_shouldReturnFalse() { + ShadowWallpaperManager.setWallpaperId(0); + + assertThat(WallpaperSuggestionActivity.isSuggestionComplete(RuntimeEnvironment.application)) + .isFalse(); + } + + @Test + @Config(shadows = ShadowWallpaperManager.class) + public void hasWallpaperSet_yes_shouldReturnTrue() { + ShadowWallpaperManager.setWallpaperId(100); + + assertThat(WallpaperSuggestionActivity.isSuggestionComplete(RuntimeEnvironment.application)) + .isTrue(); + } + + @Implements(WallpaperManager.class) + public static class ShadowWallpaperManager { private static int sWallpaperId; @@ -107,13 +115,11 @@ public class WallpaperSuggestionActivityTest { sWallpaperId = id; } + @Resetter public static void reset() { sWallpaperId = 0; } - public void __constructor__(Context context) { - } - @Implementation public boolean isWallpaperServiceEnabled() { return true; diff --git a/tests/robotests/src/com/android/settings/wifi/details/WifiDetailPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/wifi/details/WifiDetailPreferenceControllerTest.java index a0238b4a865..9c20d18aeba 100644 --- a/tests/robotests/src/com/android/settings/wifi/details/WifiDetailPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/wifi/details/WifiDetailPreferenceControllerTest.java @@ -63,7 +63,7 @@ import com.android.settings.R; import com.android.settings.applications.LayoutPreference; import com.android.settings.testutils.SettingsRobolectricTestRunner; import com.android.settings.testutils.shadow.ShadowBidiFormatter; -import com.android.settings.testutils.shadow.ShadowDevicePolicyManagerWrapper; +import com.android.settings.testutils.shadow.ShadowDevicePolicyManager; import com.android.settings.testutils.shadow.ShadowEntityHeaderController; import com.android.settings.testutils.shadow.ShadowPackageManagerWrapper; import com.android.settings.widget.ActionButtonPreference; @@ -96,10 +96,10 @@ import java.util.stream.Collectors; @RunWith(SettingsRobolectricTestRunner.class) @Config(shadows = { - ShadowDevicePolicyManagerWrapper.class, - ShadowEntityHeaderController.class, - ShadowPackageManagerWrapper.class, - ShadowBidiFormatter.class + ShadowDevicePolicyManager.class, + ShadowEntityHeaderController.class, + ShadowPackageManagerWrapper.class, + ShadowBidiFormatter.class }) public class WifiDetailPreferenceControllerTest { @@ -372,7 +372,7 @@ public class WifiDetailPreferenceControllerTest { mController.onPause(); verify(mockConnectivityManager, times(1)) - .unregisterNetworkCallback(mCallbackCaptor.getValue()); + .unregisterNetworkCallback(mCallbackCaptor.getValue()); } @Test @@ -469,16 +469,16 @@ public class WifiDetailPreferenceControllerTest { @Test public void dnsServersPref_shouldHaveDetailTextSet() throws UnknownHostException { - mLinkProperties.addDnsServer(InetAddress.getByAddress(new byte[]{8,8,4,4})); - mLinkProperties.addDnsServer(InetAddress.getByAddress(new byte[]{8,8,8,8})); + mLinkProperties.addDnsServer(InetAddress.getByAddress(new byte[] {8, 8, 4, 4})); + mLinkProperties.addDnsServer(InetAddress.getByAddress(new byte[] {8, 8, 8, 8})); mLinkProperties.addDnsServer(Constants.IPV6_DNS); displayAndResume(); verify(mockDnsPref).setDetailText( "8.8.4.4\n" + - "8.8.8.8\n" + - Constants.IPV6_DNS.getHostAddress()); + "8.8.8.8\n" + + Constants.IPV6_DNS.getHostAddress()); } @Test @@ -591,8 +591,8 @@ public class WifiDetailPreferenceControllerTest { updateLinkProperties(lp); inOrder.verify(mockDnsPref).setDetailText( Constants.IPV6_DNS.getHostAddress() + "\n" + - Constants.IPV4_DNS1.getHostAddress() + "\n" + - Constants.IPV4_DNS2.getHostAddress()); + Constants.IPV4_DNS1.getHostAddress() + "\n" + + Constants.IPV4_DNS2.getHostAddress()); inOrder.verify(mockDnsPref).setVisible(true); } @@ -693,8 +693,8 @@ public class WifiDetailPreferenceControllerTest { mockWifiConfig.creatorUid = doUid; ComponentName doComponent = new ComponentName(doPackage, "some.Class"); ShadowPackageManagerWrapper.setPackageUidAsUser(doPackage, doUserId, doUid); - ShadowDevicePolicyManagerWrapper.setDeviceOComponentName(doComponent); - ShadowDevicePolicyManagerWrapper.setDeviceOwnerUserId(doUserId); + ShadowDevicePolicyManager.getShadow().setDeviceOwnerComponentOnAnyUser(doComponent); + ShadowDevicePolicyManager.getShadow().setDeviceOwnerUserId(doUserId); Settings.Global.putInt(mContext.getContentResolver(), Settings.Global.WIFI_DEVICE_OWNER_CONFIGS_LOCKDOWN, 1); @@ -779,7 +779,7 @@ public class WifiDetailPreferenceControllerTest { displayAndResume(); - List addrs = mIpv6AddressCaptor.getAllValues(); + List addrs = mIpv6AddressCaptor.getAllValues(); String expectedAddresses = String.join("\n", asString(Constants.IPV6_LINKLOCAL), @@ -840,6 +840,7 @@ public class WifiDetailPreferenceControllerTest { verify(mockAccessPoint, times(2)).getLevel(); verify(mockIconInjector, times(1)).getIcon(anyInt()); } + @Test public void testRefreshRssiViews_shouldUpdateOnLevelChange() { displayAndResume(); diff --git a/tests/unit/src/com/android/settings/deviceinfo/storage/StorageAsyncLoaderTest.java b/tests/unit/src/com/android/settings/deviceinfo/storage/StorageAsyncLoaderTest.java index f622804c04a..d1d2b041e68 100644 --- a/tests/unit/src/com/android/settings/deviceinfo/storage/StorageAsyncLoaderTest.java +++ b/tests/unit/src/com/android/settings/deviceinfo/storage/StorageAsyncLoaderTest.java @@ -17,7 +17,6 @@ package com.android.settings.deviceinfo.storage; import static com.google.common.truth.Truth.assertThat; - import static org.mockito.Matchers.any; import static org.mockito.Matchers.anyInt; import static org.mockito.Matchers.anyString; @@ -31,11 +30,11 @@ import android.content.pm.PackageManager.NameNotFoundException; import android.content.pm.UserInfo; import android.net.TrafficStats; import android.os.UserHandle; +import android.os.UserManager; import android.support.test.filters.SmallTest; import android.support.test.runner.AndroidJUnit4; import android.util.SparseArray; -import com.android.settings.wrapper.UserManagerWrapper; import com.android.settingslib.applications.StorageStatsSource; import com.android.settingslib.wrapper.PackageManagerWrapper; @@ -65,7 +64,7 @@ public class StorageAsyncLoaderTest { @Mock private PackageManagerWrapper mPackageManager; @Mock - private UserManagerWrapper mUserManager; + private UserManager mUserManager; private List mInfo = new ArrayList<>(); private List mUsers;