Merge changes Ic2ac6a5c,I47dc068e
* changes:
[MEP] The removale slot can read the esim card
Changing the condition since the esim may be removable
diff --git a/res/layout/data_usage_bytes_editor.xml b/res/layout/data_usage_bytes_editor.xml
index a72352d..bcfc25e 100644
--- a/res/layout/data_usage_bytes_editor.xml
+++ b/res/layout/data_usage_bytes_editor.xml
@@ -38,7 +38,6 @@
android:id="@+id/size_spinner"
android:layout_width="wrap_content"
android:layout_height="match_parent"
- android:layout_gravity="center_vertical"
- android:entries="@array/bytes_picker_sizes" />
+ android:layout_gravity="center_vertical" />
</LinearLayout>
diff --git a/res/values/arrays.xml b/res/values/arrays.xml
index 0fe13fe..9f0af97 100644
--- a/res/values/arrays.xml
+++ b/res/values/arrays.xml
@@ -1180,14 +1180,14 @@
</string-array>
<!-- Array of color for sim color for multi-sim in light mode -->
- <string-array name="sim_color_light">
+ <integer-array name="sim_color_light">
<item>@color/SIM_color_cyan</item>
<item>@color/SIM_color_blue800</item>
<item>@color/SIM_color_green800</item>
<item>@color/SIM_color_purple800</item>
<item>@color/SIM_color_pink800</item>
<item>@color/SIM_color_orange</item>
- </string-array>
+ </integer-array>
<!-- Array of titles for sim color for multi-sim -->
<string-array name="color_picker">
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 019ac70..8be1a97 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -608,8 +608,10 @@
<string name="zone_info_exemplar_location_and_offset"><xliff:g id="exemplar_location" example="Los Angeles">%1$s</xliff:g> (<xliff:g id="offset" example="GMT-08:00">%2$s</xliff:g>)</string>
<!-- Label describing a time zone offset and name[CHAR LIMIT=NONE] -->
<string name="zone_info_offset_and_name"><xliff:g id="time_type" example="Pacific Time">%2$s</xliff:g> (<xliff:g id="offset" example="GMT-08:00">%1$s</xliff:g>)</string>
- <!-- Label describing a time zone and changes to DST or standard time [CHAR LIMIT=NONE] -->
- <string name="zone_info_footer">Uses <xliff:g id="offset_and_name" example="Pacific Time (GMT-08:00)">%1$s</xliff:g>. <xliff:g id="dst_time_type" example="Pacific Daylight Time">%2$s</xliff:g> starts on <xliff:g id="transition_date" example="Mar 11 2018">%3$s</xliff:g>.</string>
+ <!-- Label describing a time zone and a follow-up sentence [CHAR LIMIT=NONE] -->
+ <string name="zone_info_footer_first_sentence">Uses <xliff:g id="offset_and_name" example="Pacific Time (GMT-08:00)">%1$s</xliff:g>. <xliff:g id="second_sentence" example="Pacific Daylight Time starts on Mar 11 2018.">%2$s</xliff:g></string>
+ <!-- Label describing the upcoming daylight savings time change [CHAR LIMIT=NONE] -->
+ <string name="zone_info_footer_second_sentence"><xliff:g id="dst_time_type" example="Pacific Daylight Time">%1$s</xliff:g> starts on <xliff:g id="transition_date" example="Mar 11 2018">%2$s</xliff:g>.</string>
<!-- Label describing a time zone without DST [CHAR LIMIT=NONE] -->
<string name="zone_info_footer_no_dst">Uses <xliff:g id="offset_and_name" example="GMT-08:00 Pacific Time">%1$s</xliff:g>. No daylight savings time.</string>
<!-- Describes the time type "daylight savings time" (used in zone_change_to_from_dst, when no zone specific name is available) -->
@@ -11305,11 +11307,6 @@
<!-- Text for the setting on whether you can type text into notifications without unlocking the device. -->
<string name="lockscreen_remote_input">If device is locked, prevent typing replies or other text in notifications</string>
- <string-array name="bytes_picker_sizes" translatable="false">
- <item>@*android:string/megabyteShort</item>
- <item>@*android:string/gigabyteShort</item>
- </string-array>
-
<!-- [CHAR LIMIT=30] Label for setting to control the default spell checker -->
<string name="default_spell_checker">Default spell checker</string>
diff --git a/res/xml/development_settings.xml b/res/xml/development_settings.xml
index 0d03149..d009222 100644
--- a/res/xml/development_settings.xml
+++ b/res/xml/development_settings.xml
@@ -292,7 +292,7 @@
android:title="@string/tethering_hardware_offload"
android:summary="@string/tethering_hardware_offload_summary" />
- <com.android.settingslib.RestrictedSwitchPreference
+ <com.android.settingslib.RestrictedPreference
android:key="default_usb_configuration"
android:fragment="com.android.settings.connecteddevice.usb.UsbDefaultFragment"
android:title="@string/usb_default_label"/>
diff --git a/src/com/android/settings/bluetooth/BluetoothPairingDialogFragment.java b/src/com/android/settings/bluetooth/BluetoothPairingDialogFragment.java
index 9e36247..650267a 100644
--- a/src/com/android/settings/bluetooth/BluetoothPairingDialogFragment.java
+++ b/src/com/android/settings/bluetooth/BluetoothPairingDialogFragment.java
@@ -55,6 +55,7 @@
private BluetoothPairingController mPairingController;
private BluetoothPairingDialog mPairingDialogActivity;
private EditText mPairingView;
+ private boolean mPositiveClicked = false;
/**
* The interface we expect a listener to implement. Typically this should be done by
* the controller.
@@ -83,6 +84,14 @@
}
@Override
+ public void onDestroy() {
+ super.onDestroy();
+ if (!mPositiveClicked) {
+ mPairingController.onCancel();
+ }
+ }
+
+ @Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@@ -104,6 +113,7 @@
@Override
public void onClick(DialogInterface dialog, int which) {
if (which == DialogInterface.BUTTON_POSITIVE) {
+ mPositiveClicked = true;
mPairingController.onDialogPositiveClick(this);
} else if (which == DialogInterface.BUTTON_NEGATIVE) {
mPairingController.onDialogNegativeClick(this);
diff --git a/src/com/android/settings/datausage/BillingCycleSettings.java b/src/com/android/settings/datausage/BillingCycleSettings.java
index 57931c1..9e83e4c 100644
--- a/src/com/android/settings/datausage/BillingCycleSettings.java
+++ b/src/com/android/settings/datausage/BillingCycleSettings.java
@@ -22,6 +22,8 @@
import android.content.Context;
import android.content.DialogInterface;
import android.content.res.Resources;
+import android.icu.text.MeasureFormat;
+import android.icu.util.MeasureUnit;
import android.net.NetworkPolicy;
import android.net.NetworkTemplate;
import android.os.Bundle;
@@ -30,6 +32,7 @@
import android.view.LayoutInflater;
import android.view.View;
import android.view.inputmethod.EditorInfo;
+import android.widget.ArrayAdapter;
import android.widget.EditText;
import android.widget.NumberPicker;
import android.widget.Spinner;
@@ -301,6 +304,17 @@
: editor.getPolicyWarningBytes(template);
final long limitDisabled = isLimit ? LIMIT_DISABLED : WARNING_DISABLED;
+ final MeasureFormat formatter = MeasureFormat.getInstance(
+ getContext().getResources().getConfiguration().locale,
+ MeasureFormat.FormatWidth.SHORT);
+ final String[] unitNames = new String[] {
+ formatter.getUnitDisplayName(MeasureUnit.MEGABYTE),
+ formatter.getUnitDisplayName(MeasureUnit.GIGABYTE)
+ };
+ final ArrayAdapter<String> adapter = new ArrayAdapter<String>(
+ getContext(), android.R.layout.simple_spinner_item, unitNames);
+ type.setAdapter(adapter);
+
final boolean unitInGigaBytes = (bytes > 1.5f * GIB_IN_BYTES);
final String bytesText = formatText(bytes,
unitInGigaBytes ? GIB_IN_BYTES : MIB_IN_BYTES);
diff --git a/src/com/android/settings/datausage/DataUsageList.java b/src/com/android/settings/datausage/DataUsageList.java
index 6beb3d8..4ee6530 100644
--- a/src/com/android/settings/datausage/DataUsageList.java
+++ b/src/com/android/settings/datausage/DataUsageList.java
@@ -37,7 +37,6 @@
import android.provider.Settings;
import android.telephony.SubscriptionInfo;
import android.telephony.SubscriptionManager;
-import android.util.FeatureFlagUtils;
import android.util.Log;
import android.util.SparseArray;
import android.view.View;
@@ -49,6 +48,7 @@
import android.widget.Spinner;
import androidx.annotation.VisibleForTesting;
+import androidx.lifecycle.Lifecycle;
import androidx.loader.app.LoaderManager.LoaderCallbacks;
import androidx.loader.content.Loader;
import androidx.preference.Preference;
@@ -501,6 +501,17 @@
+ cycle.end + "]");
}
+ // Avoid from updating UI after #onStop.
+ if (!getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) {
+ return;
+ }
+
+ // Avoid from updating UI when async query still on-going.
+ // This could happen when a request from #onMobileDataEnabledChange.
+ if (mCycleData == null) {
+ return;
+ }
+
// update chart to show selected cycle, and update detail data
// to match updated sweep bounds.
mChart.setNetworkCycleData(mCycleData.get(position));
diff --git a/src/com/android/settings/datetime/timezone/RegionPreferenceController.java b/src/com/android/settings/datetime/timezone/RegionPreferenceController.java
index 53959a6..c4b47b9 100644
--- a/src/com/android/settings/datetime/timezone/RegionPreferenceController.java
+++ b/src/com/android/settings/datetime/timezone/RegionPreferenceController.java
@@ -15,6 +15,8 @@
*/
package com.android.settings.datetime.timezone;
+import static com.android.settingslib.datetime.ZoneGetter.capitalizeForStandaloneDisplay;
+
import android.content.Context;
import android.icu.text.LocaleDisplayNames;
@@ -23,19 +25,21 @@
public class RegionPreferenceController extends BaseTimeZonePreferenceController {
private static final String PREFERENCE_KEY = "region";
+ private final Locale mLocale;
private final LocaleDisplayNames mLocaleDisplayNames;
private String mRegionId = "";
public RegionPreferenceController(Context context) {
super(context, PREFERENCE_KEY);
Locale locale = context.getResources().getConfiguration().getLocales().get(0);
+ mLocale = locale;
mLocaleDisplayNames = LocaleDisplayNames.getInstance(locale);
-
}
@Override
public CharSequence getSummary() {
- return mLocaleDisplayNames.regionDisplayName(mRegionId);
+ return capitalizeForStandaloneDisplay(mLocale,
+ mLocaleDisplayNames.regionDisplayName(mRegionId));
}
public void setRegionId(String regionId) {
diff --git a/src/com/android/settings/datetime/timezone/RegionSearchPicker.java b/src/com/android/settings/datetime/timezone/RegionSearchPicker.java
index 85d5d70..3977aa9 100644
--- a/src/com/android/settings/datetime/timezone/RegionSearchPicker.java
+++ b/src/com/android/settings/datetime/timezone/RegionSearchPicker.java
@@ -16,6 +16,8 @@
package com.android.settings.datetime.timezone;
+import static com.android.settingslib.datetime.ZoneGetter.capitalizeForStandaloneDisplay;
+
import android.app.Activity;
import android.app.settings.SettingsEnums;
import android.content.Intent;
@@ -116,7 +118,8 @@
final LocaleDisplayNames localeDisplayNames = LocaleDisplayNames.getInstance(getLocale());
long i = 0;
for (String regionId : regionIds) {
- String name = localeDisplayNames.regionDisplayName(regionId);
+ String name = capitalizeForStandaloneDisplay(
+ mLocale, localeDisplayNames.regionDisplayName(regionId));
items.add(new RegionItem(i++, regionId, name));
}
return new ArrayList<>(items);
diff --git a/src/com/android/settings/datetime/timezone/RegionZonePicker.java b/src/com/android/settings/datetime/timezone/RegionZonePicker.java
index 7f988cd..1bc68a1 100644
--- a/src/com/android/settings/datetime/timezone/RegionZonePicker.java
+++ b/src/com/android/settings/datetime/timezone/RegionZonePicker.java
@@ -16,6 +16,8 @@
package com.android.settings.datetime.timezone;
+import static com.android.settingslib.datetime.ZoneGetter.capitalizeForStandaloneDisplay;
+
import android.app.settings.SettingsEnums;
import android.content.Intent;
import android.icu.text.Collator;
@@ -65,7 +67,8 @@
final LocaleDisplayNames localeDisplayNames = LocaleDisplayNames.getInstance(getLocale());
final String regionId =
getArguments() == null ? null : getArguments().getString(EXTRA_REGION_ID);
- mRegionName = regionId == null ? null : localeDisplayNames.regionDisplayName(regionId);
+ mRegionName = regionId == null ? null : capitalizeForStandaloneDisplay(
+ mLocale, localeDisplayNames.regionDisplayName(regionId));
}
@Override
diff --git a/src/com/android/settings/datetime/timezone/SpannableUtil.java b/src/com/android/settings/datetime/timezone/SpannableUtil.java
index 49c3e7d..ed28f64 100644
--- a/src/com/android/settings/datetime/timezone/SpannableUtil.java
+++ b/src/com/android/settings/datetime/timezone/SpannableUtil.java
@@ -18,14 +18,72 @@
import android.annotation.StringRes;
import android.content.res.Resources;
+import android.icu.text.CaseMap;
+import android.icu.text.Edits;
import android.text.Spannable;
import android.text.SpannableStringBuilder;
+import android.util.Log;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Formattable;
+import java.util.FormattableFlags;
import java.util.Formatter;
+import java.util.List;
import java.util.Locale;
public class SpannableUtil {
+ private static final String TAG = "SpannableUtil";
+
+ private static class SpannableFormattable implements Formattable {
+
+ private final Spannable mSpannable;
+
+ private SpannableFormattable(Spannable spannable) {
+ this.mSpannable = spannable;
+ }
+
+ @Override
+ public void formatTo(Formatter formatter, int flags, int width, int precision) {
+ CharSequence s = handlePrecision(mSpannable, precision);
+ s = handleWidth(s, width, (flags & FormattableFlags.LEFT_JUSTIFY) != 0);
+ try {
+ formatter.out().append(s);
+ } catch (IOException e) {
+ // The error should never occur because formatter.out() returns
+ // SpannableStringBuilder which doesn't throw IOException.
+ Log.e(TAG, "error in SpannableFormattable", e);
+ }
+ }
+
+ private static CharSequence handlePrecision(CharSequence s, int precision) {
+ if (precision != -1 && precision < s.length()) {
+ return s.subSequence(0, precision);
+ }
+ return s;
+ }
+
+ private static CharSequence handleWidth(CharSequence s, int width, boolean isLeftJustify) {
+ if (width == -1) {
+ return s;
+ }
+ int diff = width - s.length();
+ if (diff <= 0) {
+ return s;
+ }
+ SpannableStringBuilder sb = new SpannableStringBuilder();
+ if (!isLeftJustify) {
+ sb.append(" ".repeat(diff));
+ }
+ sb.append(s);
+ if (isLeftJustify) {
+ sb.append(" ".repeat(diff));
+ }
+ return sb;
+ }
+ }
/**
* {@class Resources} has no method to format string resource with {@class Spannable} a
@@ -35,7 +93,56 @@
Object... args) {
final Locale locale = res.getConfiguration().getLocales().get(0);
final SpannableStringBuilder builder = new SpannableStringBuilder();
+ // Formatter converts CharSequence to String by calling toString() if an arg isn't
+ // Formattable. Wrap Spannable by SpannableFormattable to preserve Spannable objects.
+ for (int i = 0; i < args.length; i++) {
+ if (args[i] instanceof Spannable) {
+ args[i] = new SpannableFormattable((Spannable) args[i]);
+ }
+ }
new Formatter(builder, locale).format(res.getString(resId), args);
return builder;
}
+
+ private static final CaseMap.Title TITLE_CASE_MAP =
+ CaseMap.toTitle().sentences().noLowercase();
+
+ /**
+ * Titlecasing {@link CharSequence} and {@link Spannable} by using {@link CaseMap.Title}.
+ */
+ public static CharSequence titleCaseSentences(Locale locale, CharSequence src) {
+ if (src instanceof Spannable) {
+ return applyCaseMapToSpannable(locale, TITLE_CASE_MAP, (Spannable) src);
+ } else {
+ return TITLE_CASE_MAP.apply(locale, null, src);
+ }
+ }
+
+ private static Spannable applyCaseMapToSpannable(Locale locale, CaseMap.Title caseMap,
+ Spannable src) {
+ Edits edits = new Edits();
+ SpannableStringBuilder dest = new SpannableStringBuilder();
+ caseMap.apply(locale, null, src, dest, edits);
+ if (!edits.hasChanges()) {
+ return src;
+ }
+ Edits.Iterator iterator = edits.getCoarseChangesIterator();
+ List<int[]> changes = new ArrayList<>();
+ while (iterator.next()) {
+ int[] change = new int[] {
+ iterator.sourceIndex(), // 0
+ iterator.oldLength(), // 1
+ iterator.destinationIndex(), // 2
+ iterator.newLength(), // 3
+ };
+ changes.add(change);
+ }
+ // Replacement starts from the end to avoid shifting the source index during replacement
+ Collections.reverse(changes);
+ SpannableStringBuilder result = new SpannableStringBuilder(src);
+ for (int[] c : changes) {
+ result.replace(c[0], c[0] + c[1], dest, c[2], c[2] + c[3]);
+ }
+ return result;
+ }
}
diff --git a/src/com/android/settings/datetime/timezone/TimeZoneInfo.java b/src/com/android/settings/datetime/timezone/TimeZoneInfo.java
index f9e819c..5076f72 100644
--- a/src/com/android/settings/datetime/timezone/TimeZoneInfo.java
+++ b/src/com/android/settings/datetime/timezone/TimeZoneInfo.java
@@ -15,6 +15,8 @@
*/
package com.android.settings.datetime.timezone;
+import static com.android.settingslib.datetime.ZoneGetter.capitalizeForStandaloneDisplay;
+
import android.icu.text.TimeZoneFormat;
import android.icu.text.TimeZoneNames;
import android.icu.util.TimeZone;
@@ -152,19 +154,29 @@
String canonicalZoneId = getCanonicalZoneId(timeZone);
final TimeZoneNames timeZoneNames = mTimeZoneFormat.getTimeZoneNames();
final java.util.TimeZone javaTimeZone = toJavaTimeZone(canonicalZoneId);
- final CharSequence gmtOffset = ZoneGetter.getGmtOffsetText(mTimeZoneFormat, mLocale,
- javaTimeZone, mNow);
+ final CharSequence gmtOffset =
+ ZoneGetter.getGmtOffsetText(mTimeZoneFormat, mLocale, javaTimeZone, mNow);
return new TimeZoneInfo.Builder(timeZone)
- .setGenericName(timeZoneNames.getDisplayName(canonicalZoneId,
- TimeZoneNames.NameType.LONG_GENERIC, mNow.getTime()))
- .setStandardName(timeZoneNames.getDisplayName(canonicalZoneId,
- TimeZoneNames.NameType.LONG_STANDARD, mNow.getTime()))
- .setDaylightName(timeZoneNames.getDisplayName(canonicalZoneId,
- TimeZoneNames.NameType.LONG_DAYLIGHT, mNow.getTime()))
- .setExemplarLocation(timeZoneNames.getExemplarLocationName(canonicalZoneId))
+ .setGenericName(getTzNameForListDisplay(mLocale, timeZoneNames,
+ canonicalZoneId, mNow, TimeZoneNames.NameType.LONG_GENERIC))
+ .setStandardName(getTzNameForListDisplay(mLocale, timeZoneNames,
+ canonicalZoneId, mNow, TimeZoneNames.NameType.LONG_STANDARD))
+ .setDaylightName(getTzNameForListDisplay(mLocale, timeZoneNames,
+ canonicalZoneId, mNow, TimeZoneNames.NameType.LONG_DAYLIGHT))
+ .setExemplarLocation(capitalizeForStandaloneDisplay(mLocale,
+ timeZoneNames.getExemplarLocationName(canonicalZoneId)))
.setGmtOffset(gmtOffset)
.build();
}
+
+ private static String getTzNameForListDisplay(
+ Locale locale, TimeZoneNames timeZoneNames, String canonicalZoneId, Date now,
+ TimeZoneNames.NameType nameType) {
+ long nowEpochMillis = now.getTime();
+ String displayName = timeZoneNames.getDisplayName(
+ canonicalZoneId, nameType, nowEpochMillis);
+ return capitalizeForStandaloneDisplay(locale, displayName);
+ }
}
/* package-private */ java.util.TimeZone getJavaTimeZone() {
diff --git a/src/com/android/settings/datetime/timezone/TimeZoneInfoPreferenceController.java b/src/com/android/settings/datetime/timezone/TimeZoneInfoPreferenceController.java
index c6ac328..fb2392b 100644
--- a/src/com/android/settings/datetime/timezone/TimeZoneInfoPreferenceController.java
+++ b/src/com/android/settings/datetime/timezone/TimeZoneInfoPreferenceController.java
@@ -17,6 +17,7 @@
package com.android.settings.datetime.timezone;
import android.content.Context;
+import android.content.res.Resources;
import android.icu.text.DateFormat;
import android.icu.text.DisplayContext;
import android.icu.text.SimpleDateFormat;
@@ -32,6 +33,7 @@
import java.time.zone.ZoneOffsetTransition;
import java.time.zone.ZoneRules;
import java.util.Date;
+import java.util.Locale;
public class TimeZoneInfoPreferenceController extends BasePreferenceController {
@@ -82,14 +84,15 @@
private CharSequence formatInfo(TimeZoneInfo item) {
final CharSequence offsetAndName = formatOffsetAndName(item);
final TimeZone timeZone = item.getTimeZone();
- if (!timeZone.observesDaylightTime()) {
- return mContext.getString(R.string.zone_info_footer_no_dst, offsetAndName);
+ ZoneOffsetTransition nextDstTransition = null;
+ if (timeZone.observesDaylightTime()) {
+ nextDstTransition = findNextDstTransition(item);
+ }
+ if (nextDstTransition == null || !timeZone.observesDaylightTime()) {
+ return SpannableUtil.getResourcesText(mContext.getResources(),
+ R.string.zone_info_footer_no_dst, offsetAndName);
}
- final ZoneOffsetTransition nextDstTransition = findNextDstTransition(item);
- if (nextDstTransition == null) { // No future transition
- return mContext.getString(R.string.zone_info_footer_no_dst, offsetAndName);
- }
final boolean toDst = getDSTSavings(timeZone, nextDstTransition.getInstant()) != 0;
String timeType = toDst ? item.getDaylightName() : item.getStandardName();
if (timeType == null) {
@@ -103,8 +106,24 @@
final Calendar transitionTime = Calendar.getInstance(timeZone);
transitionTime.setTimeInMillis(nextDstTransition.getInstant().toEpochMilli());
final String date = mDateFormat.format(transitionTime);
- return SpannableUtil.getResourcesText(mContext.getResources(),
- R.string.zone_info_footer, offsetAndName, timeType, date);
+ return createFooterString(offsetAndName, timeType, date);
+ }
+
+ /**
+ * @param offsetAndName {@Spannable} styled text information should be preserved. See
+ * {@link #formatInfo} and {@link com.android.settingslib.datetime.ZoneGetter#getGmtOffsetText}.
+ *
+ */
+ private CharSequence createFooterString(CharSequence offsetAndName, String timeType,
+ String date) {
+ Resources res = mContext.getResources();
+ Locale locale = res.getConfiguration().getLocales().get(0);
+ CharSequence secondSentence = SpannableUtil.titleCaseSentences(locale,
+ SpannableUtil.getResourcesText(res, R.string.zone_info_footer_second_sentence,
+ timeType, date));
+
+ return SpannableUtil.titleCaseSentences(locale, SpannableUtil.getResourcesText(res,
+ R.string.zone_info_footer_first_sentence, offsetAndName, secondSentence));
}
private ZoneOffsetTransition findNextDstTransition(TimeZoneInfo timeZoneInfo) {
diff --git a/src/com/android/settings/development/DefaultUsbConfigurationPreferenceController.java b/src/com/android/settings/development/DefaultUsbConfigurationPreferenceController.java
index be7704f..7c3d3b1 100644
--- a/src/com/android/settings/development/DefaultUsbConfigurationPreferenceController.java
+++ b/src/com/android/settings/development/DefaultUsbConfigurationPreferenceController.java
@@ -24,7 +24,7 @@
import androidx.preference.Preference;
import androidx.preference.PreferenceScreen;
-import com.android.settingslib.RestrictedSwitchPreference;
+import com.android.settingslib.RestrictedPreference;
import com.android.settingslib.development.DeveloperOptionsPreferenceController;
public class DefaultUsbConfigurationPreferenceController extends
@@ -32,7 +32,7 @@
private static final String PREFERENCE_KEY = "default_usb_configuration";
- private RestrictedSwitchPreference mPreference;
+ private RestrictedPreference mPreference;
public DefaultUsbConfigurationPreferenceController(Context context) {
super(context);
diff --git a/src/com/android/settings/enterprise/OWNERS b/src/com/android/settings/enterprise/OWNERS
index 5811673..c675d26 100644
--- a/src/com/android/settings/enterprise/OWNERS
+++ b/src/com/android/settings/enterprise/OWNERS
@@ -1,7 +1,4 @@
# Default reviewers for this and subdirectories.
-sandness@google.com
-tonymak@google.com
-yuemingw@google.com
-arangelov@google.com
+file:platform/frameworks/base:/core/java/android/app/admin/WorkDeviceExperience_OWNERS
-# Emergency approvers in case the above are not available
\ No newline at end of file
+# Emergency approvers in case the above are not available
diff --git a/src/com/android/settings/homepage/contextualcards/CardContentProvider.java b/src/com/android/settings/homepage/contextualcards/CardContentProvider.java
index 75ec651..7ad5506 100644
--- a/src/com/android/settings/homepage/contextualcards/CardContentProvider.java
+++ b/src/com/android/settings/homepage/contextualcards/CardContentProvider.java
@@ -65,11 +65,8 @@
URI_MATCHER.addURI(CARD_AUTHORITY, CardDatabaseHelper.CARD_TABLE, MATCH_CARDS);
}
- private CardDatabaseHelper mDBHelper;
-
@Override
public boolean onCreate() {
- mDBHelper = CardDatabaseHelper.getInstance(getContext());
return true;
}
@@ -84,7 +81,8 @@
public int bulkInsert(Uri uri, ContentValues[] values) {
final StrictMode.ThreadPolicy oldPolicy = StrictMode.getThreadPolicy();
int numInserted = 0;
- final SQLiteDatabase database = mDBHelper.getWritableDatabase();
+ final CardDatabaseHelper DBHelper = CardDatabaseHelper.getInstance(getContext());
+ final SQLiteDatabase database = DBHelper.getWritableDatabase();
final boolean keepDismissalTimestampBeforeDeletion = getContext().getResources()
.getBoolean(R.bool.config_keep_contextual_card_dismissal_timestamp);
final Map<String, Long> dismissedTimeMap = new ArrayMap<>();
@@ -168,7 +166,8 @@
final SQLiteQueryBuilder queryBuilder = new SQLiteQueryBuilder();
final String table = getTableFromMatch(uri);
queryBuilder.setTables(table);
- final SQLiteDatabase database = mDBHelper.getReadableDatabase();
+ final CardDatabaseHelper DBHelper = CardDatabaseHelper.getInstance(getContext());
+ final SQLiteDatabase database = DBHelper.getReadableDatabase();
final Cursor cursor = queryBuilder.query(database,
projection, selection, selectionArgs, null /* groupBy */, null /* having */,
sortOrder);
diff --git a/src/com/android/settings/network/PrivateDnsPreferenceController.java b/src/com/android/settings/network/PrivateDnsPreferenceController.java
index 07d5714..ed6f9ed 100644
--- a/src/com/android/settings/network/PrivateDnsPreferenceController.java
+++ b/src/com/android/settings/network/PrivateDnsPreferenceController.java
@@ -85,9 +85,12 @@
@Override
public int getAvailabilityStatus() {
- return mContext.getResources().getBoolean(R.bool.config_show_private_dns_settings)
- ? AVAILABLE
- : UNSUPPORTED_ON_DEVICE;
+ if (!mContext.getResources().getBoolean(R.bool.config_show_private_dns_settings)) {
+ return UNSUPPORTED_ON_DEVICE;
+ }
+ final UserManager userManager = mContext.getSystemService(UserManager.class);
+ if (userManager.isGuestUser()) return DISABLED_FOR_USER;
+ return AVAILABLE;
}
@Override
diff --git a/src/com/android/settings/security/SimLockPreferenceController.java b/src/com/android/settings/security/SimLockPreferenceController.java
index 3b85888..e570e5d 100644
--- a/src/com/android/settings/security/SimLockPreferenceController.java
+++ b/src/com/android/settings/security/SimLockPreferenceController.java
@@ -95,7 +95,8 @@
for (SubscriptionInfo subInfo : subInfoList) {
final int simState = mTelephonyManager.getSimState(subInfo.getSimSlotIndex());
if ((simState != TelephonyManager.SIM_STATE_ABSENT)
- && (simState != TelephonyManager.SIM_STATE_UNKNOWN)) {
+ && (simState != TelephonyManager.SIM_STATE_UNKNOWN)
+ && (simState != TelephonyManager.SIM_STATE_PERM_DISABLED)) {
return true;
}
}
diff --git a/src/com/android/settings/utils/FileSizeFormatter.java b/src/com/android/settings/utils/FileSizeFormatter.java
index e56388a..9ef0fe2 100644
--- a/src/com/android/settings/utils/FileSizeFormatter.java
+++ b/src/com/android/settings/utils/FileSizeFormatter.java
@@ -16,11 +16,20 @@
package com.android.settings.utils;
+import android.annotation.NonNull;
import android.annotation.Nullable;
import android.content.Context;
-import android.content.res.Resources;
+import android.icu.text.DecimalFormat;
+import android.icu.text.MeasureFormat;
+import android.icu.text.NumberFormat;
+import android.icu.util.Measure;
+import android.icu.util.MeasureUnit;
import android.text.BidiFormatter;
-import android.text.format.Formatter;
+import android.text.TextUtils;
+import android.view.View;
+
+import java.math.BigDecimal;
+import java.util.Locale;
/**
* Utility class to aid in formatting file sizes always with the same unit. This is modified from
@@ -31,6 +40,61 @@
public static final long MEGABYTE_IN_BYTES = KILOBYTE_IN_BYTES * 1000;
public static final long GIGABYTE_IN_BYTES = MEGABYTE_IN_BYTES * 1000;
+ private static class RoundedBytesResult {
+ public final float value;
+ public final MeasureUnit units;
+ public final int fractionDigits;
+ public final long roundedBytes;
+
+ private RoundedBytesResult(
+ float value, MeasureUnit units, int fractionDigits, long roundedBytes) {
+ this.value = value;
+ this.units = units;
+ this.fractionDigits = fractionDigits;
+ this.roundedBytes = roundedBytes;
+ }
+ }
+
+ private static Locale localeFromContext(@NonNull Context context) {
+ return context.getResources().getConfiguration().locale;
+ }
+
+ private static String bidiWrap(@NonNull Context context, String source) {
+ final Locale locale = localeFromContext(context);
+ if (TextUtils.getLayoutDirectionFromLocale(locale) == View.LAYOUT_DIRECTION_RTL) {
+ return BidiFormatter.getInstance(true /* RTL*/).unicodeWrap(source);
+ } else {
+ return source;
+ }
+ }
+
+ private static NumberFormat getNumberFormatter(Locale locale, int fractionDigits) {
+ final NumberFormat numberFormatter = NumberFormat.getInstance(locale);
+ numberFormatter.setMinimumFractionDigits(fractionDigits);
+ numberFormatter.setMaximumFractionDigits(fractionDigits);
+ numberFormatter.setGroupingUsed(false);
+ if (numberFormatter instanceof DecimalFormat) {
+ // We do this only for DecimalFormat, since in the general NumberFormat case, calling
+ // setRoundingMode may throw an exception.
+ numberFormatter.setRoundingMode(BigDecimal.ROUND_HALF_UP);
+ }
+ return numberFormatter;
+ }
+
+ private static String formatMeasureShort(Locale locale, NumberFormat numberFormatter,
+ float value, MeasureUnit units) {
+ final MeasureFormat measureFormatter = MeasureFormat.getInstance(
+ locale, MeasureFormat.FormatWidth.SHORT, numberFormatter);
+ return measureFormatter.format(new Measure(value, units));
+ }
+
+ private static String formatRoundedBytesResult(
+ @NonNull Context context, @NonNull RoundedBytesResult input) {
+ final Locale locale = localeFromContext(context);
+ final NumberFormat numberFormatter = getNumberFormatter(locale, input.fractionDigits);
+ return formatMeasureShort(locale, numberFormatter, input.value, input.units);
+ }
+
/**
* Formats a content size to be in the form of bytes, kilobytes, megabytes, etc.
*
@@ -47,23 +111,17 @@
*
* @param context Context to use to load the localized units
* @param sizeBytes size value to be formatted, in bytes
- * @param suffix String id for the unit suffix.
- * @param mult Amount of bytes in the unit. * @return formatted string with the number
+ * @param unit The unit used for formatting.
+ * @param mult Amount of bytes in the unit.
+ * @return formatted string with the number
*/
public static String formatFileSize(
- @Nullable Context context, long sizeBytes, int suffix, long mult) {
+ @Nullable Context context, long sizeBytes, MeasureUnit unit, long mult) {
if (context == null) {
return "";
}
- final Formatter.BytesResult res =
- formatBytes(context.getResources(), sizeBytes, suffix, mult);
- return BidiFormatter.getInstance()
- .unicodeWrap(context.getString(getFileSizeSuffix(context), res.value, res.units));
- }
-
- private static int getFileSizeSuffix(Context context) {
- final Resources res = context.getResources();
- return res.getIdentifier("fileSizeSuffix", "string", "android");
+ final RoundedBytesResult res = formatBytes(sizeBytes, unit, mult);
+ return bidiWrap(context, formatRoundedBytesResult(context, res));
}
/**
@@ -76,8 +134,8 @@
* @param suffix String id for the unit suffix.
* @param mult Amount of bytes in the unit.
*/
- private static Formatter.BytesResult formatBytes(
- Resources res, long sizeBytes, int suffix, long mult) {
+ private static RoundedBytesResult formatBytes(
+ long sizeBytes, MeasureUnit unit, long mult) {
final boolean isNegative = (sizeBytes < 0);
float result = isNegative ? -sizeBytes : sizeBytes;
result = result / mult;
@@ -85,32 +143,29 @@
// compute the rounded value. String.format("%f", 0.1) might not return "0.1" due to
// floating point errors.
final int roundFactor;
- final String roundFormat;
+ final int roundDigits;
if (mult == 1) {
roundFactor = 1;
- roundFormat = "%.0f";
+ roundDigits = 0;
} else if (result < 1) {
roundFactor = 100;
- roundFormat = "%.2f";
+ roundDigits = 2;
} else if (result < 10) {
roundFactor = 10;
- roundFormat = "%.1f";
+ roundDigits = 1;
} else { // 10 <= result < 100
roundFactor = 1;
- roundFormat = "%.0f";
+ roundDigits = 0;
}
if (isNegative) {
result = -result;
}
- final String roundedString = String.format(roundFormat, result);
// Note this might overflow if abs(result) >= Long.MAX_VALUE / 100, but that's like 80PB so
// it's okay (for now)...
final long roundedBytes = (((long) Math.round(result * roundFactor)) * mult / roundFactor);
- final String units = res.getString(suffix);
-
- return new Formatter.BytesResult(roundedString, units, roundedBytes);
+ return new RoundedBytesResult(result, unit, roundDigits, roundedBytes);
}
}
diff --git a/src/com/android/settings/wfd/WifiDisplayPreferenceController.java b/src/com/android/settings/wfd/WifiDisplayPreferenceController.java
index a83a56b..b15396b 100644
--- a/src/com/android/settings/wfd/WifiDisplayPreferenceController.java
+++ b/src/com/android/settings/wfd/WifiDisplayPreferenceController.java
@@ -19,6 +19,7 @@
import android.content.Context;
import android.media.MediaRouter;
import android.media.MediaRouter.RouteInfo;
+import android.text.TextUtils;
import androidx.preference.Preference;
import androidx.preference.PreferenceScreen;
@@ -87,7 +88,12 @@
final MediaRouter.RouteInfo route = mRouter.getRouteAt(i);
if (route.matchesTypes(MediaRouter.ROUTE_TYPE_REMOTE_DISPLAY)
&& route.isSelected() && !route.isConnecting()) {
- summary = mContext.getString(R.string.wifi_display_status_connected);
+ CharSequence status = route.getStatus();
+ if (!TextUtils.isEmpty(status)) {
+ summary = status;
+ } else {
+ summary = mContext.getString(R.string.wifi_display_status_connected);
+ }
break;
}
}
diff --git a/src/com/android/settings/wfd/WifiDisplaySettings.java b/src/com/android/settings/wfd/WifiDisplaySettings.java
index 19b6c54..8562e5f 100755
--- a/src/com/android/settings/wfd/WifiDisplaySettings.java
+++ b/src/com/android/settings/wfd/WifiDisplaySettings.java
@@ -38,6 +38,7 @@
import android.os.Handler;
import android.os.Looper;
import android.provider.Settings;
+import android.text.TextUtils;
import android.util.Slog;
import android.util.TypedValue;
import android.view.Menu;
@@ -678,7 +679,12 @@
if (route.isConnecting()) {
setSummary(R.string.wifi_display_status_connecting);
} else {
- setSummary(R.string.wifi_display_status_connected);
+ CharSequence status = route.getStatus();
+ if (!TextUtils.isEmpty(status)) {
+ setSummary(status);
+ } else {
+ setSummary(R.string.wifi_display_status_connected);
+ }
}
} else {
if (isEnabled()) {
diff --git a/src/com/android/settings/wifi/dpp/WifiDppQrCodeGeneratorFragment.java b/src/com/android/settings/wifi/dpp/WifiDppQrCodeGeneratorFragment.java
index 2ec960e..d3a4be7 100644
--- a/src/com/android/settings/wifi/dpp/WifiDppQrCodeGeneratorFragment.java
+++ b/src/com/android/settings/wifi/dpp/WifiDppQrCodeGeneratorFragment.java
@@ -43,7 +43,7 @@
import com.android.internal.app.chooser.DisplayResolveInfo;
import com.android.internal.app.chooser.TargetInfo;
import com.android.settings.R;
-import com.android.settings.wifi.qrcode.QrCodeGenerator;
+import com.android.settingslib.qrcode.QrCodeGenerator;
import com.google.zxing.WriterException;
diff --git a/src/com/android/settings/wifi/qrcode/QrCodeGenerator.java b/src/com/android/settings/wifi/qrcode/QrCodeGenerator.java
deleted file mode 100644
index d9682d2..0000000
--- a/src/com/android/settings/wifi/qrcode/QrCodeGenerator.java
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * 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.wifi.qrcode;
-
-import android.graphics.Bitmap;
-import android.graphics.Color;
-
-import com.google.zxing.BarcodeFormat;
-import com.google.zxing.EncodeHintType;
-import com.google.zxing.MultiFormatWriter;
-import com.google.zxing.WriterException;
-import com.google.zxing.common.BitMatrix;
-
-import java.nio.charset.CharsetEncoder;
-import java.nio.charset.StandardCharsets;
-import java.util.HashMap;
-import java.util.Map;
-
-public final class QrCodeGenerator {
- /**
- * Generates a barcode image with {@code contents}.
- *
- * @param contents The contents to encode in the barcode
- * @param size The preferred image size in pixels
- * @return Barcode bitmap
- */
- public static Bitmap encodeQrCode(String contents, int size)
- throws WriterException, IllegalArgumentException {
- final Map<EncodeHintType, Object> hints = new HashMap<>();
- if (!isIso88591(contents)) {
- hints.put(EncodeHintType.CHARACTER_SET, StandardCharsets.UTF_8.name());
- }
-
- final BitMatrix qrBits = new MultiFormatWriter().encode(contents, BarcodeFormat.QR_CODE,
- size, size, hints);
- final Bitmap bitmap = Bitmap.createBitmap(size, size, Bitmap.Config.RGB_565);
- for (int x = 0; x < size; x++) {
- for (int y = 0; y < size; y++) {
- bitmap.setPixel(x, y, qrBits.get(x, y) ? Color.BLACK : Color.WHITE);
- }
- }
- return bitmap;
- }
-
- private static boolean isIso88591(String contents) {
- CharsetEncoder encoder = StandardCharsets.ISO_8859_1.newEncoder();
- return encoder.canEncode(contents);
- }
-}
diff --git a/tests/legacy_unit/src/com/android/settings/utils/FileSizeFormatterTest.java b/tests/legacy_unit/src/com/android/settings/utils/FileSizeFormatterTest.java
index a255d0b..953bd34 100644
--- a/tests/legacy_unit/src/com/android/settings/utils/FileSizeFormatterTest.java
+++ b/tests/legacy_unit/src/com/android/settings/utils/FileSizeFormatterTest.java
@@ -18,9 +18,11 @@
import static com.android.settings.utils.FileSizeFormatter.GIGABYTE_IN_BYTES;
import static com.android.settings.utils.FileSizeFormatter.MEGABYTE_IN_BYTES;
+
import static com.google.common.truth.Truth.assertThat;
import android.content.Context;
+import android.icu.util.MeasureUnit;
import androidx.test.InstrumentationRegistry;
import androidx.test.filters.SmallTest;
@@ -46,7 +48,7 @@
FileSizeFormatter.formatFileSize(
mContext,
0 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("0.00 GB");
}
@@ -57,7 +59,7 @@
FileSizeFormatter.formatFileSize(
mContext,
MEGABYTE_IN_BYTES * 11 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("0.01 GB");
}
@@ -68,7 +70,7 @@
FileSizeFormatter.formatFileSize(
mContext,
MEGABYTE_IN_BYTES * 155 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("0.16 GB");
}
@@ -79,7 +81,7 @@
FileSizeFormatter.formatFileSize(
mContext,
MEGABYTE_IN_BYTES * 1551 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("1.6 GB");
}
@@ -91,7 +93,7 @@
FileSizeFormatter.formatFileSize(
mContext,
GIGABYTE_IN_BYTES * 15 + MEGABYTE_IN_BYTES * 50 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("15 GB");
}
@@ -102,7 +104,7 @@
FileSizeFormatter.formatFileSize(
mContext,
MEGABYTE_IN_BYTES * -155 /* size */,
- com.android.internal.R.string.gigabyteShort,
+ MeasureUnit.GIGABYTE,
GIGABYTE_IN_BYTES))
.isEqualTo("-0.16 GB");
}
diff --git a/tests/robotests/src/com/android/settings/datetime/timezone/SpannableUtilTest.java b/tests/robotests/src/com/android/settings/datetime/timezone/SpannableUtilTest.java
index b9a3056..04528d0 100644
--- a/tests/robotests/src/com/android/settings/datetime/timezone/SpannableUtilTest.java
+++ b/tests/robotests/src/com/android/settings/datetime/timezone/SpannableUtilTest.java
@@ -18,23 +18,91 @@
import static com.google.common.truth.Truth.assertThat;
+import android.icu.text.TimeZoneFormat;
import android.text.Spannable;
+import android.text.SpannableStringBuilder;
import com.android.settings.R;
+import com.android.settingslib.datetime.ZoneGetter;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.robolectric.RobolectricTestRunner;
import org.robolectric.RuntimeEnvironment;
+import java.util.Date;
+import java.util.Locale;
+import java.util.TimeZone;
+
@RunWith(RobolectricTestRunner.class)
public class SpannableUtilTest {
@Test
- public void testFormat() {
+ public void testGetResourceText() {
+ CharSequence gmtString = getGmtString("GMT+00:00");
+
Spannable spannable = SpannableUtil.getResourcesText(
RuntimeEnvironment.application.getResources(), R.string.zone_info_offset_and_name,
- "GMT+00:00", "UTC");
+ gmtString, "UTC");
assertThat(spannable.toString()).isEqualTo("UTC (GMT+00:00)");
+
+ // Verify that the spans are kept.
+ Object[] spans = ((Spannable) gmtString).getSpans(0, gmtString.length(), Object.class);
+ Object[] newSpans = spannable.getSpans(0, spannable.length(), Object.class);
+ assertThat(newSpans.length).isEqualTo(spans.length);
+ assertThat(newSpans).isEqualTo(spans);
+ }
+
+ private static CharSequence getGmtString(String tzId) {
+ Locale locale = Locale.US;
+ TimeZoneFormat timeZoneFormat = TimeZoneFormat.getInstance(locale);
+ TimeZone gmtZone = TimeZone.getTimeZone(tzId);
+ Date date = new Date(0);
+ return ZoneGetter.getGmtOffsetText(timeZoneFormat, locale, gmtZone, date);
+ }
+ /**
+ * Verify the assumption on the GMT string used in {@link #testGetResourceText()}
+ */
+ @Test
+ public void testGetGmtString() {
+ // Create a GMT string and verify the assumptions
+ CharSequence gmtString = getGmtString("GMT+00:00");
+ assertThat(gmtString.toString()).isEqualTo("GMT+00:00");
+ assertThat(gmtString).isInstanceOf(Spannable.class);
+ Object[] spans = ((Spannable) gmtString).getSpans(0, gmtString.length(), Object.class);
+ assertThat(spans).isNotEmpty();
+
+ assertThat(getGmtString("GMT-08:00").toString()).isEqualTo("GMT-08:00");
+ }
+
+ @Test
+ public void testTitleCaseSentences_enUS() {
+ Locale locale = Locale.US;
+ CharSequence titleCasedFirstSentence = SpannableUtil.titleCaseSentences(locale,
+ "pacific Daylight Time starts on Mar 11 2018.");
+ assertThat(titleCasedFirstSentence.toString())
+ .isEqualTo("Pacific Daylight Time starts on Mar 11 2018.");
+
+ SpannableStringBuilder sb = new SpannableStringBuilder()
+ .append("uses ")
+ .append("Pacific Time (")
+ .append(getGmtString("GMT-08:00"))
+ .append("). ")
+ .append(titleCasedFirstSentence);
+
+ assertThat(sb.toString()).isEqualTo(
+ "uses Pacific Time (GMT-08:00). Pacific Daylight Time starts on Mar 11 2018.");
+
+ Object[] spans = sb.getSpans(0, sb.length(), Object.class);
+ assertThat(spans).isNotEmpty();
+
+ CharSequence titledOutput = SpannableUtil.titleCaseSentences(Locale.US, sb);
+ assertThat(titledOutput.toString()).isEqualTo(
+ "Uses Pacific Time (GMT-08:00). Pacific Daylight Time starts on Mar 11 2018.");
+ assertThat(titledOutput).isInstanceOf(Spannable.class);
+ Object[] newSpans = ((Spannable) titledOutput).getSpans(0, titledOutput.length(),
+ Object.class);
+ assertThat(newSpans.length).isEqualTo(spans.length);
+ assertThat(newSpans).isEqualTo(spans);
}
}
diff --git a/tests/robotests/src/com/android/settings/development/DefaultUsbConfigurationPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/development/DefaultUsbConfigurationPreferenceControllerTest.java
index c9b13e27..a386473 100644
--- a/tests/robotests/src/com/android/settings/development/DefaultUsbConfigurationPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/development/DefaultUsbConfigurationPreferenceControllerTest.java
@@ -32,7 +32,7 @@
import androidx.preference.PreferenceScreen;
import com.android.settingslib.RestrictedLockUtils;
-import com.android.settingslib.RestrictedSwitchPreference;
+import com.android.settingslib.RestrictedPreference;
import org.junit.Before;
import org.junit.Test;
@@ -48,7 +48,7 @@
private static final ComponentName TEST_COMPONENT_NAME = new ComponentName("test", "test");
@Mock
- private RestrictedSwitchPreference mPreference;
+ private RestrictedPreference mPreference;
@Mock
private PreferenceScreen mPreferenceScreen;
@Mock
diff --git a/tests/robotests/src/com/android/settings/network/PrivateDnsPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/network/PrivateDnsPreferenceControllerTest.java
index e31d959..057b6cb 100644
--- a/tests/robotests/src/com/android/settings/network/PrivateDnsPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/network/PrivateDnsPreferenceControllerTest.java
@@ -26,6 +26,7 @@
import static androidx.lifecycle.Lifecycle.Event.ON_STOP;
import static com.android.settings.core.BasePreferenceController.AVAILABLE;
+import static com.android.settings.core.BasePreferenceController.DISABLED_FOR_USER;
import static com.android.settings.core.BasePreferenceController.UNSUPPORTED_ON_DEVICE;
import static com.google.common.truth.Truth.assertThat;
@@ -35,6 +36,7 @@
import static org.mockito.Mockito.CALLS_REAL_METHODS;
import static org.mockito.Mockito.atLeastOnce;
import static org.mockito.Mockito.doNothing;
+import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.spy;
@@ -109,6 +111,8 @@
private Network mNetwork;
@Mock
private Preference mPreference;
+ @Mock
+ private UserManager mUserManager;
@Captor
private ArgumentCaptor<NetworkCallback> mCallbackCaptor;
private PrivateDnsPreferenceController mController;
@@ -127,6 +131,7 @@
mShadowContentResolver = Shadow.extract(mContentResolver);
when(mContext.getSystemService(Context.CONNECTIVITY_SERVICE))
.thenReturn(mConnectivityManager);
+ when(mContext.getSystemService(UserManager.class)).thenReturn(mUserManager);
doNothing().when(mConnectivityManager).registerDefaultNetworkCallback(
mCallbackCaptor.capture(), nullable(Handler.class));
@@ -174,6 +179,12 @@
}
@Test
+ public void getAvailabilityStatus_disabledForGuestUser() {
+ doReturn(true).when(mUserManager).isGuestUser();
+ assertThat(mController.getAvailabilityStatus()).isEqualTo(DISABLED_FOR_USER);
+ }
+
+ @Test
public void goThroughLifecycle_shouldRegisterUnregisterSettingsObserver() {
mLifecycle.handleLifecycleEvent(ON_START);
verify(mContext, atLeastOnce()).getContentResolver();
diff --git a/tests/robotests/src/com/android/settings/wifi/qrcode/QrCameraTest.java b/tests/robotests/src/com/android/settings/wifi/qrcode/QrCameraTest.java
index de0df73..3ad846d 100644
--- a/tests/robotests/src/com/android/settings/wifi/qrcode/QrCameraTest.java
+++ b/tests/robotests/src/com/android/settings/wifi/qrcode/QrCameraTest.java
@@ -32,6 +32,8 @@
import android.hardware.Camera.Parameters;
import android.hardware.Camera.Size;
+import com.android.settingslib.qrcode.QrCodeGenerator;
+
import com.google.zxing.BinaryBitmap;
import com.google.zxing.LuminanceSource;
import com.google.zxing.RGBLuminanceSource;
diff --git a/tests/unit/README b/tests/unit/README
index 5a85603..262c8bf 100644
--- a/tests/unit/README
+++ b/tests/unit/README
@@ -7,14 +7,14 @@
// The following instrutions show how to run the test suite using make + adb //
To build the tests you can use the following command at the root of your android source tree
-$ make SettingsUnitTests
+$ make -j SettingsUnitTests
The test apk then needs to be installed onto your test device. The apk's location will vary
depending on your device model and architecture. At the end of the make command's output, there
should be a line similar to the following:
-"Copy: out/target/product/shamu/testcases/SettingsUnitTests/arm64/SettingsUnitTests.apk"
+"Copy: ${ANDROID_PRODUCT_OUT}/testcases/SettingsUnitTests/arm64/SettingsUnitTests.apk"
Install via the following command:
-$ adb install -r out/target/product/shamu/testcases/SettingsUnitTests/arm64/SettingsUnitTests.apk
+$ adb install -r ${ANDROID_PRODUCT_OUT}/testcases/SettingsUnitTests/arm64/SettingsUnitTests.apk
To run all tests:
$ adb shell am instrument -w com.android.settings.tests.unit/androidx.test.runner.AndroidJUnitRunner