Merge "Convert Magnify controller to TogglePrefController" into pi-dev
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index d55493c..5dd22c2 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -207,8 +207,6 @@
android:value="com.android.settings.category.ia.homepage"/>
<meta-data android:name="com.android.settings.PRIMARY_PROFILE_CONTROLLED"
android:value="true" />
- <meta-data android:name="android.metadata.SLICE_URI"
- android:value="content://android.settings.slices/action/toggle_bluetooth_switch" />
</activity>
<activity android:name="AirplaneModeVoiceActivity"
@@ -253,8 +251,6 @@
android:value="com.android.settings.wifi.WifiSettings" />
<meta-data android:name="com.android.settings.PRIMARY_PROFILE_CONTROLLED"
android:value="true" />
- <meta-data android:name="android.metadata.SLICE_URI"
- android:value="content://android.settings.slices/wifi" />
</activity>
<activity
@@ -745,7 +741,7 @@
<activity
android:name=".notification.ZenSuggestionActivity"
android:label="@string/zen_mode_settings_title"
- android:icon="@drawable/ic_zen"
+ android:icon="@drawable/ic_do_not_disturb_on_24dp"
android:theme="@android:style/Theme.NoDisplay">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
@@ -2246,8 +2242,6 @@
android:value="com.android.settings.category.ia.homepage" />
<meta-data android:name="com.android.settings.FRAGMENT_CLASS"
android:value="com.android.settings.fuelgauge.PowerUsageSummary" />
- <meta-data android:name="android.metadata.SLICE_URI"
- android:value="content://android.settings.slices/action/auto_brightness" />
</activity>
<activity
@@ -2264,8 +2258,6 @@
android:value="com.android.settings.fuelgauge.batterysaver.BatterySaverSettings" />
<meta-data android:name="com.android.settings.PRIMARY_PROFILE_CONTROLLED"
android:value="true" />
- <meta-data android:name="android.metadata.SLICE_URI"
- android:value="content://android.settings.slices/action/battery_saver_summary" />
</activity>
<activity android:name=".fuelgauge.BatterySaverModeVoiceActivity"
@@ -2687,8 +2679,6 @@
android:value="true" />
<meta-data android:name="com.android.settings.summary"
android:resource="@string/sound_dashboard_summary"/>
- <meta-data android:name="android.metadata.SLICE_URI"
- android:value="content://android.settings.slices/action/alarm_volume" />
</activity>
<!-- Show apps for which application-level notification settings are applicable -->
diff --git a/res/drawable/ic_do_not_disturb_on_24dp.xml b/res/drawable/ic_do_not_disturb_on_24dp.xml
new file mode 100644
index 0000000..cace8d4
--- /dev/null
+++ b/res/drawable/ic_do_not_disturb_on_24dp.xml
@@ -0,0 +1,28 @@
+<!--
+ 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.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:width="24dp"
+ android:height="24dp"
+ android:viewportWidth="24.0"
+ android:viewportHeight="24.0"
+ android:tint="?android:attr/colorControlNormal">
+ <path
+ android:fillColor="#FFFFFFFF"
+ android:pathData="M12,2C6.48,2 2,6.48 2,12c0,5.52 4.48,10 10,10c5.52,0 10,-4.48 10,-10C22,6.48 17.52,2 12,2zM12,20c-4.41,0 -8,-3.59 -8,-8c0,-4.41 3.59,-8 8,-8c4.41,0 8,3.59 8,8C20,16.41 16.41,20 12,20z"/>
+ <path
+ android:fillColor="#FFFFFFFF"
+ android:pathData="M7,11h10v2h-10z"/>
+</vector>
diff --git a/res/drawable/ic_homepage_sound.xml b/res/drawable/ic_homepage_sound.xml
index 4991656..a7369ad 100644
--- a/res/drawable/ic_homepage_sound.xml
+++ b/res/drawable/ic_homepage_sound.xml
@@ -32,5 +32,5 @@
android:height="@dimen/dashboard_tile_foreground_image_size"
android:start="@dimen/dashboard_tile_foreground_image_inset"
android:top="@dimen/dashboard_tile_foreground_image_inset"
- android:drawable="@drawable/ic_settings_sound_white" />
+ android:drawable="@drawable/ic_volume_up_24dp" />
</layer-list>
diff --git a/res/drawable/ic_notifications_off_24dp.xml b/res/drawable/ic_notifications_off_24dp.xml
new file mode 100644
index 0000000..1622025
--- /dev/null
+++ b/res/drawable/ic_notifications_off_24dp.xml
@@ -0,0 +1,31 @@
+<!--
+ 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.
+ -->
+
+<vector
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:autoMirrored="true"
+ android:height="24dp"
+ android:viewportHeight="24.0"
+ android:viewportWidth="24.0"
+ android:width="24dp"
+ android:tint="?android:attr/colorControlNormal">
+ <path android:fillColor="#FF000000"
+ android:pathData="M12,22c1.1,0 2,-0.9 2,-2h-4C10,21.1 10.9,22 12,22z" />
+ <path android:fillColor="#FF000000"
+ android:pathData="M16,16L2.81,2.81L1.39,4.22l4.85,4.85C6.09,9.68 6,10.33 6,11v6H4v2h12.17l3.61,3.61l1.41,-1.41L16,16zM8,17c0,0 0.01,-6.11 0.01,-6.16L14.17,17H8z" />
+ <path android:fillColor="#FF000000"
+ android:pathData="M12,6.5c2.49,0 4,2.02 4,4.5v2.17l2,2V11c0,-3.07 -1.63,-5.64 -4.5,-6.32V4c0,-0.83 -0.67,-1.5 -1.5,-1.5S10.5,3.17 10.5,4v0.68C9.72,4.86 9.05,5.2 8.46,5.63L9.93,7.1C10.51,6.73 11.2,6.5 12,6.5z" />
+</vector>
diff --git a/res/drawable/ic_volume_ringer_mute.xml b/res/drawable/ic_volume_ringer_mute.xml
deleted file mode 100644
index 03357e9..0000000
--- a/res/drawable/ic_volume_ringer_mute.xml
+++ /dev/null
@@ -1,38 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
- 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.
--->
-<vector xmlns:android="http://schemas.android.com/apk/res/android"
- android:height="24dp"
- android:viewportHeight="23.4"
- android:viewportWidth="23.3"
- android:width="24dp"
- android:tint="?android:attr/colorControlNormal">
-
- <group
- android:translateX="-0.85"
- android:translateY="-0.5">
- <path
- android:fillColor="#FFF"
- android:pathData="M20.73,19.46l-0.6,-0.6c0,0 0,0 0,0L5.54,4.26c-0.35,-0.35 -0.92,-0.35 -1.27,0c-0.35,0.35 -0.35,0.92 0,1.27l2.4,2.4C6.25,8.85 6,9.88 6,11v5l-2.15,2.15c-0.19,0.2 -0.19,0.51 0.01,0.71C3.95,18.95 4.07,19 4.2,19h13.53l1.73,1.73c0.35,0.35 0.92,0.35 1.27,0C21.09,20.38 21.09,19.81 20.73,19.46z" />
- <path
- android:fillColor="#FFF"
- android:pathData="M18,11c0,-3.07 -1.64,-5.64 -4.5,-6.32V4c0,-0.83 -0.67,-1.5 -1.5,-1.5S10.5,3.17 10.5,4v0.68C9.87,4.83 9.31,5.08 8.8,5.4l9.2,9.2V11z" />
- <path
- android:fillColor="#FFF"
- android:pathData="M12,22c1.1,0 2,-0.9 2,-2h-4C10,21.1 10.9,22 12,22z" />
- </group>
-
-</vector>
diff --git a/res/drawable/ic_settings_sound_white.xml b/res/drawable/ic_volume_up_24dp.xml
similarity index 61%
rename from res/drawable/ic_settings_sound_white.xml
rename to res/drawable/ic_volume_up_24dp.xml
index 4737349..8c68c00 100644
--- a/res/drawable/ic_settings_sound_white.xml
+++ b/res/drawable/ic_volume_up_24dp.xml
@@ -13,17 +13,19 @@
See the License for the specific language governing permissions and
limitations under the License.
-->
+
<vector xmlns:android="http://schemas.android.com/apk/res/android"
- android:width="24.0dp"
- android:height="24.0dp"
+ android:width="24dp"
+ android:height="24dp"
android:viewportWidth="24.0"
android:viewportHeight="24.0">
<path
android:fillColor="#FFFFFFFF"
- android:pathData="M3 10v4c0 .55 .45 1 1 1h3l3.29 3.29c.63 .63 1.71 .18
-1.71-.71V6.41c0-.89-1.08-1.34-1.71-.71L7 9H4c-.55 0-1 .45-1 1zm13.5 2A4.5 4.5 0
-0 0 14 7.97v8.05c1.48-.73 2.5-2.25 2.5-4.02zM14 4.46v.19c0 .38 .25 .71 .61
-.85C17.18 6.54 19 9.06 19 12s-1.82 5.46-4.39 6.5c-.36 .14 -.61 .47 -.61 .85
-v.19c0 .63 .63 1.08 1.22 .86 a8.995 8.995 0 0 0 0-16.8c-.59-.23-1.22 .23 -1.22
-.86 z"/>
+ android:pathData="M3,9v6h4l5,5V4L7,9H3zM10,8.83v6.34L7.83,13H5v-2h2.83L10,8.83z"/>
+ <path
+ android:fillColor="#FFFFFFFF"
+ android:pathData="M16.5,12c0,-1.77 -1.02,-3.29 -2.5,-4.03v8.05C15.48,15.29 16.5,13.77 16.5,12z"/>
+ <path
+ android:fillColor="#FFFFFFFF"
+ android:pathData="M14,3.23v2.06c2.89,0.86 5,3.54 5,6.71c0,3.17 -2.11,5.85 -5,6.71v2.06c4.01,-0.91 7,-4.49 7,-8.77C21,7.72 18.01,4.14 14,3.23z"/>
</vector>
diff --git a/res/drawable/ic_zen.xml b/res/drawable/ic_zen.xml
deleted file mode 100644
index 2c55e02..0000000
--- a/res/drawable/ic_zen.xml
+++ /dev/null
@@ -1,26 +0,0 @@
-<!--
- Copyright (C) 2015 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.
--->
-<vector xmlns:android="http://schemas.android.com/apk/res/android"
- android:viewportHeight="24.0"
- android:viewportWidth="24.0"
- android:height="24dp"
- android:width="24dp" >
-
- <path
- android:fillColor="?android:attr/colorControlActivated"
- android:pathData="M 12 2 C 6.48 2 2 6.48 2 12 s 4.48 10 10 10 10 -4.48 10 -10 S 17.52 2 12 2 z m 4 11 H 8 c -.55 0 -1 -.45 -1 -1 s .45 -1 1 -1 h 8c.55 0 1 .45 1 1 s -.45 1 -1 1z" />
-
-</vector>
diff --git a/res/layout/choose_lock_pattern_common.xml b/res/layout/choose_lock_pattern_common.xml
index c4a9381..77dd12d 100644
--- a/res/layout/choose_lock_pattern_common.xml
+++ b/res/layout/choose_lock_pattern_common.xml
@@ -50,6 +50,7 @@
<TextView
android:id="@+id/suw_layout_title"
style="@style/SuwGlifHeaderTitle"
+ android:accessibilityLiveRegion="polite"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
diff --git a/res/layout/storage_item.xml b/res/layout/storage_item.xml
index ba1c697..aa2b4f8 100644
--- a/res/layout/storage_item.xml
+++ b/res/layout/storage_item.xml
@@ -72,7 +72,7 @@
android:layout_height="wrap_content"
android:textAlignment="viewStart"
android:textAppearance="@android:style/TextAppearance.Material.Body1"
- android:textColor="?android:attr/textColorSecondaryNoDisable"
+ android:textColor="?android:attr/textColorSecondary"
android:maxLines="10"
android:layout_alignParentEnd="true"/>
diff --git a/res/layout/zen_onboarding.xml b/res/layout/zen_onboarding.xml
index 6467955..82951bd 100644
--- a/res/layout/zen_onboarding.xml
+++ b/res/layout/zen_onboarding.xml
@@ -17,40 +17,112 @@
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="320dp"
- android:layout_height="wrap_content"
- android:padding="20dp">
+ android:layout_height="wrap_content" >
- <TextView
- android:id="@+id/header"
- android:layout_width="wrap_content"
+ <RelativeLayout
+ android:id="@+id/zen_onboarding_choices"
+ android:layout_width="match_parent"
android:layout_height="wrap_content"
- android:text="@string/zen_onboarding_dnd_visual_disturbances_header"
- android:textAppearance="@android:style/TextAppearance.Material.DialogWindowTitle" />
+ android:paddingLeft="24dp"
+ android:paddingRight="24dp"
+ android:paddingTop="18dp">
- <TextView
- android:id="@+id/feature_description"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_below="@+id/header"
- android:layout_marginTop="24dp"
- android:textAppearance="?android:attr/textAppearanceListItem"
- android:text="@string/zen_onboarding_dnd_visual_disturbances_description" />
+ <TextView
+ android:id="@+id/header"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/zen_onboarding_dnd_visual_disturbances_header"
+ android:textAppearance="@android:style/TextAppearance.Material.DialogWindowTitle" />
+
+ <LinearLayout
+ android:id="@+id/zen_onboarding_new_setting"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_below="@+id/header"
+ android:layout_centerHorizontal="true"
+ android:layout_marginTop="22dp"
+ android:orientation="horizontal">
+
+ <RadioButton
+ android:id="@+id/zen_onboarding_new_setting_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:paddingHorizontal="8dp" />
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical">
+
+ <TextView
+ android:id="@+id/zen_onboarding_new_setting_title"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/zen_onboarding_new_setting_title"
+ android:textAppearance="?android:attr/textAppearanceListItem" />
+
+ <TextView
+ android:id="@+id/zen_onboarding_new_setting_summary"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/zen_onboarding_new_setting_summary" />
+ </LinearLayout>
+
+ </LinearLayout>
+
+ <LinearLayout
+ android:id="@+id/zen_onboarding_current_setting"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_below="@+id/zen_onboarding_new_setting"
+ android:layout_centerHorizontal="true"
+ android:layout_marginTop="10dp"
+ android:orientation="horizontal">
+
+ <RadioButton
+ android:id="@+id/zen_onboarding_current_setting_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:paddingHorizontal="8dp" />
+
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical">
+
+ <TextView
+ android:id="@+id/zen_onboarding_current_setting_title"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/zen_onboarding_current_setting_title"
+ android:textAppearance="?android:attr/textAppearanceListItem" />
+
+ <TextView
+ android:id="@+id/zen_onboarding_current_setting_summary"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/zen_onboarding_current_setting_summary" />
+ </LinearLayout>
+ </LinearLayout>
+ </RelativeLayout>
<RelativeLayout
android:id="@+id/buttons"
android:layout_width="match_parent"
android:layout_height="wrap_content"
- android:layout_below="@+id/feature_description"
- android:layout_marginTop="35dp">
+ android:layout_below="@+id/zen_onboarding_choices"
+ android:layout_marginLeft="8dp"
+ android:layout_marginTop="20dp"
+ android:layout_marginBottom="10dp">
<Button
- android:id="@+id/no"
+ android:id="@+id/settings"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
- android:text="@string/zen_onboarding_no_update"
- android:layout_toStartOf="@+id/ok"
+ android:text="@string/zen_onboarding_settings"
+ android:layout_alignParentStart="true"
style="@style/TextAppearance.ZenOnboardingButton"
- android:onClick="close" />
+ android:onClick="launchSettings" />
<Button
android:id="@+id/ok"
diff --git a/res/values/config.xml b/res/values/config.xml
index f8a7acc..e3ec74f 100755
--- a/res/values/config.xml
+++ b/res/values/config.xml
@@ -131,7 +131,4 @@
<!-- List of a11y components on the device allowed to be enabled by Settings Slices -->
<string-array name="config_settings_slices_accessibility_components" translatable="false"/>
- <!-- Whether or not swipe up gesture's opt-in setting is available on this device -->
- <bool name="config_swipe_up_gesture_setting_available">false</bool>
-
</resources>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 8347f99..ca11c9b 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -402,11 +402,6 @@
<!-- Summary for bluetooth item in connection detail page. (phone)-->
<string name="bluetooth_pref_summary" product="default">Allow your phone to communicate with nearby Bluetooth devices</string>
- <!-- Setting Checkbox title for disabling Bluetooth inband ringing in Development Settings -->
- <string name="bluetooth_disable_inband_ringing">Disable in-band ringing</string>
- <!-- Summary of checkbox for disabling Bluetooth inband ringing in Development Settings -->
- <string name="bluetooth_disable_inband_ringing_summary">Don’t play custom phone ringtones on Bluetooth headsets</string>
-
<!-- Title for Bluetooth device group with media capability group [CHAR LIMIT=none]-->
<string name="connected_device_available_media_title">Available media devices</string>
<!-- Title for Bluetooth device group with media capability group [CHAR LIMIT=none]-->
@@ -1691,15 +1686,10 @@
<!-- Bluetooth settings. Dock Setting Dialog - Remember setting and don't ask user again -->
<string name="bluetooth_dock_settings_remember">Remember settings</string>
- <!-- Bluetooth developer options. -->
<!-- Bluetooth developer settings: Maximum number of connected audio devices -->
<string name="bluetooth_max_connected_audio_devices_string">Maximum connected Bluetooth audio devices</string>
<!-- Bluetooth developer settings: Maximum number of connected audio devices -->
<string name="bluetooth_max_connected_audio_devices_dialog_title">Select maximum number of connected Bluetooth audio devices</string>
- <!-- Bluetooth developer settings: Checkbox title for disabling Bluetooth receiving AVDTP delay reports -->
- <string name="bluetooth_disable_avdtp_delay_reports">Disable Bluetooth AVDTP delay reports</string>
- <!-- Bluetooth developer settings: Summary of checkbox for disabling Bluetooth receiving AVDTP delay reports -->
- <string name="bluetooth_disable_avdtp_delay_reports_summary">Disallow receiving Bluetooth AVDTP delay reports</string>
<!-- Wifi Display settings. The title of the screen. [CHAR LIMIT=40] -->
<string name="wifi_display_settings_title">Cast</string>
@@ -2350,6 +2340,17 @@
<!-- Message of private dns that provides a help link. [CHAR LIMIT=NONE] -->
<string name="private_dns_help_message"><annotation id="url">Learn more</annotation> about Private DNS features</string>
+ <!-- Message to display when setting wifi calling are not editable [CHAR LIMIT=NONE] -->
+ <string name="wifi_calling_pref_managed_by_carrier">Setting managed by carrier</string>
+ <!-- Message to display when wifi calling needs activation [CHAR LIMIT=NONE] -->
+ <string name="wifi_calling_settings_activation_instructions">Activate Wi\u2011Fi Calling</string>
+ <!-- Message to display when wifi calling should be on [CHAR LIMIT=NONE] -->
+ <string name="wifi_calling_turn_on">Turn on Wi\u2011Fi calling</string>
+ <!-- Message to display when carrier does not support wifi calling or doesn't want the user
+ to modify the settings [CHAR LIMIT=NONE] -->
+ <string name="wifi_calling_not_supported">Wi\u2011Fi calling is not supported for %1$s</string>
+ <!-- Carrier string to use in other messages -->
+ <string name="carrier">Carrier</string>
<!-- Sound and alerts settings -->
<skip/>
<string name="display_settings_title">Display</string>
@@ -4922,6 +4923,8 @@
<string name="background_activity_warning_dialog_title">Limit background activity?</string>
<!-- TODO: Pending UX review. Text for the warning dialog to show to the user when limiting background activity for an app -->
<string name="background_activity_warning_dialog_text">If you limit background activity for an app, it may misbehave</string>
+ <!-- Dialog message when app can't been restricted because it is not optimized [CHAR_LIMIT=120] -->
+ <string name="background_activity_disabled_dialog_text">Since this app is not set to optimize battery, you can\u2019t restrict it.\n\nTo restrict the app, first turn on battery optimization.</string>
<!-- Title for the screen usage in power use UI [CHAR_LIMIT=60] -->
<string name="device_screen_usage">Screen usage since full charge</string>
@@ -6915,9 +6918,13 @@
<!-- Title for setting tile leading to Connected devices settings [CHAR LIMIT=40]-->
<string name="connected_devices_dashboard_title">Connected devices</string>
<!-- Summary for Connected devices settings, explaning a few important settings under it [CHAR LIMIT=NONE]-->
- <string name="connected_devices_dashboard_summary">Bluetooth, Cast, NFC</string>
+ <string name="connected_devices_dashboard_summary">Bluetooth, driving mode, NFC</string>
<!-- Summary for Connected devices settings, explaning a few important settings under it [CHAR LIMIT=NONE]-->
- <string name="connected_devices_dashboard_no_nfc_summary">Bluetooth, Cast</string>
+ <string name="connected_devices_dashboard_no_nfc_summary">Bluetooth, driving mode</string>
+ <!-- Summary for Connected devices settings, explaning a few important settings under it [CHAR LIMIT=NONE]-->
+ <string name="connected_devices_dashboard_no_driving_mode_summary">Bluetooth, NFC</string>
+ <!-- Summary for Connected devices settings, explaning a few important settings under it [CHAR LIMIT=NONE]-->
+ <string name="connected_devices_dashboard_no_driving_mode_no_nfc_summary">Bluetooth</string>
<!-- Title for setting tile leading to Apps & Notification settings [CHAR LIMIT=40]-->
<string name="app_and_notification_dashboard_title">Apps & notifications</string>
<!-- Summary for Apps & Notification settings, explaining a few important settings under it [CHAR LIMIT=NONE]-->
@@ -7400,26 +7407,34 @@
<string name="zen_msg_event_reminder_footer">When Do Not Disturb is on, messages, reminders, and events will muted, except for the items you allow above. You can adjust messages settings to allow your friends, family, or other contacts to reach you.</string>
<!-- Do not disturb onboarding dialog, accept new settings [CHAR LIMIT=30]-->
- <string name="zen_onboarding_ok">Update</string>
- <!-- Do not disturb onboarding dialog, do not accept new settings [CHAR LIMIT=30]-->
- <string name="zen_onboarding_no_update">Don\'t update</string>
- <!-- Do not disturb onboarding dialog, description of new settings [CHAR LIMIT=NONE]-->
- <string name="zen_onboarding_dnd_visual_disturbances_description">Your phone can do more to help you focus.\n\nUpdate settings to:\n\n- Hide notifications completely\n\n- Allow calls from starred contacts and repeat callers</string>
- <!-- Do not disturb onboarding dialog, header prompt for settings [CHAR LIMIT=80]-->
- <string name="zen_onboarding_dnd_visual_disturbances_header">Update Do Not Disturb?</string>
-
- <!-- obsolete -->
+ <string name="zen_onboarding_ok">Done</string>
+ <!-- Do not disturb onboarding dialog, on click user goes to dnd settings page [CHAR LIMIT=30]-->
<string name="zen_onboarding_settings">Settings</string>
- <!-- obsolete -->
- <string name="zen_onboarding_more_options">You can further customize this in Settings.</string>
- <!-- obsolete -->
- <string name="zen_onboarding_screen_on_title">Block when the screen is on</string>
- <!-- obsolete -->
- <string name="zen_onboarding_screen_off_title">Block when the screen is off</string>
- <!-- obsolete -->
- <string name="zen_onboarding_screen_off_summary">Don\'t turn on the screen or wake for notifications</string>
- <!-- obsolete -->
- <string name="zen_onboarding_screen_on_summary">Don\'t show notifications at all, except for basic phone activity and status</string>
+
+ <!-- Do not disturb onboarding dialog, title for radio button [CHAR LIMIT=80]-->
+ <string name="zen_onboarding_new_setting_title">No visuals or sounds from notifications</string>
+ <!-- Do not disturb onboarding dialog, title for radio button [CHAR LIMIT=80]-->
+ <string name="zen_onboarding_current_setting_title">No sound from notifications</string>
+ <!-- Do not disturb onboarding dialog, secondary text for radio button [CHAR LIMIT=NONE]-->
+ <string name="zen_onboarding_new_setting_summary">You won\u2019t see or hear notifications. Calls from starred contacts and repeat callers are allowed.</string>
+ <!-- Do not disturb onboarding dialog, secondary text for radio button [CHAR LIMIT=NONE]-->
+ <string name="zen_onboarding_current_setting_summary">(Current setting)</string>
+
+ <!-- Do not disturb onboarding dialog, header prompt for settings [CHAR LIMIT=80]-->
+ <string name="zen_onboarding_dnd_visual_disturbances_header">Change Do Not Disturb notification settings?</string>
+
+ <!-- DO NOT TRANSLATE obsolete [CHAR LIMIT=NONE]-->
+ <string name="zen_onboarding_dnd_visual_disturbances_description" translatable="false">Your phone can do more to help you focus.\n\nUpdate settings to:\n\n- Hide notifications completely\n\n- Allow calls from starred contacts and repeat callers</string>
+ <!-- DO NOT TRANSLATE obsolete -->
+ <string name="zen_onboarding_more_options" translatable="false">You can further customize this in Settings.</string>
+ <!-- DO NOT TRANSLATE obsolete -->
+ <string name="zen_onboarding_screen_on_title" translatable="false">Block when the screen is on</string>
+ <!-- DO NOT TRANSLATE obsolete -->
+ <string name="zen_onboarding_screen_off_title" translatable="false">Block when the screen is off</string>
+ <!-- DO NOT TRANSLATE obsolete -->
+ <string name="zen_onboarding_screen_off_summary" translatable="false">Don\'t turn on the screen or wake for notifications</string>
+ <!-- DO NOT TRANSLATE obsolete -->
+ <string name="zen_onboarding_screen_on_summary" translatable="false">Don\'t show notifications at all, except for basic phone activity and status</string>
<!-- Work Sounds: Work sound settings section header. [CHAR LIMIT=50] -->
<string name="sound_work_settings">Work profile sounds</string>
@@ -7930,6 +7945,9 @@
<!-- [CHAR LIMIT=20] Zen mode settings: Calls option -->
<string name="zen_mode_calls">Calls</string>
+ <!-- [CHAR LIMIT=40] Zen mode settings: Allow calls toggle title -->
+ <string name="zen_mode_calls_title">Allow calls</string>
+
<!-- [CHAR LIMIT=20] Zen mode settings: Calls screen footer -->
<string name="zen_mode_calls_footer">When Do Not Disturb is on, incoming calls are blocked. You can adjust settings to allow your friends, family, or other contacts to reach you.</string>
@@ -7945,6 +7963,9 @@
<!-- [CHAR LIMIT=20] Zen mode settings: Messages option -->
<string name="zen_mode_messages">Messages</string>
+ <!-- [CHAR LIMIT=40] Zen mode settings: Allow messages toggle title -->
+ <string name="zen_mode_messages_title">Allow messages</string>
+
<!-- [CHAR LIMIT=50] Zen mode settings: All messages summary -->
<string name="zen_mode_all_messages">Messages</string>
@@ -7984,9 +8005,15 @@
<!-- [CHAR LIMIT=50] Zen mode settings: Reminders option -->
<string name="zen_mode_reminders">Reminders</string>
+ <!-- [CHAR LIMIT=70] Zen mode settings: Allow reminders toggle title -->
+ <string name="zen_mode_reminders_title">Allow reminders</string>
+
<!-- [CHAR LIMIT=50] Zen mode settings: Events option -->
<string name="zen_mode_events">Events</string>
+ <!-- [CHAR LIMIT=70] Zen mode settings: Allow events toggle title -->
+ <string name="zen_mode_events_title">Allow events</string>
+
<!-- [CHAR LIMIT=50] Zen mode settings: All callers summary -->
<string name="zen_mode_all_callers">anyone</string>
@@ -7999,8 +8026,11 @@
<!-- [CHAR LIMIT=50] Zen mode settings: Repeat callers option -->
<string name="zen_mode_repeat_callers">Repeat callers</string>
+ <!-- [CHAR LIMIT=70] Zen mode settings: Allow repeat callers toggle title -->
+ <string name="zen_mode_repeat_callers_title">Allow repeat callers</string>
+
<!-- [CHAR LIMIT=50] Zen mode settings: calls summary -->
- <string name="zen_mode_calls_summary_one">From <xliff:g id="caller type" example="contacts">%1$s</xliff:g> only</string>
+ <string name="zen_mode_calls_summary_one">From <xliff:g id="caller type" example="contacts">%1$s</xliff:g></string>
<!-- [CHAR LIMIT=50] Zen mode settings: calls summary -->
<string name="zen_mode_calls_summary_two">From <xliff:g id="caller type" example="starred contacts">%1$s</xliff:g> and <xliff:g id="callert tpye" example="repeat callers">%2$s</xliff:g></string>
@@ -9219,7 +9249,7 @@
<!-- Informational text about update time only, without carrier. First argument intentionally skipped. [CHAR LIMIT=30] -->
<string name="no_carrier_update_text">Updated <xliff:g name="time" example="3m">^2</xliff:g> ago</string>
- <!-- Informational text about a recent carrier and update time [CHAR LIMIT=30] -->
+ <!-- Informational text about a recent carrier and update time [CHAR LIMIT=34] -->
<string name="carrier_and_update_now_text">Updated by <xliff:g name="carrier" example="T-mobile">^1</xliff:g> just now</string>
<!-- Informational text about recent update time only, without carrier [CHAR LIMIT=30] -->
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 819202e..763d8fa 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -439,8 +439,7 @@
<item name="android:background">@drawable/btn_borderless_rect</item>
<item name="android:gravity">center</item>
<item name="android:focusable">true</item>
- <item name="android:paddingStart">8dp</item>
- <item name="android:paddingEnd">8dp</item>
+ <item name="android:padding">8dp</item>
</style>
<style name="ActionPrimaryButton" parent="android:Widget.DeviceDefault.Button.Colored"/>
diff --git a/res/xml/app_info_settings.xml b/res/xml/app_info_settings.xml
index 86b0df0..15afb5f 100644
--- a/res/xml/app_info_settings.xml
+++ b/res/xml/app_info_settings.xml
@@ -162,9 +162,16 @@
</PreferenceCategory>
<Preference
+ android:key="app_settings_link"
+ android:title="@string/app_settings_link"
+ settings:controller="com.android.settings.applications.appinfo.AppSettingPreferenceController"
+ settings:allowDividerAbove="true" />
+
+ <Preference
android:key="app_version"
android:selectable="false"
android:order="9999"
- settings:controller="com.android.settings.applications.appinfo.AppVersionPreferenceController" />
+ settings:controller="com.android.settings.applications.appinfo.AppVersionPreferenceController"
+ settings:allowDividerAbove="true" />
</PreferenceScreen>
\ No newline at end of file
diff --git a/res/xml/bluetooth_screen.xml b/res/xml/bluetooth_screen.xml
index 407feb6..9f09a8a 100644
--- a/res/xml/bluetooth_screen.xml
+++ b/res/xml/bluetooth_screen.xml
@@ -21,7 +21,7 @@
<com.android.settingslib.RestrictedPreference
android:key="bluetooth_screen_add_bt_devices"
- android:title="@string/connected_device_add_device_title"
+ android:title="@string/bluetooth_pairing_pref_title"
android:icon="@drawable/ic_menu_add"
android:summary="@string/connected_device_add_device_summary"
android:fragment="com.android.settings.bluetooth.BluetoothPairingDetail"
diff --git a/res/xml/development_settings.xml b/res/xml/development_settings.xml
index c491980..3836b43 100644
--- a/res/xml/development_settings.xml
+++ b/res/xml/development_settings.xml
@@ -254,16 +254,6 @@
android:title="@string/bluetooth_disable_absolute_volume"
android:summary="@string/bluetooth_disable_absolute_volume_summary" />
- <SwitchPreference
- android:key="bluetooth_disable_inband_ringing"
- android:title="@string/bluetooth_disable_inband_ringing"
- android:summary="@string/bluetooth_disable_inband_ringing_summary" />
-
- <SwitchPreference
- android:key="bluetooth_disable_avdtp_delay_reports"
- android:title="@string/bluetooth_disable_avdtp_delay_reports"
- android:summary="@string/bluetooth_disable_avdtp_delay_reports_summary"/>
-
<ListPreference
android:key="bluetooth_select_avrcp_version"
android:title="@string/bluetooth_select_avrcp_version_string"
diff --git a/res/xml/network_and_internet.xml b/res/xml/network_and_internet.xml
index 064d625..69d8fca 100644
--- a/res/xml/network_and_internet.xml
+++ b/res/xml/network_and_internet.xml
@@ -97,6 +97,7 @@
android:order="15"
android:dialogTitle="@string/select_private_dns_configuration_dialog_title"
android:dialogLayout="@layout/private_dns_mode_dialog"
- android:positiveButtonText="@string/save" />
+ android:positiveButtonText="@string/save"
+ android:negativeButtonText="@android:string/cancel" />
</PreferenceScreen>
diff --git a/res/xml/sound_settings.xml b/res/xml/sound_settings.xml
index 61f529f..a70c85d 100644
--- a/res/xml/sound_settings.xml
+++ b/res/xml/sound_settings.xml
@@ -44,7 +44,6 @@
android:icon="@drawable/ic_local_phone_24_lib"
android:title="@string/call_volume_option_title"
android:order="-170"
- settings:allowDividerAbove="true"
settings:controller="com.android.settings.notification.CallVolumePreferenceController"/>
<!-- Hands free profile output switcher -->
@@ -61,14 +60,7 @@
android:icon="@*android:drawable/ic_audio_ring_notif"
android:title="@string/ring_volume_option_title"
android:order="-160"
- settings:controller="com.android.settings.notification.RingVolumePreferenceController"
- settings:allowDividerAbove="true"/>
-
- <!-- Also vibrate for calls -->
- <SwitchPreference
- android:key="vibrate_when_ringing"
- android:title="@string/vibrate_when_ringing_title"
- android:order="-155"/>
+ settings:controller="com.android.settings.notification.RingVolumePreferenceController"/>
<!-- Alarm volume -->
<com.android.settings.notification.VolumeSeekBarPreference
@@ -76,7 +68,6 @@
android:icon="@*android:drawable/ic_audio_alarm"
android:title="@string/alarm_volume_option_title"
android:order="-150"
- settings:allowDividerAbove="true"
settings:controller="com.android.settings.notification.AlarmVolumePreferenceController"/>
<!-- Notification volume -->
@@ -87,6 +78,13 @@
android:order="-140"
settings:controller="com.android.settings.notification.NotificationVolumePreferenceController"/>
+ <!-- Also vibrate for calls -->
+ <SwitchPreference
+ android:key="vibrate_when_ringing"
+ android:title="@string/vibrate_when_ringing_title"
+ settings:controller="com.android.settings.notification.VibrateWhenRingPreferenceController"
+ android:order="-130"/>
+
<!-- Interruptions -->
<com.android.settingslib.RestrictedPreference
android:key="zen_mode"
@@ -102,7 +100,6 @@
android:title="@string/gesture_prevent_ringing_sound_title"
android:order="-110"
android:fragment="com.android.settings.gestures.PreventRingingGestureSettings"
- settings:allowDividerAbove="true"
settings:controller="com.android.settings.gestures.PreventRingingPreferenceController" />
<!-- Phone ringtone -->
diff --git a/res/xml/zen_mode_calls_settings.xml b/res/xml/zen_mode_calls_settings.xml
index 62d9ef4..1a6655f 100644
--- a/res/xml/zen_mode_calls_settings.xml
+++ b/res/xml/zen_mode_calls_settings.xml
@@ -25,7 +25,7 @@
<!-- Calls -->
<ListPreference
android:key="zen_mode_calls"
- android:title="@string/zen_mode_calls"
+ android:title="@string/zen_mode_calls_title"
android:entries="@array/zen_mode_contacts_entries"
android:entryValues="@array/zen_mode_contacts_values"/>
@@ -36,7 +36,7 @@
<!-- Repeat callers -->
<SwitchPreference
android:key="zen_mode_repeat_callers"
- android:title="@string/zen_mode_repeat_callers" />
+ android:title="@string/zen_mode_repeat_callers_title" />
</PreferenceCategory>
<com.android.settingslib.widget.FooterPreference/>
diff --git a/res/xml/zen_mode_msg_event_reminder_settings.xml b/res/xml/zen_mode_msg_event_reminder_settings.xml
index 2f065a6..9bee9e9 100644
--- a/res/xml/zen_mode_msg_event_reminder_settings.xml
+++ b/res/xml/zen_mode_msg_event_reminder_settings.xml
@@ -25,7 +25,7 @@
<!-- Messages -->
<ListPreference
android:key="zen_mode_messages"
- android:title="@string/zen_mode_messages"
+ android:title="@string/zen_mode_messages_title"
android:entries="@array/zen_mode_contacts_entries"
android:entryValues="@array/zen_mode_contacts_values"/>
@@ -36,12 +36,12 @@
<!-- Reminders -->
<SwitchPreference
android:key="zen_mode_reminders"
- android:title="@string/zen_mode_reminders"/>
+ android:title="@string/zen_mode_reminders_title"/>
<!-- Events -->
<SwitchPreference
android:key="zen_mode_events"
- android:title="@string/zen_mode_events"/>
+ android:title="@string/zen_mode_events_title"/>
</PreferenceCategory>
<com.android.settingslib.widget.FooterPreference />
diff --git a/src/com/android/settings/TetherSettings.java b/src/com/android/settings/TetherSettings.java
index 94c3fb5..1e56e54 100644
--- a/src/com/android/settings/TetherSettings.java
+++ b/src/com/android/settings/TetherSettings.java
@@ -387,7 +387,6 @@
if (adapter.getState() == BluetoothAdapter.STATE_OFF) {
mBluetoothEnableForTether = true;
adapter.enable();
- mBluetoothTether.setSummary(R.string.bluetooth_turning_on);
mBluetoothTether.setEnabled(false);
return;
}
diff --git a/src/com/android/settings/applications/appinfo/AppHeaderViewPreferenceController.java b/src/com/android/settings/applications/appinfo/AppHeaderViewPreferenceController.java
index 4b7631a..15d1789 100644
--- a/src/com/android/settings/applications/appinfo/AppHeaderViewPreferenceController.java
+++ b/src/com/android/settings/applications/appinfo/AppHeaderViewPreferenceController.java
@@ -68,7 +68,7 @@
mEntityHeaderController = EntityHeaderController
.newInstance(activity, mParent, mHeader.findViewById(R.id.entity_header))
.setPackageName(mPackageName)
- .setButtonActions(EntityHeaderController.ActionType.ACTION_APP_PREFERENCE,
+ .setButtonActions(EntityHeaderController.ActionType.ACTION_NONE,
EntityHeaderController.ActionType.ACTION_NONE)
.bindHeaderButtons();
}
diff --git a/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java b/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java
index 4a0db4e..e71c8d1 100755
--- a/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java
+++ b/src/com/android/settings/applications/appinfo/AppInfoDashboardFragment.java
@@ -167,6 +167,9 @@
use(AppOpenByDefaultPreferenceController.class).setParentFragment(this);
use(AppPermissionPreferenceController.class).setParentFragment(this);
use(AppPermissionPreferenceController.class).setPackageName(packageName);
+ use(AppSettingPreferenceController.class)
+ .setPackageName(packageName)
+ .setParentFragment(this);
use(AppStoragePreferenceController.class).setParentFragment(this);
use(AppVersionPreferenceController.class).setParentFragment(this);
use(InstantAppDomainsPreferenceController.class).setParentFragment(this);
diff --git a/src/com/android/settings/applications/appinfo/AppSettingPreferenceController.java b/src/com/android/settings/applications/appinfo/AppSettingPreferenceController.java
new file mode 100644
index 0000000..f2941b2
--- /dev/null
+++ b/src/com/android/settings/applications/appinfo/AppSettingPreferenceController.java
@@ -0,0 +1,77 @@
+/*
+ * 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.applications.appinfo;
+
+import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_OPEN_APP_SETTING;
+
+import android.content.Context;
+import android.content.Intent;
+import android.content.pm.ResolveInfo;
+import android.support.v7.preference.Preference;
+import android.text.TextUtils;
+
+import com.android.settings.overlay.FeatureFactory;
+
+public class AppSettingPreferenceController extends AppInfoPreferenceControllerBase {
+
+ private String mPackageName;
+
+ public AppSettingPreferenceController(Context context, String preferenceKey) {
+ super(context, preferenceKey);
+ }
+
+ public AppSettingPreferenceController setPackageName(String packageName) {
+ mPackageName = packageName;
+ return this;
+ }
+
+ @Override
+ public int getAvailabilityStatus() {
+ if (TextUtils.isEmpty(mPackageName) || mParent == null) {
+ return CONDITIONALLY_UNAVAILABLE;
+ }
+ final Intent intent = resolveIntent(
+ new Intent(Intent.ACTION_APPLICATION_PREFERENCES).setPackage(mPackageName));
+ return intent != null ? AVAILABLE : CONDITIONALLY_UNAVAILABLE;
+ }
+
+ @Override
+ public boolean handlePreferenceTreeClick(Preference preference) {
+ if (!TextUtils.equals(preference.getKey(), getPreferenceKey())) {
+ return false;
+ }
+ final Intent intent = resolveIntent(
+ new Intent(Intent.ACTION_APPLICATION_PREFERENCES).setPackage(mPackageName));
+ if (intent == null) {
+ return false;
+ }
+ FeatureFactory.getFactory(mContext).getMetricsFeatureProvider()
+ .actionWithSource(mContext, mParent.getMetricsCategory(),
+ ACTION_OPEN_APP_SETTING);
+ mContext.startActivity(intent);
+ return true;
+ }
+
+ private Intent resolveIntent(Intent i) {
+ ResolveInfo result = mContext.getPackageManager().resolveActivity(i, 0);
+ if (result != null) {
+ return new Intent(i.getAction())
+ .setClassName(result.activityInfo.packageName, result.activityInfo.name);
+ }
+ return null;
+ }
+}
diff --git a/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdater.java b/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdater.java
index c8e6f26..01c1ff6 100644
--- a/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdater.java
+++ b/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdater.java
@@ -25,11 +25,13 @@
import com.android.settings.dashboard.DashboardFragment;
import com.android.settingslib.bluetooth.LocalBluetoothManager;
import com.android.settingslib.bluetooth.CachedBluetoothDevice;
+import android.support.v7.preference.Preference;
/**
* Controller to maintain available media Bluetooth devices
*/
-public class AvailableMediaBluetoothDeviceUpdater extends BluetoothDeviceUpdater {
+public class AvailableMediaBluetoothDeviceUpdater extends BluetoothDeviceUpdater
+ implements Preference.OnPreferenceClickListener {
private static final String TAG = "AvailableMediaBluetoothDeviceUpdater";
private static final boolean DBG = false;
@@ -116,5 +118,12 @@
}
return isFilterMatched;
}
+
+ @Override
+ public boolean onPreferenceClick(Preference preference) {
+ final CachedBluetoothDevice device = ((BluetoothDevicePreference) preference)
+ .getBluetoothDevice();
+ return device.setActive();
+ }
}
diff --git a/src/com/android/settings/bluetooth/BluetoothDeviceUpdater.java b/src/com/android/settings/bluetooth/BluetoothDeviceUpdater.java
index 8937b17..bab7171 100644
--- a/src/com/android/settings/bluetooth/BluetoothDeviceUpdater.java
+++ b/src/com/android/settings/bluetooth/BluetoothDeviceUpdater.java
@@ -59,24 +59,12 @@
protected DashboardFragment mFragment;
private final boolean mShowDeviceWithoutNames;
- private Preference.OnPreferenceClickListener mDevicePreferenceClickListener = null;
-
+
@VisibleForTesting
final GearPreference.OnGearClickListener mDeviceProfilesListener = pref -> {
launchDeviceDetails(pref);
};
- private class PreferenceClickListener implements
- Preference.OnPreferenceClickListener {
- @Override
- public boolean onPreferenceClick(Preference preference) {
- final CachedBluetoothDevice device =
- ((BluetoothDevicePreference) preference).getBluetoothDevice();
- Log.i(TAG, "OnPreferenceClickListener: device=" + device);
- return device.setActive();
- }
- }
-
public BluetoothDeviceUpdater(Context context, DashboardFragment fragment,
DevicePreferenceCallback devicePreferenceCallback) {
this(fragment, devicePreferenceCallback, Utils.getLocalBtManager(context));
@@ -91,7 +79,6 @@
BLUETOOTH_SHOW_DEVICES_WITHOUT_NAMES_PROPERTY, false);
mPreferenceMap = new HashMap<>();
mLocalManager = localManager;
- mDevicePreferenceClickListener = new PreferenceClickListener();
}
/**
@@ -212,7 +199,10 @@
new BluetoothDevicePreference(mPrefContext, cachedDevice,
mShowDeviceWithoutNames);
btPreference.setOnGearClickListener(mDeviceProfilesListener);
- btPreference.setOnPreferenceClickListener(mDevicePreferenceClickListener);
+ if (this instanceof Preference.OnPreferenceClickListener) {
+ btPreference.setOnPreferenceClickListener(
+ (Preference.OnPreferenceClickListener)this);
+ }
mPreferenceMap.put(device, btPreference);
mDevicePreferenceCallback.onDeviceAdded(btPreference);
}
diff --git a/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdater.java b/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdater.java
index 34cb574..f087c6a 100644
--- a/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdater.java
+++ b/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdater.java
@@ -24,11 +24,15 @@
import com.android.settings.dashboard.DashboardFragment;
import com.android.settingslib.bluetooth.CachedBluetoothDevice;
import com.android.settingslib.bluetooth.LocalBluetoothManager;
+import android.support.v7.preference.Preference;
+import android.util.Log;
/**
* Maintain and update saved bluetooth devices(bonded but not connected)
*/
-public class SavedBluetoothDeviceUpdater extends BluetoothDeviceUpdater {
+public class SavedBluetoothDeviceUpdater extends BluetoothDeviceUpdater
+ implements Preference.OnPreferenceClickListener {
+ private static final String TAG = "SavedBluetoothDeviceUpdater";
public SavedBluetoothDeviceUpdater(Context context, DashboardFragment fragment,
DevicePreferenceCallback devicePreferenceCallback) {
@@ -57,4 +61,12 @@
final BluetoothDevice device = cachedDevice.getDevice();
return device.getBondState() == BluetoothDevice.BOND_BONDED && !device.isConnected();
}
+
+ @Override
+ public boolean onPreferenceClick(Preference preference) {
+ final CachedBluetoothDevice device = ((BluetoothDevicePreference) preference)
+ .getBluetoothDevice();
+ device.connect(true);
+ return true;
+ }
}
diff --git a/src/com/android/settings/dashboard/DashboardSummary.java b/src/com/android/settings/dashboard/DashboardSummary.java
index af7c900..20033b6 100644
--- a/src/com/android/settings/dashboard/DashboardSummary.java
+++ b/src/com/android/settings/dashboard/DashboardSummary.java
@@ -276,7 +276,7 @@
mSummaryLoader.updateSummaryToCache(category);
mStagingCategory = category;
if (mSuggestionControllerMixin == null) {
- mAdapter.setCategory(mStagingCategory);
+ ThreadUtils.postOnMainThread(() -> mAdapter.setCategory(mStagingCategory));
return;
}
if (mSuggestionControllerMixin.isSuggestionLoaded()) {
diff --git a/src/com/android/settings/dashboard/conditional/DndCondition.java b/src/com/android/settings/dashboard/conditional/DndCondition.java
index 4acd332..405ed81 100644
--- a/src/com/android/settings/dashboard/conditional/DndCondition.java
+++ b/src/com/android/settings/dashboard/conditional/DndCondition.java
@@ -83,7 +83,7 @@
@Override
public Drawable getIcon() {
- return mManager.getContext().getDrawable(R.drawable.ic_zen);
+ return mManager.getContext().getDrawable(R.drawable.ic_do_not_disturb_on_24dp);
}
@Override
diff --git a/src/com/android/settings/dashboard/conditional/RingerMutedCondition.java b/src/com/android/settings/dashboard/conditional/RingerMutedCondition.java
index bf5bc36..7f7bc2b 100644
--- a/src/com/android/settings/dashboard/conditional/RingerMutedCondition.java
+++ b/src/com/android/settings/dashboard/conditional/RingerMutedCondition.java
@@ -55,7 +55,7 @@
@Override
public Drawable getIcon() {
- return mManager.getContext().getDrawable(R.drawable.ic_volume_ringer_mute);
+ return mManager.getContext().getDrawable(R.drawable.ic_notifications_off_24dp);
}
@Override
diff --git a/src/com/android/settings/development/BluetoothDelayReportsPreferenceController.java b/src/com/android/settings/development/BluetoothDelayReportsPreferenceController.java
deleted file mode 100644
index 6c7a7dd..0000000
--- a/src/com/android/settings/development/BluetoothDelayReportsPreferenceController.java
+++ /dev/null
@@ -1,69 +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.development;
-
-import android.content.Context;
-import android.os.SystemProperties;
-import android.support.annotation.VisibleForTesting;
-import android.support.v14.preference.SwitchPreference;
-import android.support.v7.preference.Preference;
-
-import com.android.settings.core.PreferenceControllerMixin;
-import com.android.settingslib.development.DeveloperOptionsPreferenceController;
-
-public class BluetoothDelayReportsPreferenceController extends DeveloperOptionsPreferenceController
- implements Preference.OnPreferenceChangeListener, PreferenceControllerMixin {
-
- private static final String BLUETOOTH_DISABLE_AVDTP_DELAY_REPORT_KEY =
- "bluetooth_disable_avdtp_delay_reports";
- @VisibleForTesting
- static final String BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY =
- "persist.bluetooth.disabledelayreports";
-
- public BluetoothDelayReportsPreferenceController(Context context) {
- super(context);
- }
-
- @Override
- public String getPreferenceKey() {
- return BLUETOOTH_DISABLE_AVDTP_DELAY_REPORT_KEY;
- }
-
- @Override
- public boolean onPreferenceChange(Preference preference, Object newValue) {
- final boolean isDisabled = (Boolean) newValue;
- SystemProperties.set(BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY,
- isDisabled ? "true" : "false");
- return true;
- }
-
- @Override
- public void updateState(Preference preference) {
- final boolean isDisabled = SystemProperties.getBoolean(
- BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY, false /* default */);
- ((SwitchPreference) mPreference).setChecked(isDisabled);
- }
-
- @Override
- protected void onDeveloperOptionsSwitchDisabled() {
- super.onDeveloperOptionsSwitchDisabled();
- // the default setting for this preference is the disabled state
- ((SwitchPreference) mPreference).setChecked(false);
- SystemProperties.set(BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY, "false");
- }
-
-}
diff --git a/src/com/android/settings/development/BluetoothInbandRingingPreferenceController.java b/src/com/android/settings/development/BluetoothInbandRingingPreferenceController.java
deleted file mode 100644
index c64ac11..0000000
--- a/src/com/android/settings/development/BluetoothInbandRingingPreferenceController.java
+++ /dev/null
@@ -1,78 +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.development;
-
-import android.bluetooth.BluetoothHeadset;
-import android.content.Context;
-import android.os.SystemProperties;
-import android.support.annotation.VisibleForTesting;
-import android.support.v14.preference.SwitchPreference;
-import android.support.v7.preference.Preference;
-
-import com.android.settings.core.PreferenceControllerMixin;
-import com.android.settingslib.development.DeveloperOptionsPreferenceController;
-
-public class BluetoothInbandRingingPreferenceController extends DeveloperOptionsPreferenceController
- implements Preference.OnPreferenceChangeListener, PreferenceControllerMixin {
-
- private static final String BLUETOOTH_DISABLE_INBAND_RINGING_KEY =
- "bluetooth_disable_inband_ringing";
- @VisibleForTesting
- static final String BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY =
- "persist.bluetooth.disableinbandringing";
-
- public BluetoothInbandRingingPreferenceController(Context context) {
- super(context);
- }
-
- @Override
- public boolean isAvailable() {
- return isInbandRingingSupported();
- }
-
- @Override
- public String getPreferenceKey() {
- return BLUETOOTH_DISABLE_INBAND_RINGING_KEY;
- }
-
- @Override
- public boolean onPreferenceChange(Preference preference, Object newValue) {
- final boolean isChecked = (Boolean) newValue;
- SystemProperties.set(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY,
- isChecked ? "true" : "false");
- return true;
- }
-
- @Override
- public void updateState(Preference preference) {
- final boolean isEnabled = SystemProperties.getBoolean(
- BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, false /* default */);
- ((SwitchPreference) mPreference).setChecked(isEnabled);
- }
-
- @Override
- protected void onDeveloperOptionsSwitchDisabled() {
- super.onDeveloperOptionsSwitchDisabled();
- ((SwitchPreference) mPreference).setChecked(false);
- SystemProperties.set(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, "false");
- }
-
- @VisibleForTesting
- boolean isInbandRingingSupported() {
- return BluetoothHeadset.isInbandRingingSupported(mContext);
- }
-}
diff --git a/src/com/android/settings/development/DevelopmentSettingsDashboardFragment.java b/src/com/android/settings/development/DevelopmentSettingsDashboardFragment.java
index 3ee5db1..5f5d1a8 100644
--- a/src/com/android/settings/development/DevelopmentSettingsDashboardFragment.java
+++ b/src/com/android/settings/development/DevelopmentSettingsDashboardFragment.java
@@ -404,8 +404,6 @@
controllers.add(new TetheringHardwareAccelPreferenceController(context));
controllers.add(new BluetoothDeviceNoNamePreferenceController(context));
controllers.add(new BluetoothAbsoluteVolumePreferenceController(context));
- controllers.add(new BluetoothInbandRingingPreferenceController(context));
- controllers.add(new BluetoothDelayReportsPreferenceController(context));
controllers.add(new BluetoothAvrcpVersionPreferenceController(context));
controllers.add(new BluetoothAudioCodecPreferenceController(context, lifecycle,
bluetoothA2dpConfigStore));
diff --git a/src/com/android/settings/fuelgauge/BatteryBroadcastReceiver.java b/src/com/android/settings/fuelgauge/BatteryBroadcastReceiver.java
index ca4742d..3075d9b 100644
--- a/src/com/android/settings/fuelgauge/BatteryBroadcastReceiver.java
+++ b/src/com/android/settings/fuelgauge/BatteryBroadcastReceiver.java
@@ -21,9 +21,14 @@
import android.content.Intent;
import android.content.IntentFilter;
import android.os.PowerManager;
+import android.support.annotation.IntDef;
import android.support.annotation.VisibleForTesting;
import com.android.settings.Utils;
+import com.android.settings.fuelgauge.batterytip.tips.BatteryTip;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
/**
* Use this broadcastReceiver to listen to the battery change, and it will invoke
@@ -43,7 +48,19 @@
* Battery saver(e.g. off->on)
*/
public interface OnBatteryChangedListener {
- void onBatteryChanged();
+ void onBatteryChanged(@BatteryUpdateType int type);
+ }
+
+ @Retention(RetentionPolicy.SOURCE)
+ @IntDef({BatteryUpdateType.MANUAL,
+ BatteryUpdateType.BATTERY_LEVEL,
+ BatteryUpdateType.BATTERY_SAVER,
+ BatteryUpdateType.BATTERY_STATUS})
+ public @interface BatteryUpdateType {
+ int MANUAL = 0;
+ int BATTERY_LEVEL = 1;
+ int BATTERY_SAVER = 2;
+ int BATTERY_STATUS = 3;
}
@VisibleForTesting
@@ -85,14 +102,17 @@
final String batteryLevel = Utils.getBatteryPercentage(intent);
final String batteryStatus = Utils.getBatteryStatus(
mContext.getResources(), intent);
- if (forceUpdate || !batteryLevel.equals(mBatteryLevel) || !batteryStatus.equals(
- mBatteryStatus)) {
- mBatteryLevel = batteryLevel;
- mBatteryStatus = batteryStatus;
- mBatteryListener.onBatteryChanged();
+ if (forceUpdate) {
+ mBatteryListener.onBatteryChanged(BatteryUpdateType.MANUAL);
+ } else if(!batteryLevel.equals(mBatteryLevel)) {
+ mBatteryListener.onBatteryChanged(BatteryUpdateType.BATTERY_LEVEL);
+ } else if (!batteryStatus.equals(mBatteryStatus)) {
+ mBatteryListener.onBatteryChanged(BatteryUpdateType.BATTERY_STATUS);
}
+ mBatteryLevel = batteryLevel;
+ mBatteryStatus = batteryStatus;
} else if (PowerManager.ACTION_POWER_SAVE_MODE_CHANGED.equals(intent.getAction())) {
- mBatteryListener.onBatteryChanged();
+ mBatteryListener.onBatteryChanged(BatteryUpdateType.BATTERY_SAVER);
}
}
}
diff --git a/src/com/android/settings/fuelgauge/PowerUsageAdvanced.java b/src/com/android/settings/fuelgauge/PowerUsageAdvanced.java
index 327a6c5..6493430 100644
--- a/src/com/android/settings/fuelgauge/PowerUsageAdvanced.java
+++ b/src/com/android/settings/fuelgauge/PowerUsageAdvanced.java
@@ -13,6 +13,8 @@
*/
package com.android.settings.fuelgauge;
+import static com.android.settings.fuelgauge.BatteryBroadcastReceiver.BatteryUpdateType;
+
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
@@ -30,7 +32,6 @@
import com.android.settings.overlay.FeatureFactory;
import com.android.settings.search.BaseSearchIndexProvider;
import com.android.settingslib.core.AbstractPreferenceController;
-import com.android.settingslib.utils.StringUtil;
import java.util.ArrayList;
import java.util.Arrays;
@@ -106,7 +107,7 @@
mMetricsFeatureProvider.action(getContext(),
MetricsProto.MetricsEvent.ACTION_SETTINGS_MENU_BATTERY_APPS_TOGGLE,
mShowAllApps);
- restartBatteryStatsLoader();
+ restartBatteryStatsLoader(BatteryUpdateType.MANUAL);
return true;
default:
return super.onOptionsItemSelected(item);
@@ -138,7 +139,7 @@
}
@Override
- protected void refreshUi() {
+ protected void refreshUi(@BatteryUpdateType int refreshType) {
final Context context = getContext();
if (context == null) {
return;
diff --git a/src/com/android/settings/fuelgauge/PowerUsageBase.java b/src/com/android/settings/fuelgauge/PowerUsageBase.java
index b811f20..58d9d08 100644
--- a/src/com/android/settings/fuelgauge/PowerUsageBase.java
+++ b/src/com/android/settings/fuelgauge/PowerUsageBase.java
@@ -15,6 +15,8 @@
*/
package com.android.settings.fuelgauge;
+import static com.android.settings.fuelgauge.BatteryBroadcastReceiver.*;
+
import android.app.Activity;
import android.app.LoaderManager;
import android.content.Context;
@@ -26,18 +28,17 @@
import com.android.internal.os.BatteryStatsHelper;
import com.android.settings.dashboard.DashboardFragment;
-import com.android.settingslib.utils.AsyncLoader;
/**
* Common base class for things that need to show the battery usage graph.
*/
-public abstract class PowerUsageBase extends DashboardFragment
- implements LoaderManager.LoaderCallbacks<BatteryStatsHelper> {
+public abstract class PowerUsageBase extends DashboardFragment {
// +1 to allow ordering for PowerUsageSummary.
@VisibleForTesting
static final int MENU_STATS_REFRESH = Menu.FIRST + 1;
private static final String TAG = "PowerUsageBase";
+ private static final String KEY_REFRESH_TYPE = "refresh_type";
protected BatteryStatsHelper mStatsHelper;
protected UserManager mUm;
@@ -57,8 +58,8 @@
setHasOptionsMenu(true);
mBatteryBroadcastReceiver = new BatteryBroadcastReceiver(getContext());
- mBatteryBroadcastReceiver.setBatteryChangedListener(() -> {
- restartBatteryStatsLoader();
+ mBatteryBroadcastReceiver.setBatteryChangedListener(type -> {
+ restartBatteryStatsLoader(type);
});
}
@@ -81,11 +82,14 @@
mBatteryBroadcastReceiver.unRegister();
}
- protected void restartBatteryStatsLoader() {
- getLoaderManager().restartLoader(0, Bundle.EMPTY, this);
+ protected void restartBatteryStatsLoader(int refreshType) {
+ final Bundle bundle = new Bundle();
+ bundle.putInt(KEY_REFRESH_TYPE, refreshType);
+
+ getLoaderManager().restartLoader(0, bundle, new PowerLoaderCallback());
}
- protected abstract void refreshUi();
+ protected abstract void refreshUi(@BatteryUpdateType int refreshType);
protected void updatePreference(BatteryHistoryPreference historyPref) {
final long startTime = System.currentTimeMillis();
@@ -93,21 +97,30 @@
BatteryUtils.logRuntime(TAG, "updatePreference", startTime);
}
- @Override
- public Loader<BatteryStatsHelper> onCreateLoader(int id,
- Bundle args) {
- return new BatteryStatsHelperLoader(getContext());
- }
+ /**
+ * {@link android.app.LoaderManager.LoaderCallbacks} for {@link PowerUsageBase} to load
+ * the {@link BatteryStatsHelper}
+ */
+ public class PowerLoaderCallback implements LoaderManager.LoaderCallbacks<BatteryStatsHelper> {
+ private int mRefreshType;
- @Override
- public void onLoadFinished(Loader<BatteryStatsHelper> loader,
- BatteryStatsHelper statsHelper) {
- mStatsHelper = statsHelper;
- refreshUi();
- }
+ @Override
+ public Loader<BatteryStatsHelper> onCreateLoader(int id,
+ Bundle args) {
+ mRefreshType = args.getInt(KEY_REFRESH_TYPE);
+ return new BatteryStatsHelperLoader(getContext());
+ }
- @Override
- public void onLoaderReset(Loader<BatteryStatsHelper> loader) {
+ @Override
+ public void onLoadFinished(Loader<BatteryStatsHelper> loader,
+ BatteryStatsHelper statsHelper) {
+ mStatsHelper = statsHelper;
+ refreshUi(mRefreshType);
+ }
+ @Override
+ public void onLoaderReset(Loader<BatteryStatsHelper> loader) {
+
+ }
}
}
diff --git a/src/com/android/settings/fuelgauge/PowerUsageSummary.java b/src/com/android/settings/fuelgauge/PowerUsageSummary.java
index 0563815..e4f7a72 100644
--- a/src/com/android/settings/fuelgauge/PowerUsageSummary.java
+++ b/src/com/android/settings/fuelgauge/PowerUsageSummary.java
@@ -16,6 +16,8 @@
package com.android.settings.fuelgauge;
+import static com.android.settings.fuelgauge.BatteryBroadcastReceiver.BatteryUpdateType;
+
import android.app.Activity;
import android.app.LoaderManager;
import android.app.LoaderManager.LoaderCallbacks;
@@ -277,7 +279,7 @@
} else {
mStatsType = BatteryStats.STATS_SINCE_CHARGED;
}
- refreshUi();
+ refreshUi(BatteryUpdateType.MANUAL);
return true;
case MENU_ADVANCED_BATTERY:
new SubSettingLauncher(getContext())
@@ -291,14 +293,15 @@
}
}
- protected void refreshUi() {
+ protected void refreshUi(@BatteryUpdateType int refreshType) {
final Context context = getContext();
if (context == null) {
return;
}
- // Only skip BatteryTipLoader for the first time when device is rotated
- if (mNeedUpdateBatteryTip) {
+ // Skip BatteryTipLoader if device is rotated or only battery level change
+ if (mNeedUpdateBatteryTip
+ && refreshType != BatteryUpdateType.BATTERY_LEVEL) {
restartBatteryTipLoader();
} else {
mNeedUpdateBatteryTip = true;
@@ -397,8 +400,9 @@
}
@Override
- protected void restartBatteryStatsLoader() {
- restartBatteryStatsLoader(true /* clearHeader */);
+ protected void restartBatteryStatsLoader(@BatteryUpdateType int refreshType) {
+ super.restartBatteryStatsLoader(refreshType);
+ mBatteryHeaderPreferenceController.quickUpdateHeaderPreference();
}
@Override
@@ -407,13 +411,6 @@
mBatteryTipPreferenceController.saveInstanceState(outState);
}
- void restartBatteryStatsLoader(boolean clearHeader) {
- super.restartBatteryStatsLoader();
- if (clearHeader) {
- mBatteryHeaderPreferenceController.quickUpdateHeaderPreference();
- }
- }
-
@Override
public void onBatteryTipHandled(BatteryTip batteryTip) {
restartBatteryTipLoader();
@@ -428,7 +425,7 @@
mContext = context;
mLoader = loader;
mBatteryBroadcastReceiver = new BatteryBroadcastReceiver(mContext);
- mBatteryBroadcastReceiver.setBatteryChangedListener(() -> {
+ mBatteryBroadcastReceiver.setBatteryChangedListener(type -> {
BatteryInfo.getBatteryInfo(mContext, new BatteryInfo.Callback() {
@Override
public void onBatteryInfoLoaded(BatteryInfo info) {
diff --git a/src/com/android/settings/gestures/SwipeUpPreferenceController.java b/src/com/android/settings/gestures/SwipeUpPreferenceController.java
index 27c7241..b768a2c 100644
--- a/src/com/android/settings/gestures/SwipeUpPreferenceController.java
+++ b/src/com/android/settings/gestures/SwipeUpPreferenceController.java
@@ -24,7 +24,7 @@
import android.provider.Settings;
import android.support.annotation.VisibleForTesting;
-import com.android.settings.R;
+import com.android.internal.R;
public class SwipeUpPreferenceController extends GesturePreferenceController {
@@ -46,7 +46,7 @@
}
final ComponentName recentsComponentName = ComponentName.unflattenFromString(
- context.getString(com.android.internal.R.string.config_recentsComponentName));
+ context.getString(R.string.config_recentsComponentName));
final Intent quickStepIntent = new Intent(ACTION_QUICKSTEP)
.setPackage(recentsComponentName.getPackageName());
if (context.getPackageManager().resolveService(quickStepIntent,
@@ -81,7 +81,7 @@
@Override
public boolean isChecked() {
final int defaultValue = mContext.getResources()
- .getBoolean(com.android.internal.R.bool.config_swipe_up_gesture_default) ? ON : OFF;
+ .getBoolean(R.bool.config_swipe_up_gesture_default) ? ON : OFF;
final int swipeUpEnabled = Settings.Secure.getInt(mContext.getContentResolver(),
Settings.Secure.SWIPE_UP_TO_SWITCH_APPS_ENABLED, defaultValue);
return swipeUpEnabled != OFF;
diff --git a/src/com/android/settings/network/PrivateDnsModeDialogPreference.java b/src/com/android/settings/network/PrivateDnsModeDialogPreference.java
index 178aa27..969cb11 100644
--- a/src/com/android/settings/network/PrivateDnsModeDialogPreference.java
+++ b/src/com/android/settings/network/PrivateDnsModeDialogPreference.java
@@ -156,16 +156,18 @@
@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(context.getContentResolver(), HOSTNAME_KEY,
- mEditText.getText().toString());
- }
+ if (which == DialogInterface.BUTTON_POSITIVE) {
+ 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(context.getContentResolver(), HOSTNAME_KEY,
+ mEditText.getText().toString());
+ }
- FeatureFactory.getFactory(context).getMetricsFeatureProvider().action(context,
- MetricsProto.MetricsEvent.ACTION_PRIVATE_DNS_MODE, mMode);
- Settings.Global.putString(context.getContentResolver(), MODE_KEY, mMode);
+ FeatureFactory.getFactory(context).getMetricsFeatureProvider().action(context,
+ MetricsProto.MetricsEvent.ACTION_PRIVATE_DNS_MODE, mMode);
+ Settings.Global.putString(context.getContentResolver(), MODE_KEY, mMode);
+ }
}
@Override
diff --git a/src/com/android/settings/network/TetherPreferenceController.java b/src/com/android/settings/network/TetherPreferenceController.java
index 1c9959e..1f19031 100644
--- a/src/com/android/settings/network/TetherPreferenceController.java
+++ b/src/com/android/settings/network/TetherPreferenceController.java
@@ -131,7 +131,8 @@
@Override
public void onCreate(Bundle savedInstanceState) {
- if (mBluetoothAdapter != null) {
+ if (mBluetoothAdapter != null &&
+ mBluetoothAdapter.getState() == BluetoothAdapter.STATE_ON) {
mBluetoothAdapter.getProfileProxy(mContext, mBtProfileServiceListener,
BluetoothProfile.PAN);
}
diff --git a/src/com/android/settings/notification/RingVolumePreferenceController.java b/src/com/android/settings/notification/RingVolumePreferenceController.java
index e328cd2..c4c71c4 100644
--- a/src/com/android/settings/notification/RingVolumePreferenceController.java
+++ b/src/com/android/settings/notification/RingVolumePreferenceController.java
@@ -17,7 +17,6 @@
package com.android.settings.notification;
import android.app.NotificationManager;
-import android.arch.lifecycle.LifecycleObserver;
import android.arch.lifecycle.OnLifecycleEvent;
import android.content.BroadcastReceiver;
import android.content.ComponentName;
@@ -47,6 +46,8 @@
private final RingReceiver mReceiver = new RingReceiver();
private final H mHandler = new H();
+ private int mMuteIcon;
+
public RingVolumePreferenceController(Context context) {
this(context, KEY_RING_VOLUME);
}
@@ -94,7 +95,7 @@
@Override
public int getMuteIcon() {
- return R.drawable.ic_volume_ringer_vibrate;
+ return mMuteIcon;
}
private void updateRingerMode() {
@@ -104,11 +105,6 @@
updatePreferenceIcon();
}
- private boolean wasRingerModeVibrate() {
- return mVibrator != null && mRingerMode == AudioManager.RINGER_MODE_SILENT
- && mHelper.getLastAudibleStreamVolume(getAudioStream()) == 0;
- }
-
private void updateEffectsSuppressor() {
final ComponentName suppressor = NotificationManager.from(mContext).getEffectsSuppressor();
if (Objects.equals(suppressor, mSuppressor)) return;
@@ -122,10 +118,15 @@
private void updatePreferenceIcon() {
if (mPreference != null) {
- mPreference.showIcon(
- mRingerMode == AudioManager.RINGER_MODE_VIBRATE || wasRingerModeVibrate()
- ? com.android.internal.R.drawable.ic_audio_ring_notif_vibrate
- : com.android.internal.R.drawable.ic_audio_ring_notif);
+ if (mRingerMode == AudioManager.RINGER_MODE_VIBRATE) {
+ mMuteIcon = R.drawable.ic_volume_ringer_vibrate;
+ mPreference.showIcon(com.android.internal.R.drawable.ic_audio_ring_notif_vibrate);
+ } else if (mRingerMode == AudioManager.RINGER_MODE_SILENT) {
+ mMuteIcon = R.drawable.ic_notifications_off_24dp;
+ mPreference.showIcon(com.android.internal.R.drawable.ic_audio_ring_notif_mute);
+ } else {
+ mPreference.showIcon(com.android.internal.R.drawable.ic_audio_ring_notif);
+ }
}
}
diff --git a/src/com/android/settings/notification/SoundSettings.java b/src/com/android/settings/notification/SoundSettings.java
index 3ba71a1..7fffb76 100644
--- a/src/com/android/settings/notification/SoundSettings.java
+++ b/src/com/android/settings/notification/SoundSettings.java
@@ -48,7 +48,6 @@
private static final String SELECTED_PREFERENCE_KEY = "selected_preference";
private static final int REQUEST_CODE = 200;
private static final String KEY_ZEN_MODE = "zen_mode";
-
private static final int SAMPLE_CUTOFF = 2000; // manually cap sample playback at 2 seconds
@VisibleForTesting
@@ -195,7 +194,6 @@
SoundSettings fragment, Lifecycle lifecycle) {
final List<AbstractPreferenceController> controllers = new ArrayList<>();
controllers.add(new ZenModePreferenceController(context, lifecycle, KEY_ZEN_MODE));
- controllers.add(new VibrateWhenRingPreferenceController(context));
// Volumes are added via xml
diff --git a/src/com/android/settings/notification/VibrateWhenRingPreferenceController.java b/src/com/android/settings/notification/VibrateWhenRingPreferenceController.java
index d41e16b..d2ff7c5 100644
--- a/src/com/android/settings/notification/VibrateWhenRingPreferenceController.java
+++ b/src/com/android/settings/notification/VibrateWhenRingPreferenceController.java
@@ -16,6 +16,8 @@
package com.android.settings.notification;
+import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;
+
import android.content.ContentResolver;
import android.content.Context;
import android.database.ContentObserver;
@@ -24,26 +26,41 @@
import android.provider.Settings;
import android.support.v7.preference.Preference;
import android.support.v7.preference.PreferenceScreen;
-import android.support.v7.preference.TwoStatePreference;
import com.android.settings.Utils;
-import com.android.settings.core.PreferenceControllerMixin;
-import com.android.settingslib.core.AbstractPreferenceController;
+import com.android.settings.core.TogglePreferenceController;
import com.android.settingslib.core.lifecycle.LifecycleObserver;
import com.android.settingslib.core.lifecycle.events.OnPause;
import com.android.settingslib.core.lifecycle.events.OnResume;
-import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;
-
-public class VibrateWhenRingPreferenceController extends AbstractPreferenceController
- implements PreferenceControllerMixin, Preference.OnPreferenceChangeListener,
- LifecycleObserver, OnResume, OnPause {
+public class VibrateWhenRingPreferenceController extends TogglePreferenceController
+ implements LifecycleObserver, OnResume, OnPause {
private static final String KEY_VIBRATE_WHEN_RINGING = "vibrate_when_ringing";
+ private final int DEFAULT_VALUE = 0;
+ private final int NOTIFICATION_VIBRATE_WHEN_RINGING = 1;
private SettingObserver mSettingObserver;
- public VibrateWhenRingPreferenceController(Context context) {
- super(context);
+ public VibrateWhenRingPreferenceController(Context context, String key) {
+ super(context, key);
+ }
+
+ @Override
+ public boolean isChecked() {
+ return Settings.System.getInt(mContext.getContentResolver(),
+ VIBRATE_WHEN_RINGING, DEFAULT_VALUE) != DEFAULT_VALUE;
+ }
+
+ @Override
+ public boolean setChecked(boolean isChecked) {
+ return Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
+ isChecked ? NOTIFICATION_VIBRATE_WHEN_RINGING : DEFAULT_VALUE);
+ }
+
+ @Override
+ @AvailabilityStatus
+ public int getAvailabilityStatus() {
+ return Utils.isVoiceCapable(mContext) ? AVAILABLE : UNSUPPORTED_ON_DEVICE;
}
@Override
@@ -70,38 +87,10 @@
}
}
- @Override
- public boolean handlePreferenceTreeClick(Preference preference) {
- return false;
- }
-
- @Override
- public String getPreferenceKey() {
- return KEY_VIBRATE_WHEN_RINGING;
- }
-
- @Override
- public boolean isAvailable() {
- return Utils.isVoiceCapable(mContext);
- }
-
- @Override
- public void updateState(Preference preference) {
- ((TwoStatePreference) preference).setChecked(
- Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 0) != 0);
- }
-
- @Override
- public boolean onPreferenceChange(Preference preference, Object newValue) {
- final boolean val = (Boolean) newValue;
- return Settings.System.putInt(mContext.getContentResolver(),
- VIBRATE_WHEN_RINGING, val ? 1 : 0);
- }
-
private final class SettingObserver extends ContentObserver {
private final Uri VIBRATE_WHEN_RINGING_URI =
- Settings.System.getUriFor(VIBRATE_WHEN_RINGING);
+ Settings.System.getUriFor(VIBRATE_WHEN_RINGING);
private final Preference mPreference;
@@ -127,5 +116,4 @@
}
}
}
-
}
diff --git a/src/com/android/settings/notification/ZenModeRestrictNotificationsSettings.java b/src/com/android/settings/notification/ZenModeRestrictNotificationsSettings.java
index 14b82f5..8d0cd0e 100644
--- a/src/com/android/settings/notification/ZenModeRestrictNotificationsSettings.java
+++ b/src/com/android/settings/notification/ZenModeRestrictNotificationsSettings.java
@@ -16,22 +16,15 @@
package com.android.settings.notification;
-import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_ZEN_SHOW_CUSTOM;
-
import android.content.Context;
import android.os.Bundle;
import android.provider.SearchIndexableResource;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.settings.R;
-import com.android.settings.overlay.FeatureFactory;
import com.android.settings.search.BaseSearchIndexProvider;
import com.android.settings.search.Indexable;
import com.android.settingslib.core.AbstractPreferenceController;
-import com.android.settingslib.core.instrumentation.MetricsFeatureProvider;
import com.android.settingslib.core.lifecycle.Lifecycle;
import com.android.settingslib.widget.FooterPreference;
@@ -40,67 +33,21 @@
public class ZenModeRestrictNotificationsSettings extends ZenModeSettingsBase implements Indexable {
- protected static final int APP_MENU_SHOW_CUSTOM = 1;
- protected boolean mShowMenuSelected;
-
@Override
public void onCreate(Bundle icicle) {
super.onCreate(icicle);
}
@Override
- public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
- menu.add(0, APP_MENU_SHOW_CUSTOM, 0, R.string.zen_mode_restrict_notifications_enable_custom)
- .setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER);
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem menuItem) {
- if (menuItem.getItemId() == APP_MENU_SHOW_CUSTOM) {
- final FeatureFactory featureFactory = FeatureFactory.getFactory(mContext);
- MetricsFeatureProvider metrics = featureFactory.getMetricsFeatureProvider();
-
- mShowMenuSelected = !mShowMenuSelected;
-
- ZenModeVisEffectsCustomPreferenceController custom =
- use(ZenModeVisEffectsCustomPreferenceController.class);
- custom.setShownByMenu(mShowMenuSelected);
- custom.displayPreference(getPreferenceScreen());
-
- if (mShowMenuSelected) {
- metrics.action(mContext, ACTION_ZEN_SHOW_CUSTOM, true);
- } else {
- metrics.action(mContext, ACTION_ZEN_SHOW_CUSTOM, false);
- }
-
- return true;
- }
- return false;
- }
-
- @Override
- public void onPrepareOptionsMenu(Menu menu) {
- if (mShowMenuSelected) {
- menu.findItem(APP_MENU_SHOW_CUSTOM)
- .setTitle(R.string.zen_mode_restrict_notifications_disable_custom);
- } else {
- menu.findItem(APP_MENU_SHOW_CUSTOM)
- .setTitle(R.string.zen_mode_restrict_notifications_enable_custom);
- }
-
- if (mShowMenuSelected && use(ZenModeVisEffectsCustomPreferenceController.class)
- .areCustomOptionsSelected()) {
- menu.findItem(APP_MENU_SHOW_CUSTOM).setEnabled(false);
- } else {
- menu.findItem(APP_MENU_SHOW_CUSTOM).setEnabled(true);
- }
- }
-
- @Override
protected List<AbstractPreferenceController> createPreferenceControllers(Context context) {
return buildPreferenceControllers(context, getLifecycle());
}
+ @Override
+ public int getHelpResource() {
+ return R.string.help_uri_interruptions;
+ }
+
private static List<AbstractPreferenceController> buildPreferenceControllers(Context context,
Lifecycle lifecycle) {
List<AbstractPreferenceController> controllers = new ArrayList<>();
diff --git a/src/com/android/settings/notification/ZenModeSettings.java b/src/com/android/settings/notification/ZenModeSettings.java
index ec0f619..62b3fe5 100644
--- a/src/com/android/settings/notification/ZenModeSettings.java
+++ b/src/com/android/settings/notification/ZenModeSettings.java
@@ -30,6 +30,7 @@
import android.app.NotificationManager;
import android.app.NotificationManager.Policy;
import android.content.Context;
+import android.icu.text.ListFormatter;
import android.provider.SearchIndexableResource;
import android.provider.Settings;
import android.service.notification.ZenModeConfig;
@@ -166,17 +167,20 @@
return mContext.getString(R.string.join_two_items, enabledCategories.get(0),
enabledCategories.get(1).toLowerCase());
} else if (numCategories == 3){
- String secondaryText = mContext.getString(R.string.join_two_unrelated_items,
- enabledCategories.get(0), enabledCategories.get(1).toLowerCase());
- return mContext.getString(R.string.join_many_items_last, secondaryText,
- enabledCategories.get(2).toLowerCase());
+ final List<String> summaries = new ArrayList<>();
+ summaries.add(enabledCategories.get(0));
+ summaries.add(enabledCategories.get(1).toLowerCase());
+ summaries.add(enabledCategories.get(2).toLowerCase());
+
+ return ListFormatter.getInstance().format(summaries);
} else {
- String secondaryText = mContext.getString(R.string.join_many_items_middle,
- enabledCategories.get(0), enabledCategories.get(1).toLowerCase());
- secondaryText = mContext.getString(R.string.join_many_items_middle, secondaryText,
- enabledCategories.get(2).toLowerCase());
- return mContext.getString(R.string.join_many_items_last, secondaryText,
- mContext.getString(R.string.zen_mode_other_options));
+ final List<String> summaries = new ArrayList<>();
+ summaries.add(enabledCategories.get(0));
+ summaries.add(enabledCategories.get(1).toLowerCase());
+ summaries.add(enabledCategories.get(2).toLowerCase());
+ summaries.add(mContext.getString(R.string.zen_mode_other_options));
+
+ return ListFormatter.getInstance().format(summaries);
}
}
diff --git a/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceController.java b/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceController.java
index 83ab037..0a7f726 100644
--- a/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceController.java
+++ b/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceController.java
@@ -28,7 +28,6 @@
public class ZenModeVisEffectsCustomPreferenceController
extends AbstractZenModePreferenceController {
- protected boolean mShowMenuSelected;
protected static final int INTERRUPTIVE_EFFECTS = Policy.SUPPRESSED_EFFECT_AMBIENT
| Policy.SUPPRESSED_EFFECT_PEEK
| Policy.SUPPRESSED_EFFECT_LIGHTS
@@ -41,11 +40,7 @@
@Override
public boolean isAvailable() {
- if (mShowMenuSelected) {
- return true;
- }
-
- return areCustomOptionsSelected();
+ return true;
}
@Override
@@ -64,10 +59,6 @@
});
}
- protected void setShownByMenu(boolean shown) {
- mShowMenuSelected = shown;
- }
-
protected boolean areCustomOptionsSelected() {
boolean allEffectsSuppressed =
Policy.areAllVisualEffectsSuppressed(mBackend.mPolicy.suppressedVisualEffects);
diff --git a/src/com/android/settings/notification/ZenOnboardingActivity.java b/src/com/android/settings/notification/ZenOnboardingActivity.java
index ff86ef6..fca1a6c 100644
--- a/src/com/android/settings/notification/ZenOnboardingActivity.java
+++ b/src/com/android/settings/notification/ZenOnboardingActivity.java
@@ -20,12 +20,14 @@
import android.app.NotificationManager;
import android.app.NotificationManager.Policy;
import android.content.Context;
+import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.provider.Settings;
import android.text.format.DateUtils;
import android.util.Log;
import android.view.View;
+import android.widget.RadioButton;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.logging.MetricsLogger;
@@ -39,13 +41,16 @@
private static final String TAG = "ZenOnboardingActivity";
@VisibleForTesting
- static final String PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME =
+ static final String PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME =
"pref_zen_suggestion_first_display_time_ms";
@VisibleForTesting
- static final String PREF_KEY_SUGGESTION_VIEWED = "pref_zen_suggestion_viewed";
- @VisibleForTesting
static final long ALWAYS_SHOW_THRESHOLD = DateUtils.DAY_IN_MILLIS * 14;
+ View mNewSetting;
+ View mKeepCurrentSetting;
+ RadioButton mNewSettingButton;
+ RadioButton mKeepCurrentSettingButton;
+
private NotificationManager mNm;
private MetricsLogger mMetrics;
@@ -66,6 +71,34 @@
protected void setupUI() {
setContentView(R.layout.zen_onboarding);
+ mNewSetting = findViewById(R.id.zen_onboarding_new_setting);
+ mKeepCurrentSetting = findViewById(R.id.zen_onboarding_current_setting);
+ mNewSettingButton = findViewById(R.id.zen_onboarding_new_setting_button);
+ mKeepCurrentSettingButton = findViewById(R.id.zen_onboarding_current_setting_button);
+
+ View.OnClickListener newSettingClickListener = new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ mKeepCurrentSettingButton.setChecked(false);
+ mNewSettingButton.setChecked(true);
+ }
+ };
+
+ View.OnClickListener currentSettingClickListener = new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ mKeepCurrentSettingButton.setChecked(true);
+ mNewSettingButton.setChecked(false);
+ }
+ };
+
+ mNewSetting.setOnClickListener(newSettingClickListener);
+ mNewSettingButton.setOnClickListener(newSettingClickListener);
+
+ mKeepCurrentSetting.setOnClickListener(currentSettingClickListener);
+ mKeepCurrentSettingButton.setOnClickListener(currentSettingClickListener);
+
+ mKeepCurrentSettingButton.setChecked(true);
mMetrics.visible(MetricsEvent.SETTINGS_ZEN_ONBOARDING);
}
@@ -79,25 +112,27 @@
mMetrics = ml;
}
- public void close(View button) {
- mMetrics.action(MetricsEvent.ACTION_ZEN_ONBOARDING_KEEP_CURRENT_SETTINGS);
-
- Settings.Global.putInt(getApplicationContext().getContentResolver(),
- Settings.Global.ZEN_SETTINGS_UPDATED, 1);
-
- finishAndRemoveTask();
+ public void launchSettings(View button) {
+ mMetrics.action(MetricsEvent.ACTION_ZEN_ONBOARDING_SETTINGS);
+ Intent settings = new Intent(Settings.ACTION_ZEN_MODE_SETTINGS);
+ settings.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
+ startActivity(settings);
}
public void save(View button) {
- mMetrics.action(MetricsEvent.ACTION_ZEN_ONBOARDING_OK);
NotificationManager.Policy policy = mNm.getNotificationPolicy();
- NotificationManager.Policy newPolicy = new NotificationManager.Policy(
- Policy.PRIORITY_CATEGORY_REPEAT_CALLERS | policy.priorityCategories,
- Policy.PRIORITY_SENDERS_STARRED,
- policy.priorityMessageSenders,
- NotificationManager.Policy.getAllSuppressedVisualEffects());
- mNm.setNotificationPolicy(newPolicy);
+ if (mNewSettingButton.isChecked()) {
+ NotificationManager.Policy newPolicy = new NotificationManager.Policy(
+ Policy.PRIORITY_CATEGORY_REPEAT_CALLERS | policy.priorityCategories,
+ Policy.PRIORITY_SENDERS_STARRED,
+ policy.priorityMessageSenders,
+ NotificationManager.Policy.getAllSuppressedVisualEffects());
+ mNm.setNotificationPolicy(newPolicy);
+ mMetrics.action(MetricsEvent.ACTION_ZEN_ONBOARDING_OK);
+ } else {
+ mMetrics.action(MetricsEvent.ACTION_ZEN_ONBOARDING_KEEP_CURRENT_SETTINGS);
+ }
Settings.Global.putInt(getApplicationContext().getContentResolver(),
Settings.Global.ZEN_SETTINGS_UPDATED, 1);
@@ -143,11 +178,11 @@
final long currentTimeMs = System.currentTimeMillis();
final long firstDisplayTimeMs;
- if (!prefs.contains(PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME)) {
+ if (!prefs.contains(PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME)) {
firstDisplayTimeMs = currentTimeMs;
- prefs.edit().putLong(PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME, currentTimeMs).commit();
+ prefs.edit().putLong(PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME, currentTimeMs).commit();
} else {
- firstDisplayTimeMs = prefs.getLong(PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME, -1);
+ firstDisplayTimeMs = prefs.getLong(PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME, -1);
}
final long showTimeMs = firstDisplayTimeMs + ALWAYS_SHOW_THRESHOLD;
diff --git a/src/com/android/settings/search/DeviceIndexFeatureProvider.java b/src/com/android/settings/search/DeviceIndexFeatureProvider.java
index a171844..8e64d79 100644
--- a/src/com/android/settings/search/DeviceIndexFeatureProvider.java
+++ b/src/com/android/settings/search/DeviceIndexFeatureProvider.java
@@ -65,7 +65,7 @@
context.getSystemService(JobScheduler.class).schedule(
new JobInfo.Builder(jobId, jobComponent)
.setPersisted(true)
- .setMinimumLatency(1)
+ .setMinimumLatency(1000)
.setOverrideDeadline(1)
.build());
diff --git a/src/com/android/settings/search/DeviceIndexUpdateJobService.java b/src/com/android/settings/search/DeviceIndexUpdateJobService.java
index 12a9cf0..19b7d5e 100644
--- a/src/com/android/settings/search/DeviceIndexUpdateJobService.java
+++ b/src/com/android/settings/search/DeviceIndexUpdateJobService.java
@@ -53,10 +53,12 @@
@Override
public boolean onStartJob(JobParameters params) {
if (DEBUG) Log.d(TAG, "onStartJob");
- mRunningJob = true;
- Thread thread = new Thread(() -> updateIndex(params));
- thread.setPriority(Thread.MIN_PRIORITY);
- thread.start();
+ if (!mRunningJob) {
+ mRunningJob = true;
+ Thread thread = new Thread(() -> updateIndex(params));
+ thread.setPriority(Thread.MIN_PRIORITY);
+ thread.start();
+ }
return true;
}
@@ -122,7 +124,7 @@
}
protected CharSequence findTitle(Slice loadedSlice, SliceMetadata metaData) {
- ListContent content = new ListContent(this, loadedSlice);
+ ListContent content = new ListContent(null, loadedSlice);
SliceItem headerItem = content.getHeaderItem();
if (headerItem == null) {
if (content.getRowItems().size() != 0) {
diff --git a/src/com/android/settings/slices/SettingsSliceProvider.java b/src/com/android/settings/slices/SettingsSliceProvider.java
index af165da..8f07447 100644
--- a/src/com/android/settings/slices/SettingsSliceProvider.java
+++ b/src/com/android/settings/slices/SettingsSliceProvider.java
@@ -18,6 +18,8 @@
import static android.Manifest.permission.READ_SEARCH_INDEXABLES;
+import static com.android.settings.wifi.calling.WifiCallingSliceHelper.PATH_WIFI_CALLING;
+
import android.app.PendingIntent;
import android.app.slice.SliceManager;
import android.content.ContentResolver;
@@ -34,7 +36,13 @@
import android.util.Log;
import android.util.Pair;
+import androidx.slice.Slice;
+import androidx.slice.SliceProvider;
+import androidx.slice.builders.ListBuilder;
+import androidx.slice.builders.SliceAction;
+
import com.android.settings.R;
+import com.android.settings.overlay.FeatureFactory;
import com.android.settingslib.utils.ThreadUtils;
import java.net.URISyntaxException;
@@ -45,11 +53,6 @@
import java.util.WeakHashMap;
import java.util.concurrent.ConcurrentHashMap;
-import androidx.slice.Slice;
-import androidx.slice.SliceProvider;
-import androidx.slice.builders.ListBuilder;
-import androidx.slice.builders.SliceAction;
-
/**
* A {@link SliceProvider} for Settings to enabled inline results in system apps.
*
@@ -160,6 +163,11 @@
switch (path) {
case "/" + PATH_WIFI:
return createWifiSlice(sliceUri);
+ case "/" + PATH_WIFI_CALLING:
+ return FeatureFactory.getFactory(getContext())
+ .getSlicesFeatureProvider()
+ .getNewWifiCallingSliceHelper(getContext())
+ .createWifiCallingSlice(sliceUri);
}
SliceData cachedSliceData = mSliceWeakDataCache.get(sliceUri);
diff --git a/src/com/android/settings/slices/SliceBroadcastReceiver.java b/src/com/android/settings/slices/SliceBroadcastReceiver.java
index 47a7f5a..0409734 100644
--- a/src/com/android/settings/slices/SliceBroadcastReceiver.java
+++ b/src/com/android/settings/slices/SliceBroadcastReceiver.java
@@ -21,6 +21,7 @@
import static com.android.settings.slices.SettingsSliceProvider.ACTION_WIFI_CHANGED;
import static com.android.settings.slices.SettingsSliceProvider.EXTRA_SLICE_KEY;
import static com.android.settings.slices.SettingsSliceProvider.EXTRA_SLICE_PLATFORM_DEFINED;
+import static com.android.settings.wifi.calling.WifiCallingSliceHelper.ACTION_WIFI_CALLING_CHANGED;
import android.app.slice.Slice;
import android.content.BroadcastReceiver;
@@ -79,6 +80,12 @@
context.getContentResolver().notifyChange(uri, null);
}, 1000);
break;
+ case ACTION_WIFI_CALLING_CHANGED:
+ FeatureFactory.getFactory(context)
+ .getSlicesFeatureProvider()
+ .getNewWifiCallingSliceHelper(context)
+ .handleWifiCallingChanged(intent);
+ break;
}
}
diff --git a/src/com/android/settings/slices/SliceBuilderUtils.java b/src/com/android/settings/slices/SliceBuilderUtils.java
index be2e8df..d744fbd 100644
--- a/src/com/android/settings/slices/SliceBuilderUtils.java
+++ b/src/com/android/settings/slices/SliceBuilderUtils.java
@@ -24,11 +24,11 @@
import static com.android.settings.slices.SettingsSliceProvider.EXTRA_SLICE_KEY;
import static com.android.settings.slices.SettingsSliceProvider.EXTRA_SLICE_PLATFORM_DEFINED;
+import android.annotation.ColorInt;
import android.app.PendingIntent;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
-import android.content.pm.PackageManager;
import android.net.Uri;
import android.provider.Settings;
import android.provider.SettingsSlicesContract;
@@ -41,6 +41,7 @@
import com.android.settings.R;
import com.android.settings.SettingsActivity;
import com.android.settings.SubSettings;
+import com.android.settings.Utils;
import com.android.settings.core.BasePreferenceController;
import com.android.settings.core.SliderPreferenceController;
import com.android.settings.core.TogglePreferenceController;
@@ -67,9 +68,6 @@
private static final String TAG = "SliceBuilder";
- // A Slice should not be store for longer than 60,000 milliseconds / 1 minute.
- public static final long SLICE_TTL_MILLIS = 60000;
-
/**
* Build a Slice from {@link SliceData}.
*
@@ -190,7 +188,12 @@
*/
public static CharSequence getSubtitleText(Context context,
AbstractPreferenceController controller, SliceData sliceData) {
- CharSequence summaryText;
+ CharSequence summaryText = sliceData.getScreenTitle();
+ if (isValidSummary(context, summaryText) && !TextUtils.equals(summaryText,
+ sliceData.getTitle())) {
+ return summaryText;
+ }
+
if (controller != null) {
summaryText = controller.getSummary();
@@ -234,13 +237,15 @@
final PendingIntent contentIntent = getContentPendingIntent(context, sliceData);
final IconCompat icon = IconCompat.createWithResource(context, sliceData.getIconResource());
final CharSequence subtitleText = getSubtitleText(context, controller, sliceData);
+ @ColorInt final int color = Utils.getColorAccent(context);
final TogglePreferenceController toggleController =
(TogglePreferenceController) controller;
final SliceAction sliceAction = getToggleAction(context, sliceData,
toggleController.isChecked());
final List<String> keywords = buildSliceKeywords(sliceData);
- return new ListBuilder(context, sliceData.getUri(), SLICE_TTL_MILLIS)
+ return new ListBuilder(context, sliceData.getUri(), ListBuilder.INFINITY)
+ .setAccentColor(color)
.addRow(rowBuilder -> rowBuilder
.setTitle(sliceData.getTitle())
.setSubtitle(subtitleText)
@@ -256,9 +261,11 @@
final PendingIntent contentIntent = getContentPendingIntent(context, sliceData);
final IconCompat icon = IconCompat.createWithResource(context, sliceData.getIconResource());
final CharSequence subtitleText = getSubtitleText(context, controller, sliceData);
+ @ColorInt final int color = Utils.getColorAccent(context);
final List<String> keywords = buildSliceKeywords(sliceData);
- return new ListBuilder(context, sliceData.getUri(), SLICE_TTL_MILLIS)
+ return new ListBuilder(context, sliceData.getUri(), ListBuilder.INFINITY)
+ .setAccentColor(color)
.addRow(rowBuilder -> rowBuilder
.setTitle(sliceData.getTitle())
.setSubtitle(subtitleText)
@@ -274,11 +281,13 @@
final PendingIntent actionIntent = getSliderAction(context, sliceData);
final PendingIntent contentIntent = getContentPendingIntent(context, sliceData);
final IconCompat icon = IconCompat.createWithResource(context, sliceData.getIconResource());
+ @ColorInt final int color = Utils.getColorAccent(context);
final SliceAction primaryAction = new SliceAction(contentIntent, icon,
sliceData.getTitle());
final List<String> keywords = buildSliceKeywords(sliceData);
- return new ListBuilder(context, sliceData.getUri(), SLICE_TTL_MILLIS)
+ return new ListBuilder(context, sliceData.getUri(), ListBuilder.INFINITY)
+ .setAccentColor(color)
.addInputRange(builder -> builder
.setTitle(sliceData.getTitle())
.setMax(sliderController.getMaxSteps())
@@ -346,6 +355,7 @@
BasePreferenceController controller) {
final String title = data.getTitle();
final List<String> keywords = buildSliceKeywords(data);
+ @ColorInt final int color = Utils.getColorAccent(context);
final String summary;
final SliceAction primaryAction;
final IconCompat icon = IconCompat.createWithResource(context, data.getIconResource());
@@ -371,7 +381,8 @@
primaryAction = new SliceAction(getSettingsIntent(context), icon, title);
}
- return new ListBuilder(context, data.getUri(), SLICE_TTL_MILLIS)
+ return new ListBuilder(context, data.getUri(), ListBuilder.INFINITY)
+ .setAccentColor(color)
.addRow(builder -> builder
.setTitle(title)
.setSubtitle(summary)
diff --git a/src/com/android/settings/slices/SlicesFeatureProvider.java b/src/com/android/settings/slices/SlicesFeatureProvider.java
index e5bba61..8dd6547 100644
--- a/src/com/android/settings/slices/SlicesFeatureProvider.java
+++ b/src/com/android/settings/slices/SlicesFeatureProvider.java
@@ -2,6 +2,8 @@
import android.content.Context;
+import com.android.settings.wifi.calling.WifiCallingSliceHelper;
+
/**
* Manages Slices in Settings.
*/
@@ -24,4 +26,9 @@
* If the data is already indexed, the data will not change.
*/
void indexSliceData(Context context);
-}
\ No newline at end of file
+
+ /**
+ * Gets new WifiCallingSliceHelper object
+ */
+ WifiCallingSliceHelper getNewWifiCallingSliceHelper(Context context);
+}
diff --git a/src/com/android/settings/slices/SlicesFeatureProviderImpl.java b/src/com/android/settings/slices/SlicesFeatureProviderImpl.java
index 8e5bc06..16684bf 100644
--- a/src/com/android/settings/slices/SlicesFeatureProviderImpl.java
+++ b/src/com/android/settings/slices/SlicesFeatureProviderImpl.java
@@ -2,6 +2,7 @@
import android.content.Context;
+import com.android.settings.wifi.calling.WifiCallingSliceHelper;
import com.android.settingslib.utils.ThreadUtils;
/**
@@ -39,4 +40,9 @@
SlicesIndexer indexer = getSliceIndexer(context);
indexer.indexSliceData();
}
-}
\ No newline at end of file
+
+ @Override
+ public WifiCallingSliceHelper getNewWifiCallingSliceHelper(Context context) {
+ return new WifiCallingSliceHelper(context);
+ }
+}
diff --git a/src/com/android/settings/support/NewDeviceIntroSuggestionActivity.java b/src/com/android/settings/support/NewDeviceIntroSuggestionActivity.java
index f881e2f..cddbb57 100644
--- a/src/com/android/settings/support/NewDeviceIntroSuggestionActivity.java
+++ b/src/com/android/settings/support/NewDeviceIntroSuggestionActivity.java
@@ -20,9 +20,12 @@
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.net.Uri;
import android.os.Bundle;
+import android.support.annotation.NonNull;
import android.support.annotation.VisibleForTesting;
import android.text.TextUtils;
import android.text.format.DateUtils;
@@ -47,6 +50,8 @@
@VisibleForTesting
static final long PERMANENT_DISMISS_THRESHOLD = DateUtils.DAY_IN_MILLIS * 14;
+ public static final String TIPS_PACKAGE_NAME = "com.google.android.apps.tips";
+
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
@@ -62,7 +67,9 @@
}
public static boolean isSuggestionComplete(Context context) {
- return !isSupported(context)
+ // Always returns 'true' if Tips application exists. Check b/77652536 for more details.
+ return isTipsInstalledAsSystemApp(context)
+ || !isSupported(context)
|| isExpired(context)
|| hasLaunchedBefore(context)
|| !canOpenUrlInBrowser(context);
@@ -130,4 +137,18 @@
.addCategory(Intent.CATEGORY_BROWSABLE)
.setData(Uri.parse(url));
}
+
+ /**
+ * Check if the specified package exists and is marked with <i>FLAG_SYSTEM</i>
+ */
+ private static boolean isTipsInstalledAsSystemApp(@NonNull Context context) {
+ try {
+ final PackageInfo info = context.getPackageManager().getPackageInfo(TIPS_PACKAGE_NAME,
+ PackageManager.MATCH_SYSTEM_ONLY);
+ return info != null;
+ } catch (PackageManager.NameNotFoundException e) {
+ Log.w(TAG, "Cannot find the package: " + TIPS_PACKAGE_NAME, e);
+ return false;
+ }
+ }
}
diff --git a/src/com/android/settings/widget/EntityHeaderController.java b/src/com/android/settings/widget/EntityHeaderController.java
index 5131159..6d67eb4 100644
--- a/src/com/android/settings/widget/EntityHeaderController.java
+++ b/src/com/android/settings/widget/EntityHeaderController.java
@@ -18,7 +18,6 @@
import static com.android.internal.logging.nano.MetricsProto.MetricsEvent
.ACTION_OPEN_APP_NOTIFICATION_SETTING;
-import static com.android.internal.logging.nano.MetricsProto.MetricsEvent.ACTION_OPEN_APP_SETTING;
import android.annotation.IdRes;
import android.annotation.UserIdInt;
@@ -28,7 +27,6 @@
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageInfo;
-import android.content.pm.ResolveInfo;
import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
@@ -59,15 +57,13 @@
public class EntityHeaderController {
@IntDef({ActionType.ACTION_NONE,
- ActionType.ACTION_APP_PREFERENCE,
ActionType.ACTION_NOTIF_PREFERENCE,
ActionType.ACTION_DND_RULE_PREFERENCE,})
@Retention(RetentionPolicy.SOURCE)
public @interface ActionType {
int ACTION_NONE = 0;
- int ACTION_APP_PREFERENCE = 1;
- int ACTION_NOTIF_PREFERENCE = 2;
- int ACTION_DND_RULE_PREFERENCE = 3;
+ int ACTION_NOTIF_PREFERENCE = 1;
+ int ACTION_DND_RULE_PREFERENCE = 2;
}
public static final String PREF_KEY_APP_HEADER = "pref_app_header";
@@ -298,9 +294,9 @@
@Override
public void onClick(View v) {
AppInfoBase.startAppInfoFragment(
- AppInfoDashboardFragment.class, R.string.application_info_label,
- mPackageName, mUid, mFragment, 0 /* request */,
- mMetricsCategory);
+ AppInfoDashboardFragment.class, R.string.application_info_label,
+ mPackageName, mUid, mFragment, 0 /* request */,
+ mMetricsCategory);
}
});
return;
@@ -371,27 +367,6 @@
}
return;
}
- case ActionType.ACTION_APP_PREFERENCE: {
- final Intent intent = resolveIntent(
- new Intent(Intent.ACTION_APPLICATION_PREFERENCES).setPackage(mPackageName));
- if (intent == null) {
- button.setImageDrawable(null);
- button.setVisibility(View.GONE);
- return;
- }
- button.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- FeatureFactory.getFactory(mAppContext).getMetricsFeatureProvider()
- .actionWithSource(mAppContext, mMetricsCategory,
- ACTION_OPEN_APP_SETTING);
- mFragment.startActivity(intent);
- }
- });
- button.setImageResource(R.drawable.ic_settings_24dp);
- button.setVisibility(View.VISIBLE);
- return;
- }
case ActionType.ACTION_NONE: {
button.setVisibility(View.GONE);
return;
@@ -399,14 +374,6 @@
}
}
- private Intent resolveIntent(Intent i) {
- ResolveInfo result = mAppContext.getPackageManager().resolveActivity(i, 0);
- if (result != null) {
- return new Intent(i.getAction())
- .setClassName(result.activityInfo.packageName, result.activityInfo.name);
- }
- return null;
- }
private void setText(@IdRes int id, CharSequence text) {
TextView textView = mHeader.findViewById(id);
diff --git a/src/com/android/settings/wifi/calling/WifiCallingSliceHelper.java b/src/com/android/settings/wifi/calling/WifiCallingSliceHelper.java
new file mode 100644
index 0000000..7213148
--- /dev/null
+++ b/src/com/android/settings/wifi/calling/WifiCallingSliceHelper.java
@@ -0,0 +1,363 @@
+/*
+ * 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.calling;
+
+import static android.app.slice.Slice.EXTRA_TOGGLE_STATE;
+
+import android.app.PendingIntent;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.net.Uri;
+import android.os.PersistableBundle;
+import android.support.v4.graphics.drawable.IconCompat;
+import android.telephony.CarrierConfigManager;
+import android.telephony.SubscriptionManager;
+import android.telephony.TelephonyManager;
+import android.text.TextUtils;
+import android.util.Log;
+
+import androidx.slice.Slice;
+import androidx.slice.builders.ListBuilder;
+import androidx.slice.builders.SliceAction;
+
+import com.android.ims.ImsManager;
+import com.android.internal.annotations.VisibleForTesting;
+import com.android.settings.R;
+import com.android.settings.slices.SliceBroadcastReceiver;
+import com.android.settings.slices.SliceBuilderUtils;
+
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+import java.util.concurrent.FutureTask;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.TimeoutException;
+
+
+/**
+ * Helper class to control slices for wifi calling settings.
+ */
+public class WifiCallingSliceHelper {
+
+ private static final String TAG = "WifiCallingSliceHelper";
+
+ /**
+ * Settings slice path to wifi calling setting.
+ */
+ public static final String PATH_WIFI_CALLING = "wifi_calling";
+
+ /**
+ * Action passed for changes to wifi calling slice (toggle).
+ */
+ public static final String ACTION_WIFI_CALLING_CHANGED =
+ "com.android.settings.wifi.calling.action.WIFI_CALLING_CHANGED";
+
+ /**
+ * Action for Wifi calling Settings activity which
+ * allows setting configuration for Wifi calling
+ * related settings
+ */
+ public static final String ACTION_WIFI_CALLING_SETTINGS_ACTIVITY =
+ "android.settings.WIFI_CALLING_SETTINGS";
+
+ /**
+ * Timeout for querying wifi calling setting from ims manager.
+ */
+ private static final int TIMEOUT_MILLIS = 2000;
+
+ /**
+ * Time for which data contained in the slice can remain fresh.
+ */
+ private static final int SLICE_TTL_MILLIS = 60000;
+
+ protected SubscriptionManager mSubscriptionManager;
+ private final Context mContext;
+
+ @VisibleForTesting
+ public WifiCallingSliceHelper(Context context) {
+ mContext = context;
+ }
+
+ /**
+ * Returns Slice object for wifi calling settings.
+ *
+ * If wifi calling is being turned on and if wifi calling activation is needed for the current
+ * carrier, this method will return Slice with instructions to go to Settings App.
+ *
+ * If wifi calling is not supported for the current carrier, this method will return slice with
+ * not supported message.
+ *
+ * If wifi calling setting can be changed, this method will return the slice to toggle wifi
+ * calling option with ACTION_WIFI_CALLING_CHANGED as endItem.
+ */
+ public Slice createWifiCallingSlice(Uri sliceUri) {
+ final int subId = getDefaultVoiceSubId();
+ final String carrierName = getSimCarrierName();
+
+ if (subId <= SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
+ Log.d(TAG, "Invalid subscription Id");
+ return getNonActionableWifiCallingSlice(
+ mContext.getString(R.string.wifi_calling_settings_title),
+ mContext.getString(R.string.wifi_calling_not_supported, carrierName),
+ sliceUri, SliceBuilderUtils.getSettingsIntent(mContext));
+ }
+
+ final ImsManager imsManager = getImsManager(subId);
+
+ if (!imsManager.isWfcEnabledByPlatform()
+ || !imsManager.isWfcProvisionedOnDevice()) {
+ Log.d(TAG, "Wifi calling is either not provisioned or not enabled by Platform");
+ return getNonActionableWifiCallingSlice(
+ mContext.getString(R.string.wifi_calling_settings_title),
+ mContext.getString(R.string.wifi_calling_not_supported, carrierName),
+ sliceUri, SliceBuilderUtils.getSettingsIntent(mContext));
+ }
+
+ try {
+ final boolean isWifiCallingEnabled = isWifiCallingEnabled(imsManager);
+ final Intent activationAppIntent =
+ getWifiCallingCarrierActivityIntent(subId);
+
+ // Send this actionable wifi calling slice to toggle the setting
+ // only when there is no need for wifi calling activation with the server
+ if (activationAppIntent != null && !isWifiCallingEnabled) {
+ Log.d(TAG, "Needs Activation");
+ // Activation needed for the next action of the user
+ // Give instructions to go to settings app
+ return getNonActionableWifiCallingSlice(
+ mContext.getString(R.string.wifi_calling_settings_title),
+ mContext.getString(
+ R.string.wifi_calling_settings_activation_instructions),
+ sliceUri, getActivityIntent(ACTION_WIFI_CALLING_SETTINGS_ACTIVITY));
+ }
+ return getWifiCallingSlice(sliceUri, mContext, isWifiCallingEnabled);
+ } catch (InterruptedException | TimeoutException | ExecutionException e) {
+ Log.e(TAG, "Unable to read the current WiFi calling status", e);
+ return getNonActionableWifiCallingSlice(
+ mContext.getString(R.string.wifi_calling_settings_title),
+ mContext.getString(R.string.wifi_calling_turn_on),
+ sliceUri, getActivityIntent(ACTION_WIFI_CALLING_SETTINGS_ACTIVITY));
+ }
+ }
+
+ private boolean isWifiCallingEnabled(ImsManager imsManager)
+ throws InterruptedException, ExecutionException, TimeoutException {
+ final FutureTask<Boolean> isWifiOnTask = new FutureTask<>(new Callable<Boolean>() {
+ @Override
+ public Boolean call() {
+ return imsManager.isWfcEnabledByUser();
+ }
+ });
+ final ExecutorService executor = Executors.newSingleThreadExecutor();
+ executor.execute(isWifiOnTask);
+
+ Boolean isWifiEnabledByUser = false;
+ isWifiEnabledByUser = isWifiOnTask.get(TIMEOUT_MILLIS, TimeUnit.MILLISECONDS);
+
+ return isWifiEnabledByUser && imsManager.isNonTtyOrTtyOnVolteEnabled();
+ }
+
+ /**
+ * Builds a toggle slice where the intent takes you to the wifi calling page and the toggle
+ * enables/disables wifi calling.
+ */
+ private Slice getWifiCallingSlice(Uri sliceUri, Context mContext,
+ boolean isWifiCallingEnabled) {
+
+ final IconCompat icon = IconCompat.createWithResource(mContext, R.drawable.wifi_signal);
+ final String title = mContext.getString(R.string.wifi_calling_settings_title);
+ return new ListBuilder(mContext, sliceUri, SLICE_TTL_MILLIS)
+ .setColor(R.color.material_blue_500)
+ .addRow(b -> b
+ .setTitle(title)
+ .addEndItem(
+ new SliceAction(
+ getBroadcastIntent(ACTION_WIFI_CALLING_CHANGED),
+ null /* actionTitle */, isWifiCallingEnabled))
+ .setPrimaryAction(new SliceAction(
+ getActivityIntent(ACTION_WIFI_CALLING_SETTINGS_ACTIVITY),
+ icon,
+ title)))
+ .build();
+ }
+
+ protected ImsManager getImsManager(int subId) {
+ return ImsManager.getInstance(mContext, SubscriptionManager.getPhoneId(subId));
+ }
+
+ private Integer getWfcMode(ImsManager imsManager)
+ throws InterruptedException, ExecutionException, TimeoutException {
+ FutureTask<Integer> wfcModeTask = new FutureTask<>(new Callable<Integer>() {
+ @Override
+ public Integer call() {
+ return imsManager.getWfcMode(false);
+ }
+ });
+ ExecutorService executor = Executors.newSingleThreadExecutor();
+ executor.execute(wfcModeTask);
+ return wfcModeTask.get(TIMEOUT_MILLIS, TimeUnit.MILLISECONDS);
+ }
+
+ /**
+ * Handles wifi calling setting change from wifi calling slice and posts notification. Should be
+ * called when intent action is ACTION_WIFI_CALLING_CHANGED. Executed in @WorkerThread
+ *
+ * @param intent action performed
+ */
+ public void handleWifiCallingChanged(Intent intent) {
+ final int subId = getDefaultVoiceSubId();
+
+ if (subId > SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
+ final ImsManager imsManager = getImsManager(subId);
+ if (imsManager.isWfcEnabledByPlatform()
+ || imsManager.isWfcProvisionedOnDevice()) {
+ final boolean currentValue = imsManager.isWfcEnabledByUser()
+ && imsManager.isNonTtyOrTtyOnVolteEnabled();
+ final boolean newValue = intent.getBooleanExtra(EXTRA_TOGGLE_STATE,
+ currentValue);
+ final Intent activationAppIntent =
+ getWifiCallingCarrierActivityIntent(subId);
+ if (!newValue || activationAppIntent == null) {
+ // If either the action is to turn off wifi calling setting
+ // or there is no activation involved - Update the setting
+ if (newValue != currentValue) {
+ imsManager.setWfcSetting(newValue);
+ }
+ }
+ }
+ }
+ // notify change in slice in any case to get re-queried. This would result in displaying
+ // appropriate message with the updated setting.
+ final Uri uri = SliceBuilderUtils.getUri(PATH_WIFI_CALLING, false /*isPlatformSlice*/);
+ mContext.getContentResolver().notifyChange(uri, null);
+ }
+
+ /**
+ * Returns Slice with the title and subtitle provided as arguments with wifi signal Icon.
+ *
+ * @param title Title of the slice
+ * @param subtitle Subtitle of the slice
+ * @param sliceUri slice uri
+ * @return Slice with title and subtitle
+ */
+ // TODO(b/79548264) asses different scenarios and return null instead of non-actionable slice
+ private Slice getNonActionableWifiCallingSlice(String title, String subtitle, Uri sliceUri,
+ PendingIntent primaryActionIntent) {
+ final IconCompat icon = IconCompat.createWithResource(mContext, R.drawable.wifi_signal);
+ return new ListBuilder(mContext, sliceUri, SLICE_TTL_MILLIS)
+ .setColor(R.color.material_blue_500)
+ .addRow(b -> b
+ .setTitle(title)
+ .setSubtitle(subtitle)
+ .setPrimaryAction(new SliceAction(
+ primaryActionIntent, icon,
+ title)))
+ .build();
+ }
+
+ /**
+ * Returns {@code true} when the key is enabled for the carrier, and {@code false} otherwise.
+ */
+ private boolean isCarrierConfigManagerKeyEnabled(Context mContext, String key,
+ int subId, boolean defaultValue) {
+ final CarrierConfigManager configManager = getCarrierConfigManager(mContext);
+ boolean ret = false;
+ if (configManager != null) {
+ final PersistableBundle bundle = configManager.getConfigForSubId(subId);
+ if (bundle != null) {
+ ret = bundle.getBoolean(key, defaultValue);
+ }
+ }
+ return ret;
+ }
+
+ protected CarrierConfigManager getCarrierConfigManager(Context mContext) {
+ return mContext.getSystemService(CarrierConfigManager.class);
+ }
+
+ /**
+ * Returns the current default voice subId obtained from SubscriptionManager
+ */
+ protected int getDefaultVoiceSubId() {
+ if (mSubscriptionManager == null) {
+ mSubscriptionManager = mContext.getSystemService(SubscriptionManager.class);
+ }
+ return SubscriptionManager.getDefaultVoiceSubscriptionId();
+ }
+
+ /**
+ * Returns Intent of the activation app required to activate wifi calling or null if there is no
+ * need for activation.
+ */
+ protected Intent getWifiCallingCarrierActivityIntent(int subId) {
+ final CarrierConfigManager configManager = getCarrierConfigManager(mContext);
+ if (configManager == null) {
+ return null;
+ }
+
+ final PersistableBundle bundle = configManager.getConfigForSubId(subId);
+ if (bundle == null) {
+ return null;
+ }
+
+ final String carrierApp = bundle.getString(
+ CarrierConfigManager.KEY_WFC_EMERGENCY_ADDRESS_CARRIER_APP_STRING);
+ if (TextUtils.isEmpty(carrierApp)) {
+ return null;
+ }
+
+ final ComponentName componentName = ComponentName.unflattenFromString(carrierApp);
+ if (componentName == null) {
+ return null;
+ }
+
+ final Intent intent = new Intent();
+ intent.setComponent(componentName);
+ return intent;
+ }
+
+ private PendingIntent getBroadcastIntent(String action) {
+ final Intent intent = new Intent(action);
+ intent.setClass(mContext, SliceBroadcastReceiver.class);
+ return PendingIntent.getBroadcast(mContext, 0 /* requestCode */, intent,
+ PendingIntent.FLAG_CANCEL_CURRENT);
+ }
+
+ /**
+ * Returns PendingIntent to start activity specified by action
+ */
+ private PendingIntent getActivityIntent(String action) {
+ final Intent intent = new Intent(action);
+ intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ return PendingIntent.getActivity(mContext, 0 /* requestCode */, intent, 0 /* flags */);
+ }
+
+ /**
+ * Returns carrier id name of the current Subscription
+ */
+ private String getSimCarrierName() {
+ final TelephonyManager telephonyManager = mContext.getSystemService(TelephonyManager.class);
+ final CharSequence carrierName = telephonyManager.getSimCarrierIdName();
+ if (carrierName == null) {
+ return mContext.getString(R.string.carrier);
+ }
+ return carrierName.toString();
+ }
+
+}
diff --git a/tests/robotests/src/com/android/settings/applications/appinfo/AppSettingPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/applications/appinfo/AppSettingPreferenceControllerTest.java
new file mode 100644
index 0000000..66b58c8
--- /dev/null
+++ b/tests/robotests/src/com/android/settings/applications/appinfo/AppSettingPreferenceControllerTest.java
@@ -0,0 +1,118 @@
+/*
+ * 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.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.Mockito.doNothing;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+import static org.robolectric.Shadows.shadowOf;
+
+import android.app.Application;
+import android.content.Intent;
+import android.content.pm.ActivityInfo;
+import android.content.pm.ResolveInfo;
+import android.support.v7.preference.Preference;
+
+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 org.robolectric.shadows.ShadowPackageManager;
+
+@RunWith(SettingsRobolectricTestRunner.class)
+public class AppSettingPreferenceControllerTest {
+
+ private static final String TEST_PKG_NAME = "test_pkg";
+ private static final String TEST_CLASS_NAME = "name";
+ private static final Intent TEST_INTENT =
+ new Intent(Intent.ACTION_APPLICATION_PREFERENCES)
+ .setClassName(TEST_PKG_NAME, TEST_CLASS_NAME);
+ private static final Intent RESOLVED_INTENT =
+ new Intent(Intent.ACTION_APPLICATION_PREFERENCES)
+ .setPackage(TEST_PKG_NAME);
+
+ @Mock
+ private AppInfoDashboardFragment mParent;
+ private Application mApplication;
+ private ShadowPackageManager mPackageManager;
+ private AppSettingPreferenceController mController;
+ private Preference mPreference;
+
+ @Before
+ public void setUp() {
+ MockitoAnnotations.initMocks(this);
+ mApplication = RuntimeEnvironment.application;
+ mPackageManager = shadowOf(mApplication.getPackageManager());
+ mController = new AppSettingPreferenceController(mApplication, "test_key");
+ mController.setPackageName(TEST_PKG_NAME).setParentFragment(mParent);
+ mPreference = new Preference(mApplication);
+ mPreference.setKey(mController.getPreferenceKey());
+ }
+
+ @Test
+ public void getAvailabilityStatus_noAppSetting_shouldNotBeAvailable() {
+ assertThat(mController.isAvailable())
+ .isFalse();
+ }
+
+ @Test
+ public void getAvailabilityStatus_noPackageName_shouldNotBeAvailable() {
+ mController.setPackageName(null);
+
+ assertThat(mController.isAvailable())
+ .isFalse();
+ }
+
+ @Test
+ public void getAvailabilityStatus_hasAppSetting_shouldBeAvailable() {
+ final ResolveInfo info = new ResolveInfo();
+ info.activityInfo = new ActivityInfo();
+ info.activityInfo.packageName = TEST_PKG_NAME;
+ info.activityInfo.name = TEST_CLASS_NAME;
+
+ mPackageManager.addResolveInfoForIntent(RESOLVED_INTENT, info);
+
+ assertThat(mController.isAvailable())
+ .isTrue();
+ }
+
+ @Test
+ public void clickPreference_noAppSetting_shouldDoNothing() {
+ assertThat(mController.handlePreferenceTreeClick(mPreference)).isFalse();
+ }
+
+ @Test
+ public void clickPreference_hasAppSetting_shouldLaunchIntent() {
+ final ResolveInfo info = new ResolveInfo();
+ info.activityInfo = new ActivityInfo();
+ info.activityInfo.packageName = TEST_PKG_NAME;
+ info.activityInfo.name = TEST_CLASS_NAME;
+
+ mPackageManager.addResolveInfoForIntent(RESOLVED_INTENT, info);
+
+ assertThat(mController.handlePreferenceTreeClick(mPreference)).isTrue();
+ assertThat(shadowOf(mApplication).getNextStartedActivity().getComponent())
+ .isEqualTo(TEST_INTENT.getComponent());
+ }
+}
diff --git a/tests/robotests/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdaterTest.java b/tests/robotests/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdaterTest.java
index ed95015..ced8fc4 100644
--- a/tests/robotests/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdaterTest.java
+++ b/tests/robotests/src/com/android/settings/bluetooth/AvailableMediaBluetoothDeviceUpdaterTest.java
@@ -73,6 +73,7 @@
private AvailableMediaBluetoothDeviceUpdater mBluetoothDeviceUpdater;
private Collection<CachedBluetoothDevice> cachedDevices;
private ShadowAudioManager mShadowAudioManager;
+ private BluetoothDevicePreference mPreference;
@Before
public void setUp() {
@@ -93,6 +94,7 @@
mBluetoothDeviceUpdater = spy(new AvailableMediaBluetoothDeviceUpdater(mDashboardFragment,
mDevicePreferenceCallback, mLocalManager));
mBluetoothDeviceUpdater.setPrefContext(mContext);
+ mPreference = new BluetoothDevicePreference(mContext, mCachedBluetoothDevice, false);
doNothing().when(mBluetoothDeviceUpdater).addPreference(any());
doNothing().when(mBluetoothDeviceUpdater).removePreference(any());
}
@@ -208,5 +210,12 @@
verify(mBluetoothDeviceUpdater).removePreference(mCachedBluetoothDevice);
}
+
+ @Test
+ public void onClick_Preference_setActive() {
+ mBluetoothDeviceUpdater.onPreferenceClick(mPreference);
+
+ verify(mCachedBluetoothDevice).setActive();
+ }
}
diff --git a/tests/robotests/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdaterTest.java b/tests/robotests/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdaterTest.java
index fae014f..547727b 100644
--- a/tests/robotests/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdaterTest.java
+++ b/tests/robotests/src/com/android/settings/bluetooth/SavedBluetoothDeviceUpdaterTest.java
@@ -57,7 +57,8 @@
private LocalBluetoothProfileManager mLocalBluetoothProfileManager;
private Context mContext;
- private BluetoothDeviceUpdater mBluetoothDeviceUpdater;
+ private SavedBluetoothDeviceUpdater mBluetoothDeviceUpdater;
+ private BluetoothDevicePreference mPreference;
@Before
public void setUp() {
@@ -71,6 +72,7 @@
mBluetoothDeviceUpdater = spy(new SavedBluetoothDeviceUpdater(mDashboardFragment,
mDevicePreferenceCallback, mLocalManager));
mBluetoothDeviceUpdater.setPrefContext(mContext);
+ mPreference = new BluetoothDevicePreference(mContext, mCachedBluetoothDevice, false);
doNothing().when(mBluetoothDeviceUpdater).addPreference(any());
doNothing().when(mBluetoothDeviceUpdater).removePreference(any());
}
@@ -110,4 +112,11 @@
verify(mBluetoothDeviceUpdater).addPreference(mCachedBluetoothDevice);
}
+
+ @Test
+ public void onClick_Preference_setConnect() {
+ mBluetoothDeviceUpdater.onPreferenceClick(mPreference);
+
+ verify(mCachedBluetoothDevice).connect(true);
+ }
}
diff --git a/tests/robotests/src/com/android/settings/development/BluetoothDelayReportsPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/development/BluetoothDelayReportsPreferenceControllerTest.java
deleted file mode 100644
index bdaad0a..0000000
--- a/tests/robotests/src/com/android/settings/development/BluetoothDelayReportsPreferenceControllerTest.java
+++ /dev/null
@@ -1,110 +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.development;
-
-import static com.android.settings.development.BluetoothDelayReportsPreferenceController
- .BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY;
-
-import static com.google.common.truth.Truth.assertThat;
-import static org.mockito.Mockito.spy;
-import static org.mockito.Mockito.when;
-
-import android.content.Context;
-import android.os.SystemProperties;
-import android.support.v14.preference.SwitchPreference;
-import android.support.v7.preference.PreferenceScreen;
-
-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;
-
-@RunWith(SettingsRobolectricTestRunner.class)
-public class BluetoothDelayReportsPreferenceControllerTest {
-
- @Mock
- private PreferenceScreen mPreferenceScreen;
-
- private Context mContext;
- private SwitchPreference mPreference;
- private BluetoothDelayReportsPreferenceController mController;
-
- @Before
- public void setup() {
- MockitoAnnotations.initMocks(this);
- mContext = RuntimeEnvironment.application;
- mPreference = new SwitchPreference(mContext);
- mController = spy(new BluetoothDelayReportsPreferenceController(mContext));
- when(mPreferenceScreen.findPreference(mController.getPreferenceKey()))
- .thenReturn(mPreference);
- mController.displayPreference(mPreferenceScreen);
- }
-
- @Test
- public void onPreferenceChanged_settingDisabled_turnOnDelayReports() {
- mController.onPreferenceChange(mPreference, true /* new value */);
-
- final boolean mode = SystemProperties.getBoolean(
- BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY, false /* default */);
-
- assertThat(mode).isTrue();
- }
-
- @Test
- public void onPreferenceChanged_settingDisabled_turnOffDelayReports() {
- mController.onPreferenceChange(mPreference, false /* new value */);
-
- final boolean mode = SystemProperties.getBoolean(
- BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY, false /* default */);
-
- assertThat(mode).isFalse();
- }
-
- @Test
- public void updateState_settingDisabled_preferenceShouldBeChecked() {
- SystemProperties.set(BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY,
- Boolean.toString(true));
- mController.updateState(mPreference);
-
- assertThat(mPreference.isChecked()).isTrue();
- }
-
- @Test
- public void updateState_settingDisabled_preferenceShouldNotBeChecked() {
- SystemProperties.set(BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY,
- Boolean.toString(false));
- mController.updateState(mPreference);
-
- assertThat(mPreference.isChecked()).isFalse();
- }
-
- @Test
- public void onDeveloperOptionsDisabled_shouldDisablePreference() {
- mController.onDeveloperOptionsDisabled();
-
- final boolean mode = SystemProperties.getBoolean(
- BLUETOOTH_DISABLE_AVDTP_DELAY_REPORTS_PROPERTY, false /* default */);
-
- assertThat(mode).isFalse();
- assertThat(mPreference.isEnabled()).isFalse();
- assertThat(mPreference.isChecked()).isFalse();
- }
-}
diff --git a/tests/robotests/src/com/android/settings/development/BluetoothInbandRingingPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/development/BluetoothInbandRingingPreferenceControllerTest.java
deleted file mode 100644
index f91bd44..0000000
--- a/tests/robotests/src/com/android/settings/development/BluetoothInbandRingingPreferenceControllerTest.java
+++ /dev/null
@@ -1,120 +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.development;
-
-import static com.android.settings.development.BluetoothInbandRingingPreferenceController.BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY;
-import static com.google.common.truth.Truth.assertThat;
-import static org.mockito.Mockito.doReturn;
-import static org.mockito.Mockito.spy;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-import android.content.Context;
-import android.os.SystemProperties;
-import android.support.v14.preference.SwitchPreference;
-import android.support.v7.preference.PreferenceScreen;
-
-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;
-
-@RunWith(SettingsRobolectricTestRunner.class)
-public class BluetoothInbandRingingPreferenceControllerTest {
-
- @Mock
- private SwitchPreference mPreference;
- @Mock
- private PreferenceScreen mPreferenceScreen;
-
- private Context mContext;
- private BluetoothInbandRingingPreferenceController mController;
-
- @Before
- public void setup() {
- MockitoAnnotations.initMocks(this);
- mContext = RuntimeEnvironment.application;
- mController = spy(new BluetoothInbandRingingPreferenceController(mContext));
- doReturn(true).when(mController).isInbandRingingSupported();
- when(mPreferenceScreen.findPreference(mController.getPreferenceKey())).thenReturn(
- mPreference);
- mController.displayPreference(mPreferenceScreen);
- }
-
- @Test
- public void isAvailable_inbandRingingNotSupported_shouldReturnFalse() {
- doReturn(false).when(mController).isInbandRingingSupported();
- assertThat(mController.isAvailable()).isFalse();
- }
-
- @Test
- public void isAvailable_inbandRingingSupported_shouldReturnTrue() {
- assertThat(mController.isAvailable()).isTrue();
- }
-
- @Test
- public void onPreferenceChanged_settingEnabled_turnOnBluetoothSnoopLog() {
- mController.onPreferenceChange(mPreference, true /* new value */);
-
- final boolean mode = SystemProperties
- .getBoolean(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, false /* default */);
-
- assertThat(mode).isTrue();
- }
-
- @Test
- public void onPreferenceChanged_settingDisabled_turnOffBluetoothSnoopLog() {
- mController.onPreferenceChange(mPreference, false /* new value */);
-
- final boolean mode = SystemProperties
- .getBoolean(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, false /* default */);
-
- assertThat(mode).isFalse();
- }
-
- @Test
- public void updateState_settingEnabled_preferenceShouldBeChecked() {
- SystemProperties.set(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, Boolean.toString(true));
- mController.updateState(mPreference);
-
- verify(mPreference).setChecked(true);
- }
-
- @Test
- public void updateState_settingDisabled_preferenceShouldNotBeChecked() {
- SystemProperties.set(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, Boolean.toString(false));
- mController.updateState(mPreference);
-
- verify(mPreference).setChecked(false);
- }
-
- @Test
- public void onDeveloperOptionsDisabled_shouldDisablePreference() {
- mController.onDeveloperOptionsDisabled();
-
- final boolean mode = SystemProperties
- .getBoolean(BLUETOOTH_DISABLE_INBAND_RINGING_PROPERTY, false /* default */);
-
- assertThat(mode).isFalse();
- verify(mPreference).setEnabled(false);
- verify(mPreference).setChecked(false);
- }
-}
diff --git a/tests/robotests/src/com/android/settings/development/DevelopmentSettingsDashboardFragmentTest.java b/tests/robotests/src/com/android/settings/development/DevelopmentSettingsDashboardFragmentTest.java
index 9272b46..da32ce8 100644
--- a/tests/robotests/src/com/android/settings/development/DevelopmentSettingsDashboardFragmentTest.java
+++ b/tests/robotests/src/com/android/settings/development/DevelopmentSettingsDashboardFragmentTest.java
@@ -131,7 +131,6 @@
@Config(shadows = {
ShadowPictureColorModePreferenceController.class,
ShadowAdbPreferenceController.class,
- ShadowBluetoothInbandRingingPreferenceController.class,
ShadowClearAdbKeysPreferenceController.class
})
public void searchIndex_pageEnabled_shouldNotAddKeysToNonIndexable() {
@@ -282,15 +281,6 @@
}
}
- @Implements(BluetoothInbandRingingPreferenceController.class)
- public static class ShadowBluetoothInbandRingingPreferenceController {
-
- @Implementation
- public boolean isAvailable() {
- return true;
- }
- }
-
@Implements(ClearAdbKeysPreferenceController.class)
public static class ShadowClearAdbKeysPreferenceController {
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/BatteryBroadcastReceiverTest.java b/tests/robotests/src/com/android/settings/fuelgauge/BatteryBroadcastReceiverTest.java
index 3fdbe83..4583dd1 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/BatteryBroadcastReceiverTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/BatteryBroadcastReceiverTest.java
@@ -15,8 +15,11 @@
*/
package com.android.settings.fuelgauge;
+import static com.android.settings.fuelgauge.BatteryBroadcastReceiver.BatteryUpdateType;
+
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.any;
+import static org.mockito.Matchers.anyInt;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.spy;
@@ -70,14 +73,14 @@
}
@Test
- public void testOnReceive_batteryDataChanged_dataUpdated() {
+ public void testOnReceive_batteryLevelChanged_dataUpdated() {
mBatteryBroadcastReceiver.onReceive(mContext, mChargingIntent);
assertThat(mBatteryBroadcastReceiver.mBatteryLevel)
.isEqualTo(Utils.getBatteryPercentage(mChargingIntent));
assertThat(mBatteryBroadcastReceiver.mBatteryStatus)
.isEqualTo(Utils.getBatteryStatus(mContext.getResources(), mChargingIntent));
- verify(mBatteryListener).onBatteryChanged();
+ verify(mBatteryListener).onBatteryChanged(BatteryUpdateType.BATTERY_LEVEL);
}
@Test
@@ -85,7 +88,7 @@
mBatteryBroadcastReceiver.onReceive(mContext,
new Intent(PowerManager.ACTION_POWER_SAVE_MODE_CHANGED));
- verify(mBatteryListener).onBatteryChanged();
+ verify(mBatteryListener).onBatteryChanged(BatteryUpdateType.BATTERY_SAVER);
}
@Test
@@ -100,7 +103,7 @@
assertThat(mBatteryBroadcastReceiver.mBatteryLevel).isEqualTo(batteryLevel);
assertThat(mBatteryBroadcastReceiver.mBatteryStatus).isEqualTo(batteryStatus);
- verify(mBatteryListener, never()).onBatteryChanged();
+ verify(mBatteryListener, never()).onBatteryChanged(anyInt());
}
@Test
@@ -115,6 +118,6 @@
assertThat(mBatteryBroadcastReceiver.mBatteryStatus)
.isEqualTo(Utils.getBatteryStatus(mContext.getResources(), mChargingIntent));
// 2 times because register will force update the battery
- verify(mBatteryListener, times(2)).onBatteryChanged();
+ verify(mBatteryListener, times(2)).onBatteryChanged(BatteryUpdateType.MANUAL);
}
}
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageAdvancedTest.java b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageAdvancedTest.java
index 4a905b4..9b61e5f 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageAdvancedTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageAdvancedTest.java
@@ -18,6 +18,7 @@
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.ArgumentMatchers.nullable;
+import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.doReturn;
@@ -86,7 +87,7 @@
@Test
public void testOptionsMenu_menuAppToggle_metricEventInvoked() {
mFragment.mShowAllApps = false;
- doNothing().when(mFragment).restartBatteryStatsLoader();
+ doNothing().when(mFragment).restartBatteryStatsLoader(anyInt());
mFragment.onOptionsItemSelected(mToggleAppsMenu);
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageBaseTest.java b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageBaseTest.java
index d9f572d..eb683c0 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageBaseTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageBaseTest.java
@@ -74,7 +74,7 @@
}
@Override
- protected void refreshUi() {
+ protected void refreshUi(int refreshType) {
// Do nothing
}
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageSummaryTest.java b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageSummaryTest.java
index b48f00e..07341a1 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageSummaryTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/PowerUsageSummaryTest.java
@@ -149,7 +149,7 @@
mFragment.initFeatureProvider();
mBatteryMeterView = new BatteryMeterView(mRealContext);
mBatteryMeterView.mDrawable = new BatteryMeterView.BatteryMeterDrawable(mRealContext, 0);
- doNothing().when(mFragment).restartBatteryStatsLoader();
+ doNothing().when(mFragment).restartBatteryStatsLoader(anyInt());
doReturn(mock(LoaderManager.class)).when(mFragment).getLoaderManager();
doReturn(MENU_ADVANCED_BATTERY).when(mAdvancedPageMenu).getItemId();
@@ -317,15 +317,6 @@
}
@Test
- public void restartBatteryStatsLoader_notClearHeader_quickUpdateNotInvoked() {
- mFragment.mBatteryHeaderPreferenceController = mBatteryHeaderPreferenceController;
-
- mFragment.restartBatteryStatsLoader(false /* clearHeader */);
-
- verify(mBatteryHeaderPreferenceController, never()).quickUpdateHeaderPreference();
- }
-
- @Test
public void optionsMenu_advancedPageEnabled() {
when(mFeatureFactory.powerUsageFeatureProvider.isPowerAccountingToggleEnabled())
.thenReturn(true);
@@ -360,7 +351,18 @@
when(mFragment.mBatteryTipPreferenceController.needUpdate()).thenReturn(false);
mFragment.updateBatteryTipFlag(new Bundle());
- mFragment.refreshUi();
+ mFragment.refreshUi(BatteryBroadcastReceiver.BatteryUpdateType.MANUAL);
+
+ verify(mFragment, never()).restartBatteryTipLoader();
+ }
+
+ @Test
+ public void refreshUi_batteryLevelChanged_doNotUpdateBatteryTip() {
+ mFragment.mBatteryTipPreferenceController = mock(BatteryTipPreferenceController.class);
+ when(mFragment.mBatteryTipPreferenceController.needUpdate()).thenReturn(true);
+ mFragment.updateBatteryTipFlag(new Bundle());
+
+ mFragment.refreshUi(BatteryBroadcastReceiver.BatteryUpdateType.BATTERY_LEVEL);
verify(mFragment, never()).restartBatteryTipLoader();
}
@@ -371,7 +373,7 @@
when(mFragment.mBatteryTipPreferenceController.needUpdate()).thenReturn(true);
mFragment.updateBatteryTipFlag(new Bundle());
- mFragment.refreshUi();
+ mFragment.refreshUi(BatteryBroadcastReceiver.BatteryUpdateType.MANUAL);
verify(mFragment).restartBatteryTipLoader();
}
diff --git a/tests/robotests/src/com/android/settings/gestures/SwipeUpPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/gestures/SwipeUpPreferenceControllerTest.java
index 4107b73..3585650 100644
--- a/tests/robotests/src/com/android/settings/gestures/SwipeUpPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/gestures/SwipeUpPreferenceControllerTest.java
@@ -27,7 +27,7 @@
import android.os.UserManager;
import android.provider.Settings;
-import com.android.settings.R;
+import com.android.internal.R;
import com.android.settings.testutils.SettingsRobolectricTestRunner;
import com.android.settings.testutils.shadow.SettingsShadowResources;
@@ -57,8 +57,7 @@
public void setUp() {
SettingsShadowResources.overrideResource(R.bool.config_swipe_up_gesture_setting_available,
true);
- SettingsShadowResources.overrideResource(
- com.android.internal.R.bool.config_swipe_up_gesture_default, true);
+ SettingsShadowResources.overrideResource(R.bool.config_swipe_up_gesture_default, true);
mContext = RuntimeEnvironment.application;
mPackageManager = Shadows.shadowOf(mContext.getPackageManager());
@@ -107,8 +106,7 @@
@Test
public void testIsChecked_defaultIsFalse_shouldReturnFalse() {
- SettingsShadowResources.overrideResource(
- com.android.internal.R.bool.config_swipe_up_gesture_default, false);
+ SettingsShadowResources.overrideResource(R.bool.config_swipe_up_gesture_default, false);
assertThat(mController.isChecked()).isFalse();
}
diff --git a/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java b/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java
index e9ffa8a..dfea6fb 100644
--- a/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java
+++ b/tests/robotests/src/com/android/settings/network/PrivateDnsModeDialogPreferenceTest.java
@@ -28,7 +28,10 @@
import android.app.AlertDialog;
import android.app.Fragment;
+import android.content.ContentResolver;
import android.content.Context;
+import android.content.DialogInterface;
+import android.net.ConnectivityManager;
import android.provider.Settings;
import android.view.LayoutInflater;
import android.view.View;
@@ -150,4 +153,36 @@
assertThat(mSaveButton.isEnabled()).named("provider: " + invalid).isFalse();
}
}
+
+ @Test
+ public void testOnClick_positiveButtonClicked_saveData() {
+ // Set the default settings to OFF
+ final ContentResolver contentResolver = mContext.getContentResolver();
+ Settings.Global.putString(contentResolver, Settings.Global.PRIVATE_DNS_MODE,
+ ConnectivityManager.PRIVATE_DNS_MODE_OFF);
+
+ mPreference.mMode = ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC;
+ mPreference.onClick(null, DialogInterface.BUTTON_POSITIVE);
+
+ // Change to OPPORTUNISTIC
+ assertThat(Settings.Global.getString(contentResolver,
+ Settings.Global.PRIVATE_DNS_MODE)).isEqualTo(
+ ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC);
+ }
+
+ @Test
+ public void testOnClick_negativeButtonClicked_doNothing() {
+ // Set the default settings to OFF
+ final ContentResolver contentResolver = mContext.getContentResolver();
+ Settings.Global.putString(contentResolver, Settings.Global.PRIVATE_DNS_MODE,
+ ConnectivityManager.PRIVATE_DNS_MODE_OFF);
+
+ mPreference.mMode = ConnectivityManager.PRIVATE_DNS_MODE_OPPORTUNISTIC;
+ mPreference.onClick(null, DialogInterface.BUTTON_NEGATIVE);
+
+ // Still equal to OFF
+ assertThat(Settings.Global.getString(contentResolver,
+ Settings.Global.PRIVATE_DNS_MODE)).isEqualTo(
+ ConnectivityManager.PRIVATE_DNS_MODE_OFF);
+ }
}
diff --git a/tests/robotests/src/com/android/settings/network/TetherPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/network/TetherPreferenceControllerTest.java
index 6166d29..ac573b4 100644
--- a/tests/robotests/src/com/android/settings/network/TetherPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/network/TetherPreferenceControllerTest.java
@@ -75,10 +75,21 @@
@Test
public void lifeCycle_onCreate_shouldInitBluetoothPan() {
+ when(mBluetoothAdapter.getState()).thenReturn(BluetoothAdapter.STATE_ON);
mController.onCreate(null);
- verify(mBluetoothAdapter)
- .getProfileProxy(mContext, mController.mBtProfileServiceListener, BluetoothProfile.PAN);
+ verify(mBluetoothAdapter).getState();
+ verify(mBluetoothAdapter).getProfileProxy(mContext, mController.mBtProfileServiceListener,
+ BluetoothProfile.PAN);
+ }
+
+ @Test
+ public void lifeCycle_onCreate_shouldNotInitBluetoothPanWhenBluetoothOff() {
+ when(mBluetoothAdapter.getState()).thenReturn(BluetoothAdapter.STATE_OFF);
+ mController.onCreate(null);
+
+ verify(mBluetoothAdapter).getState();
+ verifyNoMoreInteractions(mBluetoothAdapter);
}
@Test
diff --git a/tests/robotests/src/com/android/settings/notification/VibrateWhenRingPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/VibrateWhenRingPreferenceControllerTest.java
index 9314109..4e69c46 100644
--- a/tests/robotests/src/com/android/settings/notification/VibrateWhenRingPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/VibrateWhenRingPreferenceControllerTest.java
@@ -17,11 +17,17 @@
package com.android.settings.notification;
import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;
+
+import static com.android.settings.core.BasePreferenceController.AVAILABLE;
+import static com.android.settings.core.BasePreferenceController.UNSUPPORTED_ON_DEVICE;
+
import static com.google.common.truth.Truth.assertThat;
+
import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;
+import android.content.ContentResolver;
import android.content.Context;
import android.provider.Settings;
import android.support.v7.preference.Preference;
@@ -37,26 +43,32 @@
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.robolectric.RuntimeEnvironment;
+import org.robolectric.shadow.api.Shadow;
+import org.robolectric.shadows.ShadowContentResolver;
@RunWith(SettingsRobolectricTestRunner.class)
public class VibrateWhenRingPreferenceControllerTest {
- @Mock
+ private static final String KEY_VIBRATE_WHEN_RINGING = "vibrate_when_ringing";
+ private final int DEFAULT_VALUE = 0;
+ private final int NOTIFICATION_VIBRATE_WHEN_RINGING = 1;
private Context mContext;
+ private ContentResolver mContentResolver;
@Mock
private PreferenceScreen mScreen;
@Mock
private TelephonyManager mTelephonyManager;
-
private VibrateWhenRingPreferenceController mController;
private Preference mPreference;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
+ mContext = spy(RuntimeEnvironment.application);
+ mContentResolver = mContext.getContentResolver();
when(mContext.getSystemService(Context.TELEPHONY_SERVICE)).thenReturn(mTelephonyManager);
- mController = new VibrateWhenRingPreferenceController(mContext);
- mPreference = new Preference(RuntimeEnvironment.application);
+ mController = new VibrateWhenRingPreferenceController(mContext, KEY_VIBRATE_WHEN_RINGING);
+ mPreference = new Preference(mContext);
mPreference.setKey(mController.getPreferenceKey());
when(mScreen.findPreference(mPreference.getKey())).thenReturn(mPreference);
}
@@ -80,26 +92,95 @@
}
@Test
+ public void testOnPreferenceChange_turnOn_returnOn() {
+ mController.onPreferenceChange(null, true);
+ final int mode = Settings.System.getInt(mContext.getContentResolver(),
+ VIBRATE_WHEN_RINGING, DEFAULT_VALUE);
+
+ assertThat(mode).isEqualTo(NOTIFICATION_VIBRATE_WHEN_RINGING);
+ }
+
+ @Test
+ public void testOnPreferenceChange_turnOff_returnOff() {
+ mController.onPreferenceChange(null, false);
+ final int mode = Settings.System.getInt(mContext.getContentResolver(),
+ VIBRATE_WHEN_RINGING, DEFAULT_VALUE);
+
+ assertThat(mode).isEqualTo(DEFAULT_VALUE);
+ }
+
+ @Test
+ public void voiceCapable_availabled() {
+ when(mTelephonyManager.isVoiceCapable()).thenReturn(true);
+
+ assertThat(mController.getAvailabilityStatus()).isEqualTo(AVAILABLE);
+ }
+
+ @Test
+ public void voiceCapable_notAvailabled() {
+ when(mTelephonyManager.isVoiceCapable()).thenReturn(false);
+
+ assertThat(mController.getAvailabilityStatus()).isEqualTo(UNSUPPORTED_ON_DEVICE);
+ }
+
+ @Test
public void updateState_settingIsOn_preferenceShouldBeChecked() {
final TwoStatePreference preference = mock(TwoStatePreference.class);
- final Context context = RuntimeEnvironment.application;
- Settings.System.putInt(context.getContentResolver(), VIBRATE_WHEN_RINGING, 1);
+ Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 1);
- mController = new VibrateWhenRingPreferenceController(context);
mController.updateState(preference);
- verify(preference).setChecked(true);
+ assertThat(mController.isChecked()).isTrue();
}
@Test
public void updateState_settingIsOff_preferenceShouldNotBeChecked() {
final TwoStatePreference preference = mock(TwoStatePreference.class);
- final Context context = RuntimeEnvironment.application;
- Settings.System.putInt(context.getContentResolver(), VIBRATE_WHEN_RINGING, 0);
+ Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 0);
- mController = new VibrateWhenRingPreferenceController(context);
mController.updateState(preference);
- verify(preference).setChecked(false);
+ assertThat(mController.isChecked()).isFalse();
+ }
+
+ @Test
+ public void setChecked_settingsIsOn() {
+ mController.setChecked(true);
+ final int mode = Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
+ -1);
+
+ assertThat(mode).isEqualTo(NOTIFICATION_VIBRATE_WHEN_RINGING);
+ }
+
+ @Test
+ public void setChecked_settingsIsOff() {
+ mController.setChecked(false);
+ final int mode = Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
+ -1);
+
+ assertThat(mode).isEqualTo(DEFAULT_VALUE);
+ }
+
+ @Test
+ public void testObserver_onResume_shouldRegisterObserver() {
+ final ShadowContentResolver shadowContentResolver = Shadow.extract(mContentResolver);
+ mController.displayPreference(mScreen);
+
+ mController.onResume();
+
+ assertThat(shadowContentResolver.getContentObservers(
+ Settings.System.getUriFor(VIBRATE_WHEN_RINGING))).isNotEmpty();
+ }
+
+ @Test
+ public void testObserver_onPause_shouldUnregisterObserver() {
+ final ShadowContentResolver shadowContentResolver = Shadow.extract(mContentResolver);
+ mController.displayPreference(mScreen);
+
+ mController.onResume();
+ mController.onPause();
+
+ assertThat(shadowContentResolver.getContentObservers(
+ Settings.System.getUriFor(VIBRATE_WHEN_RINGING))).isEmpty();
}
}
diff --git a/tests/robotests/src/com/android/settings/notification/ZenModeSettingsTest.java b/tests/robotests/src/com/android/settings/notification/ZenModeSettingsTest.java
index 5b2782f..39e9271 100644
--- a/tests/robotests/src/com/android/settings/notification/ZenModeSettingsTest.java
+++ b/tests/robotests/src/com/android/settings/notification/ZenModeSettingsTest.java
@@ -134,13 +134,13 @@
public void testGetCallsSettingSummary_contacts() {
Policy policy = new Policy(Policy.PRIORITY_CATEGORY_ALARMS | Policy.PRIORITY_CATEGORY_CALLS,
Policy.PRIORITY_SENDERS_CONTACTS, 0, 0);
- assertThat(mBuilder.getCallsSettingSummary(policy)).isEqualTo("From contacts only");
+ assertThat(mBuilder.getCallsSettingSummary(policy)).isEqualTo("From contacts");
}
@Test
public void testGetCallsSettingSummary_repeatCallers() {
Policy policy = new Policy(Policy.PRIORITY_CATEGORY_REPEAT_CALLERS, 0, 0, 0);
- assertThat(mBuilder.getCallsSettingSummary(policy)).isEqualTo("From repeat callers only");
+ assertThat(mBuilder.getCallsSettingSummary(policy)).isEqualTo("From repeat callers");
}
@Test
diff --git a/tests/robotests/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceControllerTest.java
index 14de98c..b1692bc 100644
--- a/tests/robotests/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/ZenModeVisEffectsCustomPreferenceControllerTest.java
@@ -88,23 +88,14 @@
}
@Test
- public void isAvailable_menuOff_noVisEffects() {
+ public void isAvailable_noVisEffects() {
mBackend.mPolicy = new NotificationManager.Policy(0, 0, 0, 0);
- mController.mShowMenuSelected = false;
- assertThat(mController.isAvailable()).isFalse();
- }
-
- @Test
- public void isAvailable_menuOn_noVisEffects() {
- mBackend.mPolicy = new NotificationManager.Policy(0, 0, 0, 0);
- mController.mShowMenuSelected = true;
assertThat(mController.isAvailable()).isTrue();
}
@Test
- public void isAvailable_menuOn_visEffects() {
+ public void isAvailable_visEffects() {
mBackend.mPolicy = new NotificationManager.Policy(0, 0, 0, 1);
- mController.mShowMenuSelected = false;
assertThat(mController.isAvailable()).isTrue();
}
diff --git a/tests/robotests/src/com/android/settings/notification/ZenOnboardingActivityTest.java b/tests/robotests/src/com/android/settings/notification/ZenOnboardingActivityTest.java
index b4d3700..e09dc0d 100644
--- a/tests/robotests/src/com/android/settings/notification/ZenOnboardingActivityTest.java
+++ b/tests/robotests/src/com/android/settings/notification/ZenOnboardingActivityTest.java
@@ -18,21 +18,11 @@
import static android.app.NotificationManager.Policy.PRIORITY_CATEGORY_ALARMS;
import static android.app.NotificationManager.Policy.PRIORITY_CATEGORY_REPEAT_CALLERS;
-import static android.app.NotificationManager.Policy.PRIORITY_SENDERS_ANY;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_AMBIENT;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_BADGE;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_FULL_SCREEN_INTENT;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_LIGHTS;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_NOTIFICATION_LIST;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_PEEK;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_SCREEN_OFF;
import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_SCREEN_ON;
-import static android.app.NotificationManager.Policy.SUPPRESSED_EFFECT_STATUS_BAR;
import static com.android.settings.notification.ZenOnboardingActivity.ALWAYS_SHOW_THRESHOLD;
-import static com.android.settings.notification.ZenOnboardingActivity.PREF_KEY_SUGGESTION_VIEWED;
import static com.android.settings.notification.ZenOnboardingActivity
- .PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME;
+ .PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME;
import static com.android.settings.notification.ZenOnboardingActivity.isSuggestionComplete;
import static com.google.common.truth.Truth.assertThat;
@@ -99,10 +89,11 @@
}
@Test
- public void save() {
+ public void saveNewSetting() {
Policy policy = new Policy(PRIORITY_CATEGORY_ALARMS, 0, 0, SUPPRESSED_EFFECT_SCREEN_ON);
when(mNm.getNotificationPolicy()).thenReturn(policy);
+ mActivity.mNewSetting.performClick();
mActivity.save(null);
verify(mMetricsLogger).action(MetricsEvent.ACTION_ZEN_ONBOARDING_OK);
@@ -120,24 +111,14 @@
}
@Test
- public void close() {
- Policy policy = new Policy(
- PRIORITY_CATEGORY_ALARMS, PRIORITY_SENDERS_ANY, 0,
- SUPPRESSED_EFFECT_SCREEN_ON
- | SUPPRESSED_EFFECT_SCREEN_OFF
- | SUPPRESSED_EFFECT_FULL_SCREEN_INTENT
- | SUPPRESSED_EFFECT_LIGHTS
- | SUPPRESSED_EFFECT_PEEK
- | SUPPRESSED_EFFECT_STATUS_BAR
- | SUPPRESSED_EFFECT_BADGE
- | SUPPRESSED_EFFECT_AMBIENT
- | SUPPRESSED_EFFECT_NOTIFICATION_LIST);
+ public void keepCurrentSetting() {
+ Policy policy = new Policy(PRIORITY_CATEGORY_ALARMS, 0, 0, SUPPRESSED_EFFECT_SCREEN_ON);
when(mNm.getNotificationPolicy()).thenReturn(policy);
- mActivity.close(null);
+ mActivity.mKeepCurrentSetting.performClick();
+ mActivity.save(null);
verify(mMetricsLogger).action(MetricsEvent.ACTION_ZEN_ONBOARDING_KEEP_CURRENT_SETTINGS);
-
verify(mNm, never()).setNotificationPolicy(any());
}
@@ -192,7 +173,7 @@
firstTime -= ALWAYS_SHOW_THRESHOLD * 2;
}
- getSharedPreferences().edit().putLong(PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME,
+ getSharedPreferences().edit().putLong(PREF_KEY_SUGGESTION_FIRST_DISPLAY_TIME,
firstTime).commit();
}
diff --git a/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java b/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
index bd589bf..00e8fe1 100644
--- a/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
+++ b/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
@@ -204,18 +204,18 @@
}
@Test
- public void testDynamicSummary_returnsSliceSummary() {
+ public void getDynamicSummary_returnsScreenTitle() {
final SliceData data = getDummyData();
final FakePreferenceController controller = new FakePreferenceController(mContext, KEY);
final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
- assertThat(summary).isEqualTo(data.getSummary());
+ assertThat(summary).isEqualTo(data.getScreenTitle());
}
@Test
- public void testDynamicSummary_returnsFragmentSummary() {
- final SliceData data = getDummyData(null);
+ public void getDynamicSummary_noScreenTitle_returnsPrefControllerSummary() {
+ final SliceData data = getDummyData("", "");
final FakePreferenceController controller = spy(
new FakePreferenceController(mContext, KEY));
final String controllerSummary = "new_Summary";
@@ -227,8 +227,21 @@
}
@Test
- public void testDynamicSummary_returnsSliceEmptyString() {
- final SliceData data = getDummyData(null);
+ public void getDynamicSummary_screenTitleMatchesTitle_returnsPrefControllerSummary() {
+ final SliceData data = getDummyData("", TITLE);
+ final FakePreferenceController controller = spy(
+ new FakePreferenceController(mContext, KEY));
+ final String controllerSummary = "new_Summary";
+ doReturn(controllerSummary).when(controller).getSummary();
+
+ final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
+
+ assertThat(summary).isEqualTo(controllerSummary);
+ }
+
+ @Test
+ public void getDynamicSummary_emptyScreenTitle_emptyControllerSummary_returnsEmptyString() {
+ final SliceData data = getDummyData(null, null);
final FakePreferenceController controller = new FakePreferenceController(mContext, KEY);
final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
@@ -236,8 +249,9 @@
}
@Test
- public void testDynamicSummary_placeHolderString_returnsEmptyString() {
- final SliceData data = getDummyData(mContext.getString(R.string.summary_placeholder));
+ public void
+ getDynamicSummary_emptyScreenTitle_placeHolderControllerSummary_returnsEmptyString() {
+ final SliceData data = getDummyData(mContext.getString(R.string.summary_placeholder), null);
final FakePreferenceController controller = new FakePreferenceController(mContext, KEY);
final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
@@ -245,9 +259,9 @@
}
@Test
- public void testDynamicSummary_sliceDataAndFragmentPlaceholder_returnsSliceEmptyString() {
+ public void getDynamicSummary_screenTitleAndControllerPlaceholder_returnsSliceEmptyString() {
final String summaryPlaceholder = mContext.getString(R.string.summary_placeholder);
- final SliceData data = getDummyData(summaryPlaceholder);
+ final SliceData data = getDummyData(summaryPlaceholder, summaryPlaceholder);
final FakePreferenceController controller = spy(
new FakePreferenceController(mContext, KEY));
doReturn(summaryPlaceholder).when(controller).getSummary();
@@ -258,18 +272,6 @@
}
@Test
- public void summaryText_bothDynamicAndStaticSummary_dynamicSummaryReturned() {
- SliceData data = getDummyData("bad_summary");
- FakePreferenceController controller = spy(new FakePreferenceController(mContext, KEY));
- String controllerSummary = "new_Summary";
- doReturn(controllerSummary).when(controller).getSummary();
-
- CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
-
- assertThat(summary).isEqualTo(controllerSummary);
- }
-
- @Test
public void getPathData_splitsIntentUri() {
final Uri uri = new Uri.Builder()
.authority(SettingsSliceProvider.SLICE_AUTHORITY)
@@ -417,23 +419,24 @@
}
private SliceData getDummyData() {
- return getDummyData(TOGGLE_CONTROLLER, SUMMARY, SliceData.SliceType.SWITCH);
+ return getDummyData(TOGGLE_CONTROLLER, SUMMARY, SliceData.SliceType.SWITCH, SCREEN_TITLE);
}
- private SliceData getDummyData(String summary) {
- return getDummyData(TOGGLE_CONTROLLER, summary, SliceData.SliceType.SWITCH);
+ private SliceData getDummyData(String summary, String screenTitle) {
+ return getDummyData(TOGGLE_CONTROLLER, summary, SliceData.SliceType.SWITCH, screenTitle);
}
private SliceData getDummyData(Class prefController, int sliceType) {
- return getDummyData(prefController, SUMMARY, sliceType);
+ return getDummyData(prefController, SUMMARY, sliceType, SCREEN_TITLE);
}
- private SliceData getDummyData(Class prefController, String summary, int sliceType) {
+ private SliceData getDummyData(Class prefController, String summary, int sliceType,
+ String screenTitle) {
return new SliceData.Builder()
.setKey(KEY)
.setTitle(TITLE)
.setSummary(summary)
- .setScreenTitle(SCREEN_TITLE)
+ .setScreenTitle(screenTitle)
.setKeywords(KEYWORDS)
.setIcon(ICON)
.setFragmentName(FRAGMENT_NAME)
diff --git a/tests/robotests/src/com/android/settings/support/NewDeviceIntroSuggestionActivityTest.java b/tests/robotests/src/com/android/settings/support/NewDeviceIntroSuggestionActivityTest.java
index 286676d..8b03376 100644
--- a/tests/robotests/src/com/android/settings/support/NewDeviceIntroSuggestionActivityTest.java
+++ b/tests/robotests/src/com/android/settings/support/NewDeviceIntroSuggestionActivityTest.java
@@ -19,7 +19,10 @@
import static com.android.settings.support.NewDeviceIntroSuggestionActivity.PERMANENT_DISMISS_THRESHOLD;
import static com.android.settings.support.NewDeviceIntroSuggestionActivity.PREF_KEY_SUGGGESTION_COMPLETE;
import static com.android.settings.support.NewDeviceIntroSuggestionActivity.PREF_KEY_SUGGGESTION_FIRST_DISPLAY_TIME;
+
+import static com.android.settings.support.NewDeviceIntroSuggestionActivity.TIPS_PACKAGE_NAME;
import static com.android.settings.support.NewDeviceIntroSuggestionActivity.isSuggestionComplete;
+
import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.any;
import static org.mockito.Mockito.when;
@@ -27,6 +30,7 @@
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
+import android.content.pm.PackageInfo;
import android.content.pm.ResolveInfo;
import com.android.settings.R;
@@ -65,6 +69,40 @@
}
@Test
+ public void isSuggestionComplete_TipsNotExistsAndNotExpiredAndCanOpenUrl_shouldReturnFalse() {
+ mShadowPackageManager.removePackage(TIPS_PACKAGE_NAME);
+
+ when(mMockContext.getResources()
+ .getBoolean(R.bool.config_new_device_intro_suggestion_supported))
+ .thenReturn(true);
+
+ when(mFeatureFactory.supportFeatureProvider.getNewDeviceIntroUrl(any(Context.class)))
+ .thenReturn("https://com.android.settings");
+ final Intent intent = NewDeviceIntroSuggestionActivity.getLaunchIntent(mContext);
+ mShadowPackageManager.addResolveInfoForIntent(intent, new ResolveInfo());
+
+ assertThat(isSuggestionComplete(mContext)).isFalse();
+ }
+
+ @Test
+ public void isSuggestionComplete_TipsExistsAndNotExpiredAndCanOpenUrl_shouldReturnTrue() {
+ final PackageInfo mockInfo = new PackageInfo();
+ mockInfo.packageName = TIPS_PACKAGE_NAME;
+ mShadowPackageManager.addPackage(mockInfo);
+
+ when(mMockContext.getResources()
+ .getBoolean(R.bool.config_new_device_intro_suggestion_supported))
+ .thenReturn(true);
+
+ when(mFeatureFactory.supportFeatureProvider.getNewDeviceIntroUrl(any(Context.class)))
+ .thenReturn("https://com.android.settings");
+ final Intent intent = NewDeviceIntroSuggestionActivity.getLaunchIntent(mContext);
+ mShadowPackageManager.addResolveInfoForIntent(intent, new ResolveInfo());
+
+ assertThat(isSuggestionComplete(mContext)).isTrue();
+ }
+
+ @Test
public void isSuggestionComplete_notSupported_shouldReturnTrue() {
when(mMockContext.getResources()
.getBoolean(R.bool.config_new_device_intro_suggestion_supported))
diff --git a/tests/robotests/src/com/android/settings/testutils/SliceTester.java b/tests/robotests/src/com/android/settings/testutils/SliceTester.java
index 529e32d..4c4b040 100644
--- a/tests/robotests/src/com/android/settings/testutils/SliceTester.java
+++ b/tests/robotests/src/com/android/settings/testutils/SliceTester.java
@@ -17,6 +17,8 @@
package com.android.settings.testutils;
import static android.app.slice.Slice.HINT_TITLE;
+import static android.app.slice.Slice.SUBTYPE_COLOR;
+import static android.app.slice.SliceItem.FORMAT_INT;
import static android.app.slice.SliceItem.FORMAT_TEXT;
import static com.android.settings.core.BasePreferenceController.CONDITIONALLY_UNAVAILABLE;
@@ -37,11 +39,13 @@
import androidx.slice.Slice;
import androidx.slice.SliceItem;
import androidx.slice.SliceMetadata;
+import androidx.slice.builders.ListBuilder;
import androidx.slice.core.SliceAction;
import androidx.slice.core.SliceQuery;
import android.support.v4.graphics.drawable.IconCompat;
+import com.android.settings.Utils;
import com.android.settings.slices.SettingsSliceProvider;
import com.android.settings.slices.SliceBuilderUtils;
import com.android.settings.slices.SliceData;
@@ -59,10 +63,19 @@
* - Correct intent
* - Correct title
* - Correct keywords
+ * - TTL
+ * - Color
*/
public static void testSettingsIntentSlice(Context context, Slice slice, SliceData sliceData) {
final SliceMetadata metadata = SliceMetadata.from(context, slice);
+ final long sliceTTL = metadata.getExpiry();
+ assertThat(sliceTTL).isEqualTo(ListBuilder.INFINITY);
+
+ final SliceItem colorItem = SliceQuery.findSubtype(slice, FORMAT_INT, SUBTYPE_COLOR);
+ final int color = colorItem.getInt();
+ assertThat(color).isEqualTo(Utils.getColorAccent(context));
+
final List<SliceAction> toggles = metadata.getToggles();
assertThat(toggles).isEmpty();
@@ -83,13 +96,22 @@
* - Correct content intent
* - Correct title
* - Correct keywords
+ * - TTL
+ * - Color
*/
public static void testSettingsToggleSlice(Context context, Slice slice, SliceData sliceData) {
final SliceMetadata metadata = SliceMetadata.from(context, slice);
+ final SliceItem colorItem = SliceQuery.findSubtype(slice, FORMAT_INT, SUBTYPE_COLOR);
+ final int color = colorItem.getInt();
+ assertThat(color).isEqualTo(Utils.getColorAccent(context));
+
final List<SliceAction> toggles = metadata.getToggles();
assertThat(toggles).hasSize(1);
+ final long sliceTTL = metadata.getExpiry();
+ assertThat(sliceTTL).isEqualTo(ListBuilder.INFINITY);
+
final SliceAction mainToggleAction = toggles.get(0);
final IconCompat expectedToggleIcon = IconCompat.createWithResource(context,
@@ -117,13 +139,22 @@
* - No intent
* - Correct title
* - Correct keywords
+ * - TTL
+ * - Color
*/
public static void testSettingsSliderSlice(Context context, Slice slice, SliceData sliceData) {
final SliceMetadata metadata = SliceMetadata.from(context, slice);
+ final SliceItem colorItem = SliceQuery.findSubtype(slice, FORMAT_INT, SUBTYPE_COLOR);
+ final int color = colorItem.getInt();
+ assertThat(color).isEqualTo(Utils.getColorAccent(context));
+
final IconCompat expectedToggleIcon = IconCompat.createWithResource(context,
sliceData.getIconResource());
+ final long sliceTTL = metadata.getExpiry();
+ assertThat(sliceTTL).isEqualTo(ListBuilder.INFINITY);
+
// Check primary intent
final PendingIntent primaryPendingIntent = metadata.getPrimaryAction().getAction();
assertThat(primaryPendingIntent).isEqualTo(
@@ -141,11 +172,20 @@
* - Correct title
* - Correct intent
* - Correct keywords
+ * - Color
+ * - TTL
*/
public static void testSettingsUnavailableSlice(Context context, Slice slice,
SliceData sliceData) {
final SliceMetadata metadata = SliceMetadata.from(context, slice);
+ final long sliceTTL = metadata.getExpiry();
+ assertThat(sliceTTL).isEqualTo(ListBuilder.INFINITY);
+
+ final SliceItem colorItem = SliceQuery.findSubtype(slice, FORMAT_INT, SUBTYPE_COLOR);
+ final int color = colorItem.getInt();
+ assertThat(color).isEqualTo(Utils.getColorAccent(context));
+
final List<SliceAction> toggles = metadata.getToggles();
assertThat(toggles).isEmpty();
diff --git a/tests/robotests/src/com/android/settings/widget/EntityHeaderControllerTest.java b/tests/robotests/src/com/android/settings/widget/EntityHeaderControllerTest.java
index e32ef77..22ad764 100644
--- a/tests/robotests/src/com/android/settings/widget/EntityHeaderControllerTest.java
+++ b/tests/robotests/src/com/android/settings/widget/EntityHeaderControllerTest.java
@@ -41,7 +41,6 @@
import android.widget.ImageButton;
import android.widget.TextView;
-import com.android.internal.logging.nano.MetricsProto;
import com.android.settings.R;
import com.android.settings.applications.LayoutPreference;
import com.android.settings.testutils.FakeFeatureFactory;
@@ -113,7 +112,7 @@
public void bindViews_shouldBindAllData() {
final String testString = "test";
final View header =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
+ mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
final TextView label = header.findViewById(R.id.entity_header_title);
final TextView summary = header.findViewById(R.id.entity_header_summary);
final TextView secondSummary = header.findViewById(R.id.entity_header_second_summary);
@@ -134,41 +133,6 @@
}
@Test
- public void bindButton_hasAppPref_shouldShowButton() {
- final ResolveInfo info = new ResolveInfo();
- info.activityInfo = new ActivityInfo();
- info.activityInfo.packageName = "123";
- info.activityInfo.name = "321";
- final View appLinks =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
- when(mActivity.getApplicationContext()).thenReturn(mContext);
- when(mContext.getPackageManager().resolveActivity(any(Intent.class), anyInt()))
- .thenReturn(info);
-
- mController = EntityHeaderController.newInstance(mActivity, mFragment, appLinks);
- mController.setButtonActions(
- EntityHeaderController.ActionType.ACTION_APP_PREFERENCE,
- EntityHeaderController.ActionType.ACTION_NONE);
- mController.done(mActivity);
-
- final ImageButton button1 = appLinks.findViewById(android.R.id.button1);
- assertThat(button1).isNotNull();
- assertThat(button1.getVisibility()).isEqualTo(View.VISIBLE);
- assertThat(button1.getDrawable()).isNotNull();
- assertThat(appLinks.findViewById(android.R.id.button2).getVisibility())
- .isEqualTo(View.GONE);
- try {
- appLinks.findViewById(android.R.id.button1).performClick();
- } catch (Exception e) {
- // Ignore exception because the launching intent is fake.
- }
- verify(mFeatureFactory.metricsFeatureProvider).actionWithSource(mContext,
- MetricsProto.MetricsEvent.VIEW_UNKNOWN,
- MetricsProto.MetricsEvent.ACTION_OPEN_APP_SETTING);
- verify(mFragment).startActivity(any(Intent.class));
- }
-
- @Test
public void bindButton_hasEditRuleNameClickListener_shouldShowButton() {
final ResolveInfo info = new ResolveInfo();
info.activityInfo = new ActivityInfo();
@@ -217,30 +181,9 @@
@Test
- public void bindButton_noAppPref_shouldNotShowButton() {
- final View appLinks =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
- when(mContext.getPackageManager().resolveActivity(any(Intent.class), anyInt()))
- .thenReturn(null);
-
- mController = EntityHeaderController.newInstance(mActivity, mFragment, appLinks);
- mController.setButtonActions(
- EntityHeaderController.ActionType.ACTION_APP_PREFERENCE,
- EntityHeaderController.ActionType.ACTION_NONE);
- mController.done(mActivity);
-
- final ImageButton button1 = appLinks.findViewById(android.R.id.button1);
- assertThat(button1).isNotNull();
- assertThat(button1.getVisibility()).isEqualTo(View.GONE);
- assertThat(button1.getDrawable()).isNull();
- assertThat(appLinks.findViewById(android.R.id.button2).getVisibility())
- .isEqualTo(View.GONE);
- }
-
- @Test
public void bindButton_noAppInfo_shouldNotAttachClickListener() {
final View appLinks =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
+ mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
final Activity activity = mock(Activity.class);
when(mFragment.getActivity()).thenReturn(activity);
@@ -265,7 +208,7 @@
@Test
public void bindButton_hasAppInfo_shouldAttachClickListener() {
final View appLinks =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
+ mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
final Activity activity = mock(Activity.class);
when(mFragment.getActivity()).thenReturn(activity);
when(mContext.getString(eq(R.string.application_info_label))).thenReturn("App Info");
@@ -281,13 +224,13 @@
appLinks.findViewById(R.id.entity_header_content).performClick();
verify(activity)
- .startActivityForResultAsUser(any(Intent.class), anyInt(), any(UserHandle.class));
+ .startActivityForResultAsUser(any(Intent.class), anyInt(), any(UserHandle.class));
}
@Test
public void iconContentDescription_shouldWorkWithSetIcon() {
final View view =
- mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
+ mLayoutInflater.inflate(R.layout.settings_entity_header, null /* root */);
when(mFragment.getActivity()).thenReturn(mock(Activity.class));
mController = EntityHeaderController.newInstance(mActivity, mFragment, view);
String description = "Fake Description";
diff --git a/tests/robotests/src/com/android/settings/wifi/calling/WifiCallingSliceHelperTest.java b/tests/robotests/src/com/android/settings/wifi/calling/WifiCallingSliceHelperTest.java
new file mode 100644
index 0000000..ac3ff3f
--- /dev/null
+++ b/tests/robotests/src/com/android/settings/wifi/calling/WifiCallingSliceHelperTest.java
@@ -0,0 +1,316 @@
+/*
+ * 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.calling;
+
+import static android.app.slice.Slice.EXTRA_TOGGLE_STATE;
+import static android.app.slice.Slice.HINT_TITLE;
+import static android.app.slice.SliceItem.FORMAT_TEXT;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.mockito.ArgumentMatchers.anyInt;
+import static org.mockito.Mockito.doReturn;
+import static org.mockito.Mockito.spy;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
+import android.app.PendingIntent;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.Resources;
+import android.net.Uri;
+import android.telephony.CarrierConfigManager;
+
+import androidx.slice.Slice;
+import androidx.slice.SliceItem;
+import androidx.slice.SliceMetadata;
+import androidx.slice.SliceProvider;
+import androidx.slice.core.SliceAction;
+import androidx.slice.core.SliceQuery;
+import androidx.slice.widget.SliceLiveData;
+
+import com.android.ims.ImsManager;
+import com.android.settings.R;
+import com.android.settings.slices.SettingsSliceProvider;
+import com.android.settings.slices.SliceBroadcastReceiver;
+import com.android.settings.slices.SliceBuilderUtils;
+import com.android.settings.slices.SliceData;
+import com.android.settings.slices.SlicesFeatureProvider;
+import com.android.settings.testutils.FakeFeatureFactory;
+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.Mock;
+import org.mockito.MockitoAnnotations;
+import org.robolectric.RuntimeEnvironment;
+
+import java.util.List;
+
+@RunWith(SettingsRobolectricTestRunner.class)
+public class WifiCallingSliceHelperTest {
+
+ private Context mContext;
+ @Mock
+ private CarrierConfigManager mMockCarrierConfigManager;
+
+ @Mock
+ private ImsManager mMockImsManager;
+
+ private final Uri mWfcURI = Uri.parse("content://com.android.settings.slices/wifi_calling");
+
+ private FakeWifiCallingSliceHelper mWfcSliceHelper;
+ private SettingsSliceProvider mProvider;
+ private SliceBroadcastReceiver mReceiver;
+ private FakeFeatureFactory mFeatureFactory;
+ private SlicesFeatureProvider mSlicesFeatureProvider;
+
+ @Before
+ public void setUp() {
+ MockitoAnnotations.initMocks(this);
+ mContext = spy(RuntimeEnvironment.application);
+
+ //setup for SettingsSliceProvider tests
+ mProvider = spy(new SettingsSliceProvider());
+ doReturn(mContext).when(mProvider).getContext();
+
+ //setup for SliceBroadcastReceiver test
+ mReceiver = spy(new SliceBroadcastReceiver());
+
+ mFeatureFactory = FakeFeatureFactory.setupForTest();
+ mSlicesFeatureProvider = mFeatureFactory.getSlicesFeatureProvider();
+
+ // Prevent crash in SliceMetadata.
+ Resources resources = spy(mContext.getResources());
+ doReturn(60).when(resources).getDimensionPixelSize(anyInt());
+ doReturn(resources).when(mContext).getResources();
+
+ mWfcSliceHelper = new FakeWifiCallingSliceHelper(mContext);
+
+ // Set-up specs for SliceMetadata.
+ SliceProvider.setSpecs(SliceLiveData.SUPPORTED_SPECS);
+ }
+
+ @Test
+ public void test_CreateWifiCallingSlice_invalidSubId() {
+ mWfcSliceHelper.setDefaultVoiceSubId(-1);
+
+ final Slice slice = mWfcSliceHelper.createWifiCallingSlice(mWfcURI);
+
+ testWifiCallingSettingsUnavailableSlice(slice, null,
+ SliceBuilderUtils.getSettingsIntent(mContext));
+ }
+
+ @Test
+ public void test_CreateWifiCallingSlice_wfcNotSupported() {
+ doReturn(false).when(mMockImsManager).isWfcEnabledByPlatform();
+
+ final Slice slice = mWfcSliceHelper.createWifiCallingSlice(mWfcURI);
+
+ assertThat(mWfcSliceHelper.getDefaultVoiceSubId()).isEqualTo(1);
+ testWifiCallingSettingsUnavailableSlice(slice, null,
+ SliceBuilderUtils.getSettingsIntent(mContext));
+ }
+
+ @Test
+ public void test_CreateWifiCallingSlice_needsActivation() {
+ /* In cases where activation is needed and the user action
+ would be turning on the wifi calling (i.e. if wifi calling is
+ turned off) we need to guide the user to wifi calling settings
+ activity so the user can perform the activation there.(PrimaryAction)
+ */
+ doReturn(true).when(mMockImsManager).isWfcEnabledByPlatform();
+ doReturn(true).when(mMockImsManager).isWfcProvisionedOnDevice();
+ doReturn(false).when(mMockImsManager).isWfcEnabledByUser();
+ doReturn(false).when(mMockImsManager).isNonTtyOrTtyOnVolteEnabled();
+ doReturn(null).when(mMockCarrierConfigManager).getConfigForSubId(1);
+ mWfcSliceHelper.setActivationAppIntent(new Intent()); // dummy Intent
+
+ final Slice slice = mWfcSliceHelper.createWifiCallingSlice(mWfcURI);
+
+ assertThat(mWfcSliceHelper.getDefaultVoiceSubId()).isEqualTo(1);
+ testWifiCallingSettingsUnavailableSlice(slice, null,
+ getActivityIntent(WifiCallingSliceHelper.ACTION_WIFI_CALLING_SETTINGS_ACTIVITY));
+ }
+
+ @Test
+ public void test_CreateWifiCallingSlice_success() {
+ doReturn(true).when(mMockImsManager).isWfcEnabledByPlatform();
+ doReturn(true).when(mMockImsManager).isWfcProvisionedOnDevice();
+ doReturn(true).when(mMockImsManager).isWfcEnabledByUser();
+ doReturn(true).when(mMockImsManager).isNonTtyOrTtyOnVolteEnabled();
+ doReturn(null).when(mMockCarrierConfigManager).getConfigForSubId(1);
+
+ final Slice slice = mWfcSliceHelper.createWifiCallingSlice(mWfcURI);
+
+ assertThat(mWfcSliceHelper.getDefaultVoiceSubId()).isEqualTo(1);
+ testWifiCallingSettingsToggleSlice(slice, null);
+ }
+
+ @Test
+ public void test_SettingSliceProvider_getsRightSliceWifiCalling() {
+ doReturn(true).when(mMockImsManager).isWfcEnabledByPlatform();
+ doReturn(true).when(mMockImsManager).isWfcProvisionedOnDevice();
+ doReturn(true).when(mMockImsManager).isWfcEnabledByUser();
+ doReturn(true).when(mMockImsManager).isNonTtyOrTtyOnVolteEnabled();
+ doReturn(null).when(mMockCarrierConfigManager).getConfigForSubId(1);
+ doReturn(mWfcSliceHelper).when(mSlicesFeatureProvider)
+ .getNewWifiCallingSliceHelper(mContext);
+
+ final Slice slice = mProvider.onBindSlice(mWfcURI);
+
+ assertThat(mWfcSliceHelper.getDefaultVoiceSubId()).isEqualTo(1);
+ testWifiCallingSettingsToggleSlice(slice, null);
+ }
+
+ @Test
+ public void test_SliceBroadcastReceiver_toggleOffWifiCalling() {
+ doReturn(true).when(mMockImsManager).isWfcEnabledByPlatform();
+ doReturn(true).when(mMockImsManager).isWfcProvisionedOnDevice();
+ doReturn(false).when(mMockImsManager).isWfcEnabledByUser();
+ doReturn(true).when(mMockImsManager).isNonTtyOrTtyOnVolteEnabled();
+ doReturn(mWfcSliceHelper).when(mSlicesFeatureProvider)
+ .getNewWifiCallingSliceHelper(mContext);
+ mWfcSliceHelper.setActivationAppIntent(null);
+
+ ArgumentCaptor<Boolean> mWfcSettingCaptor = ArgumentCaptor.forClass(Boolean.class);
+
+ // turn on Wifi calling setting
+ Intent intent = new Intent(WifiCallingSliceHelper.ACTION_WIFI_CALLING_CHANGED);
+ intent.putExtra(EXTRA_TOGGLE_STATE, true);
+
+ // change the setting
+ mReceiver.onReceive(mContext, intent);
+
+ verify((mMockImsManager)).setWfcSetting(mWfcSettingCaptor.capture());
+
+ // assert the change
+ assertThat(mWfcSettingCaptor.getValue()).isTrue();
+ }
+
+ private void testWifiCallingSettingsUnavailableSlice(Slice slice,
+ SliceData sliceData, PendingIntent expectedPrimaryAction) {
+ final SliceMetadata metadata = SliceMetadata.from(mContext, slice);
+
+ //Check there is no toggle action
+ final List<SliceAction> toggles = metadata.getToggles();
+ assertThat(toggles).isEmpty();
+
+ // Check whether the primary action is to open wifi calling settings activity
+ final PendingIntent primaryPendingIntent =
+ metadata.getPrimaryAction().getAction();
+ assertThat(primaryPendingIntent).isEqualTo(expectedPrimaryAction);
+
+ // Check the title
+ final List<SliceItem> sliceItems = slice.getItems();
+ assertTitle(sliceItems, mContext.getString(R.string.wifi_calling_settings_title));
+ }
+
+ private void testWifiCallingSettingsToggleSlice(Slice slice,
+ SliceData sliceData) {
+ final SliceMetadata metadata = SliceMetadata.from(mContext, slice);
+
+ final List<SliceAction> toggles = metadata.getToggles();
+ assertThat(toggles).hasSize(1);
+
+ final SliceAction mainToggleAction = toggles.get(0);
+
+ // Check intent in Toggle Action
+ final PendingIntent togglePendingIntent = mainToggleAction.getAction();
+ final PendingIntent expectedToggleIntent = getBroadcastIntent(
+ WifiCallingSliceHelper.ACTION_WIFI_CALLING_CHANGED);
+ assertThat(togglePendingIntent).isEqualTo(expectedToggleIntent);
+
+ // Check primary intent
+ final PendingIntent primaryPendingIntent = metadata.getPrimaryAction().getAction();
+ final PendingIntent expectedPendingIntent =
+ getActivityIntent(WifiCallingSliceHelper.ACTION_WIFI_CALLING_SETTINGS_ACTIVITY);
+ assertThat(primaryPendingIntent).isEqualTo(expectedPendingIntent);
+
+ // Check the title
+ final List<SliceItem> sliceItems = slice.getItems();
+ assertTitle(sliceItems, mContext.getString(R.string.wifi_calling_settings_title));
+ }
+
+ private PendingIntent getBroadcastIntent(String action) {
+ final Intent intent = new Intent(action);
+ intent.setClass(mContext, SliceBroadcastReceiver.class);
+ return PendingIntent.getBroadcast(mContext, 0 /* requestCode */, intent,
+ PendingIntent.FLAG_CANCEL_CURRENT);
+ }
+
+ private PendingIntent getActivityIntent(String action) {
+ final Intent intent = new Intent(action);
+ intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ return PendingIntent.getActivity(mContext, 0 /* requestCode */, intent, 0 /* flags */);
+ }
+
+ private void assertTitle(List<SliceItem> sliceItems, String title) {
+ boolean hasTitle = false;
+ for (SliceItem item : sliceItems) {
+ List<SliceItem> titleItems = SliceQuery.findAll(item, FORMAT_TEXT, HINT_TITLE,
+ null /* non-hints */);
+ if (titleItems == null) {
+ continue;
+ }
+
+ hasTitle = true;
+ for (SliceItem subTitleItem : titleItems) {
+ assertThat(subTitleItem.getText()).isEqualTo(title);
+ }
+ }
+ assertThat(hasTitle).isTrue();
+ }
+ private class FakeWifiCallingSliceHelper extends WifiCallingSliceHelper {
+ int mSubId = 1;
+
+ private Intent mActivationAppIntent;
+ FakeWifiCallingSliceHelper(Context context) {
+ super(context);
+ mActivationAppIntent = null;
+ }
+
+ @Override
+ protected CarrierConfigManager getCarrierConfigManager(Context mContext) {
+ return mMockCarrierConfigManager;
+ }
+
+ @Override
+ protected ImsManager getImsManager(int subId) {
+ return mMockImsManager;
+ }
+
+ protected int getDefaultVoiceSubId() {
+ return mSubId;
+ }
+
+ protected void setDefaultVoiceSubId(int id) {
+ mSubId = id;
+ }
+
+ @Override
+ protected Intent getWifiCallingCarrierActivityIntent(int subId) {
+ return mActivationAppIntent;
+ }
+
+ public void setActivationAppIntent(Intent intent) {
+ mActivationAppIntent = intent;
+ }
+ }
+}