Merge "Fix test expectations for NetworkCallbacks" into pi-dev
diff --git a/res/drawable-nodpi/auto_awesome_battery b/res/drawable-nodpi/auto_awesome_battery
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/res/drawable-nodpi/auto_awesome_battery
diff --git a/res/drawable/ic_settings_aod.xml b/res/drawable/ic_settings_aod.xml
new file mode 100644
index 0000000..8d91349
--- /dev/null
+++ b/res/drawable/ic_settings_aod.xml
@@ -0,0 +1,34 @@
+<?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:width="24dp"
+        android:height="24dp"
+        android:viewportWidth="24"
+        android:viewportHeight="24">
+
+    <path
+        android:fillColor="#000000"
+        android:pathData="M17,1.01L7,1C5.9,1,5,1.9,5,3v18c0,1.1,0.9,2,2,2h10c1.1,0,2-0.9,2-2V3C19,1.9,18.1,1.01,17,1.01z M17,21H7l0-1h10V21z M17,18H7V6h10V18z M17,4H7V3h10V4z" />
+    <path
+        android:fillColor="#000000"
+        android:pathData="M 8 10 H 16 V 11.5 H 8 V 10 Z" />
+    <path
+        android:fillColor="#000000"
+        android:pathData="M 9 13 H 15 V 14.5 H 9 V 13 Z" />
+    <path
+        android:pathData="M 0 0 H 24 V 24 H 0 V 0 Z" />
+</vector>
\ No newline at end of file
diff --git a/res/layout/smart_battery_header.xml b/res/layout/smart_battery_header.xml
deleted file mode 100644
index 960f04a..0000000
--- a/res/layout/smart_battery_header.xml
+++ /dev/null
@@ -1,30 +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.
-  -->
-
-<!-- Entity header -->
-<LinearLayout
-    xmlns:android="http://schemas.android.com/apk/res/android"
-    android:id="@+id/entity_header"
-    style="@style/EntityHeader"
-    android:layout_width="match_parent"
-    android:layout_height="match_parent"
-    android:minHeight="200dp"
-    android:paddingBottom="32dp"
-    android:paddingStart="@dimen/preference_no_icon_padding_start"
-    android:paddingTop="24dp">
-
-</LinearLayout>
diff --git a/res/layout/suggestion_tile_with_button.xml b/res/layout/suggestion_tile_with_button.xml
index a901a48..cff0566 100644
--- a/res/layout/suggestion_tile_with_button.xml
+++ b/res/layout/suggestion_tile_with_button.xml
@@ -86,15 +86,18 @@
             android:singleLine="true"
             android:textAppearance="@style/TextAppearance.SuggestionSummary" />
 
-        <Button
-            android:id="@android:id/primary"
-            style="@style/ActionPrimaryButton"
-            android:layout_gravity="center"
+        <FrameLayout
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:layout_marginTop="16dp"
-            android:layout_marginBottom="18dp"
-            android:text="@string/suggestion_button_text" />
+            style="@style/SuggestionCardButton">
+            <Button
+                android:id="@android:id/primary"
+                style="@style/ActionPrimaryButton"
+                android:layout_gravity="center"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="@string/suggestion_button_text" />
+        </FrameLayout>
 
     </LinearLayout>
 
diff --git a/res/layout/video_preference.xml b/res/layout/video_preference.xml
index 9ab52ae..55bc7a5 100644
--- a/res/layout/video_preference.xml
+++ b/res/layout/video_preference.xml
@@ -23,11 +23,11 @@
     android:clipToPadding="false"
     android:gravity="center"
     android:minHeight="?android:attr/listPreferredItemHeightSmall"
-    android:paddingEnd="?android:attr/listPreferredItemPaddingEnd"
     android:orientation="horizontal">
 
     <com.android.settings.widget.AspectRatioFrameLayout
-        android:layout_width="240dp"
+        android:id="@+id/video_container"
+        android:layout_width="wrap_content"
         android:layout_height="240dp"
         android:padding="@dimen/gesture_animation_padding">
 
diff --git a/res/raw/auto_awesome_battery.mp4 b/res/raw/auto_awesome_battery.mp4
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/res/raw/auto_awesome_battery.mp4
diff --git a/res/values-ru/arrays.xml b/res/values-ru/arrays.xml
index f29ab53..df2fbff 100644
--- a/res/values-ru/arrays.xml
+++ b/res/values-ru/arrays.xml
@@ -489,7 +489,7 @@
   <string-array name="wifi_metered_entries">
     <item msgid="5200910605264415911">"Определять автоматически"</item>
     <item msgid="8745603368609022803">"Лимитное"</item>
-    <item msgid="2266114985518865625">"Безлимитное"</item>
+    <item msgid="2266114985518865625">"Без тарификации трафика"</item>
   </string-array>
     <!-- no translation found for wifi_hidden_entries:0 (234221371123852300) -->
     <!-- no translation found for wifi_hidden_entries:1 (3863157480502955888) -->
diff --git a/res/values/dimens.xml b/res/values/dimens.xml
index 406cac2..6a052d2 100755
--- a/res/values/dimens.xml
+++ b/res/values/dimens.xml
@@ -318,6 +318,10 @@
     <dimen name="suggestion_card_inner_margin">12dp</dimen>
     <dimen name="suggestion_card_padding_bottom_one_card">16dp</dimen>
     <dimen name="suggestion_card_corner_radius">2dp</dimen>
+    <dimen name="suggestion_card_icon_side_margin">12dp</dimen>
+    <dimen name="suggestion_card_button_side_margin">8dp</dimen>
+    <dimen name="suggestion_card_button_top_margin">16dp</dimen>
+    <dimen name="suggestion_card_button_bottom_margin">18dp</dimen>
 
     <!-- Padding for the reset screens -->
     <dimen name="reset_checkbox_padding_end">8dp</dimen>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 67c564e..31b4f90 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -6614,6 +6614,8 @@
 
     <!-- Help URL, WiFi [DO NOT TRANSLATE] -->
     <string name="help_url_wifi" translatable="false"></string>
+    <!-- Help URL, WiFi Direct [DO NOT TRANSLATE] -->
+    <string name="help_url_wifi_p2p" translatable="false"></string>
     <!-- Help URL, Bluetooth [DO NOT TRANSLATE] -->
     <string name="help_url_bluetooth" translatable="false"></string>
     <!-- Help URL, Data usage [DO NOT TRANSLATE] -->
@@ -8769,9 +8771,9 @@
     <string name="android_version_pending_update_summary">Update available</string>
 
     <!-- Title for dialog displayed when user selects on a setting locked by an admin [CHAR LIMIT=30] -->
-    <string name="disabled_by_policy_title">Can\'t change this setting</string>
+    <string name="disabled_by_policy_title">Can’t change this setting</string>
     <!-- Title for dialog displayed to tell user that changing volume was disallowed by an admin [CHAR LIMIT=50] -->
-    <string name="disabled_by_policy_title_adjust_volume">Can\'t change volume</string>
+    <string name="disabled_by_policy_title_adjust_volume">Can’t change volume</string>
     <!-- Title for dialog displayed to tell user that outgoing calls were disabled by an admin [CHAR LIMIT=50] -->
     <string name="disabled_by_policy_title_outgoing_calls">Calling not allowed</string>
     <!-- Title for dialog displayed to tell user that sending SMS were disabled by an admin [CHAR LIMIT=50] -->
@@ -8781,9 +8783,9 @@
     <!-- Title for dialog displayed to tell user that screenshots are disabled by an admin [CHAR LIMIT=50] -->
     <string name="disabled_by_policy_title_screen_capture">Screenshot not allowed</string>
     <!-- Title for dialog displayed to tell user that turning off backups is disallowed by an admin [CHAR LIMIT=50] -->
-    <string name="disabled_by_policy_title_turn_off_backups">Can\'t turn off backups</string>
+    <string name="disabled_by_policy_title_turn_off_backups">Can’t turn off backups</string>
     <!-- Title for dialog displayed to tell user that the app was suspended by an admin [CHAR LIMIT=50] -->
-    <string name="disabled_by_policy_title_suspend_packages">Can\'t open this app</string>
+    <string name="disabled_by_policy_title_suspend_packages">Can’t open this app</string>
     <!-- Shown when the user tries to change a settings locked by an admin [CHAR LIMIT=200] -->
     <string name="default_admin_support_msg">If you have questions, contact your IT admin</string>
     <!-- Shown in dialog to allow user to see more information about the device admin [CHAR LIMIT=30] -->
@@ -9395,6 +9397,15 @@
     <!-- Title for settings suggestion for double twist for camera [CHAR LIMIT=60] -->
     <string name="double_twist_for_camera_suggestion_title">Take selfies faster</string>
 
+    <!-- Title text for swipe up to switch apps [CHAR LIMIT=60] -->
+    <string name="swipe_up_to_switch_apps_title">Swipe up on Home button</string>
+    <!-- Summary text for swipe up to switch apps  [CHAR LIMIT=250] -->
+    <string name="swipe_up_to_switch_apps_summary">To switch apps, swipe up on the Home button. Swipe up again to see all apps. Works from any screen. You’ll no longer have an Overview button on the bottom right of your screen.</string>
+    <!-- Title for settings suggestion for swipe up to switch apps [CHAR LIMIT=60] -->
+    <string name="swipe_up_to_switch_apps_suggestion_title">Try the new Home button</string>
+    <!-- Summary for settings suggestion for swipe up to switch apps [CHAR LIMIT=60] -->
+    <string name="swipe_up_to_switch_apps_suggestion_summary">Turn on the new gesture to switch apps</string>
+
     <!-- Preference and settings suggestion title text for ambient display double tap (phone) [CHAR LIMIT=60]-->
     <string name="ambient_display_title" product="default">Double-tap to check phone</string>
     <!-- Preference and settings suggestion title text for ambient display double tap (tablet) [CHAR LIMIT=60]-->
@@ -9590,8 +9601,8 @@
     <string name="do_disclosure_with_name">This device is managed by <xliff:g id="organization_name" example="Foo, Inc.">%s</xliff:g>.</string>
     <!-- Message indicating that the device is enterprise-managed: Space that separates the main text and the "learn more" link that follows it. [CHAR LIMIT=NONE] -->
     <string name="do_disclosure_learn_more_separator">" "</string>
-    <!-- Message indicating that the device is enterprise-managed: Link to learn more about what a Device Owner app can do [CHAR LIMIT=NONE] -->
-    <string name="do_disclosure_learn_more">Learn more</string>
+    <!-- Button label to allow the user to view additional information [CHAR LIMIT=NONE BACKUP_MESSAGE_ID=2416766240581561009] -->
+    <string name="learn_more">Learn more</string>
 
     <!-- Strings for displaying which applications were set as default for specific actions. -->
     <!-- Title for the apps that have been set as default handlers of camera-related intents. [CHAR LIMIT=30] -->
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 86375fa..c6500c4 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -329,6 +329,16 @@
     <style name="SuggestionCardIcon">
         <item name="android:layout_centerHorizontal">false</item>
         <item name="android:layout_alignParentStart">true</item>
+        <item name="android:layout_marginStart">@dimen/suggestion_card_icon_side_margin</item>
+        <item name="android:layout_marginEnd">@dimen/suggestion_card_icon_side_margin</item>
+    </style>
+
+    <style name="SuggestionCardButton">
+        <item name="android:layout_gravity">start</item>
+        <item name="android:layout_marginStart">@dimen/suggestion_card_button_side_margin</item>
+        <item name="android:layout_marginEnd">@dimen/suggestion_card_button_side_margin</item>
+        <item name="android:layout_marginTop">@dimen/suggestion_card_button_top_margin</item>
+        <item name="android:layout_marginBottom">@dimen/suggestion_card_button_bottom_margin</item>
     </style>
 
     <style name="TextAppearance.SuggestionTitle"
diff --git a/res/xml/smart_battery_detail.xml b/res/xml/smart_battery_detail.xml
index e7fb9f7..e1246ed 100644
--- a/res/xml/smart_battery_detail.xml
+++ b/res/xml/smart_battery_detail.xml
@@ -21,18 +21,16 @@
     android:key="smart_battery_detail"
     android:title="@string/smart_battery_manager_title">
 
-    <!-- TODO(b/71722498): Add header back, otherwise also remove smart_battery_header
-    <com.android.settings.applications.LayoutPreference
-        android:key="header_view"
-        android:layout="@layout/smart_battery_header"
-        android:selectable="false"
-        android:order="-10000"/>
-     -->
+    <com.android.settings.widget.VideoPreference
+        android:key="auto_awesome_battery"
+        settings:animation="@raw/auto_awesome_battery"
+        settings:preview="@drawable/auto_awesome_battery"/>
 
     <SwitchPreference
         android:key="smart_battery"
         android:title="@string/smart_battery_title"
-        android:summary="@string/smart_battery_summary"/>
+        android:summary="@string/smart_battery_summary"
+        settings:allowDividerAbove="true"/>
 
     <SwitchPreference
         android:key="auto_restriction"
diff --git a/res/xml/sound_settings.xml b/res/xml/sound_settings.xml
index 23936a7..7fd3709 100644
--- a/res/xml/sound_settings.xml
+++ b/res/xml/sound_settings.xml
@@ -27,6 +27,7 @@
         android:key="media_volume"
         android:icon="@*android:drawable/ic_audio_media"
         android:title="@string/media_volume_option_title"
+        settings:controller="com.android.settings.notification.MediaVolumePreferenceController"
         android:order="-170"/>
 
     <!-- Alarm volume -->
@@ -34,6 +35,7 @@
         android:key="alarm_volume"
         android:icon="@*android:drawable/ic_audio_alarm"
         android:title="@string/alarm_volume_option_title"
+        settings:controller="com.android.settings.notification.AlarmVolumePreferenceController"
         android:order="-160"/>
 
     <!-- Ring volume -->
@@ -41,6 +43,7 @@
         android:key="ring_volume"
         android:icon="@*android:drawable/ic_audio_ring_notif"
         android:title="@string/ring_volume_option_title"
+        settings:controller="com.android.settings.notification.RingVolumePreferenceController"
         android:order="-150"/>
 
     <!-- Notification volume -->
@@ -48,6 +51,7 @@
         android:key="notification_volume"
         android:icon="@*android:drawable/ic_audio_ring_notif"
         android:title="@string/notification_volume_option_title"
+        settings:controller="com.android.settings.notification.NotificationVolumePreferenceController"
         android:order="-140"/>
 
     <!-- Also vibrate for calls -->
diff --git a/src/com/android/settings/SettingsDumpService.java b/src/com/android/settings/SettingsDumpService.java
index 67a8f50..07ea73e 100644
--- a/src/com/android/settings/SettingsDumpService.java
+++ b/src/com/android/settings/SettingsDumpService.java
@@ -15,7 +15,9 @@
 package com.android.settings;
 
 import android.app.Service;
+import android.content.Context;
 import android.content.Intent;
+import android.content.SharedPreferences;
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.net.ConnectivityManager;
@@ -27,9 +29,12 @@
 import android.telephony.SubscriptionInfo;
 import android.telephony.SubscriptionManager;
 import android.telephony.TelephonyManager;
+
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.settings.applications.ProcStatsData;
+import com.android.settings.fuelgauge.batterytip.AnomalyConfigJobService;
 import com.android.settingslib.net.DataUsageController;
+
 import org.json.JSONArray;
 import org.json.JSONException;
 import org.json.JSONObject;
@@ -39,12 +44,20 @@
 import java.io.PrintWriter;
 
 public class SettingsDumpService extends Service {
-    @VisibleForTesting static final String KEY_SERVICE = "service";
-    @VisibleForTesting static final String KEY_STORAGE = "storage";
-    @VisibleForTesting static final String KEY_DATAUSAGE = "datausage";
-    @VisibleForTesting static final String KEY_MEMORY = "memory";
-    @VisibleForTesting static final String KEY_DEFAULT_BROWSER_APP = "default_browser_app";
-    @VisibleForTesting static final Intent BROWSER_INTENT =
+    @VisibleForTesting
+    static final String KEY_SERVICE = "service";
+    @VisibleForTesting
+    static final String KEY_STORAGE = "storage";
+    @VisibleForTesting
+    static final String KEY_DATAUSAGE = "datausage";
+    @VisibleForTesting
+    static final String KEY_MEMORY = "memory";
+    @VisibleForTesting
+    static final String KEY_DEFAULT_BROWSER_APP = "default_browser_app";
+    @VisibleForTesting
+    static final String KEY_ANOMALY_DETECTION = "anomaly_detection";
+    @VisibleForTesting
+    static final Intent BROWSER_INTENT =
             new Intent("android.intent.action.VIEW", Uri.parse("http://"));
 
     @Override
@@ -62,6 +75,7 @@
             dump.put(KEY_DATAUSAGE, dumpDataUsage());
             dump.put(KEY_MEMORY, dumpMemory());
             dump.put(KEY_DEFAULT_BROWSER_APP, dumpDefaultBrowser());
+            dump.put(KEY_ANOMALY_DETECTION, dumpAnomalyDetection());
         } catch (Exception e) {
             e.printStackTrace();
         }
@@ -151,4 +165,18 @@
             return resolveInfo.activityInfo.packageName;
         }
     }
+
+    @VisibleForTesting
+    JSONObject dumpAnomalyDetection() throws JSONException {
+        final JSONObject obj = new JSONObject();
+        final SharedPreferences sharedPreferences = getSharedPreferences(
+                AnomalyConfigJobService.PREF_DB,
+                Context.MODE_PRIVATE);
+        final int currentVersion = sharedPreferences.getInt(
+                AnomalyConfigJobService.KEY_ANOMALY_CONFIG_VERSION,
+                0 /* defValue */);
+        obj.put("anomaly_config_version", String.valueOf(currentVersion));
+
+        return obj;
+    }
 }
diff --git a/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java b/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java
index 05cb46b..44d5b79 100644
--- a/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java
+++ b/src/com/android/settings/accessibility/MagnificationPreferenceFragment.java
@@ -25,20 +25,15 @@
 import android.provider.Settings;
 import android.support.v7.preference.Preference;
 import android.text.TextUtils;
-import android.view.View;
 import android.view.accessibility.AccessibilityManager;
 
 import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
-import com.android.settings.dashboard.DashboardFragment;
 import com.android.settings.R;
-import com.android.settings.SettingsPreferenceFragment;
+import com.android.settings.dashboard.DashboardFragment;
 import com.android.settings.search.BaseSearchIndexProvider;
 import com.android.settings.search.Indexable;
-import com.android.settingslib.core.AbstractPreferenceController;
 
-import java.util.ArrayList;
 import java.util.Arrays;
-import java.util.Collections;
 import java.util.List;
 
 public final class MagnificationPreferenceFragment extends DashboardFragment {
@@ -144,13 +139,14 @@
                 @Override
                 public List<SearchIndexableResource> getXmlResourcesToIndex(Context context,
                         boolean enabled) {
-                    if (isApplicable(context.getResources())) {
-                        final SearchIndexableResource sir = new SearchIndexableResource(context);
-                        sir.xmlResId = R.xml.accessibility_magnification_settings;
-                        return Arrays.asList(sir);
-                    } else {
-                        return Collections.emptyList();
-                    }
+                    final SearchIndexableResource sir = new SearchIndexableResource(context);
+                    sir.xmlResId = R.xml.accessibility_magnification_settings;
+                    return Arrays.asList(sir);
+                }
+
+                @Override
+                protected boolean isPageSearchEnabled(Context context) {
+                    return isApplicable(context.getResources());
                 }
 
                 @Override
diff --git a/src/com/android/settings/display/ColorModePreferenceFragment.java b/src/com/android/settings/display/ColorModePreferenceFragment.java
index 5f5445b..6e4bd1f 100644
--- a/src/com/android/settings/display/ColorModePreferenceFragment.java
+++ b/src/com/android/settings/display/ColorModePreferenceFragment.java
@@ -16,6 +16,7 @@
 import android.content.Context;
 import android.graphics.drawable.Drawable;
 import android.support.annotation.VisibleForTesting;
+import android.support.v7.preference.Preference;
 import android.support.v7.preference.PreferenceScreen;
 
 import com.android.internal.app.ColorDisplayController;
@@ -24,13 +25,15 @@
 import com.android.settings.applications.LayoutPreference;
 import com.android.settings.R;
 import com.android.settings.widget.RadioButtonPickerFragment;
+import com.android.settings.widget.RadioButtonPreference;
 import com.android.settingslib.widget.CandidateInfo;
 
 import java.util.Arrays;
 import java.util.List;
 
 @SuppressWarnings("WeakerAccess")
-public class ColorModePreferenceFragment extends RadioButtonPickerFragment {
+public class ColorModePreferenceFragment extends RadioButtonPickerFragment
+        implements ColorDisplayController.Callback {
 
     @VisibleForTesting
     static final String KEY_COLOR_MODE_NATURAL = "color_mode_natural";
@@ -48,6 +51,16 @@
     public void onAttach(Context context) {
         super.onAttach(context);
         mController = new ColorDisplayController(context);
+        mController.setListener(this);
+    }
+
+    @Override
+    public void onDetach() {
+        super.onDetach();
+        if (mController != null) {
+            mController.setListener(null);
+            mController = null;
+        }
     }
 
     @Override
@@ -71,15 +84,16 @@
     @Override
     protected List<? extends CandidateInfo> getCandidates() {
         Context c = getContext();
+        final boolean enabled = !mController.getAccessibilityTransformActivated();
         return Arrays.asList(
-            new ColorModeCandidateInfo(c.getString(R.string.color_mode_option_natural),
-                    KEY_COLOR_MODE_NATURAL),
-            new ColorModeCandidateInfo(c.getString(R.string.color_mode_option_boosted),
-                    KEY_COLOR_MODE_BOOSTED),
-            new ColorModeCandidateInfo(c.getString(R.string.color_mode_option_saturated),
-                    KEY_COLOR_MODE_SATURATED),
-            new ColorModeCandidateInfo(c.getString(R.string.color_mode_option_automatic),
-                    KEY_COLOR_MODE_AUTOMATIC)
+            new ColorModeCandidateInfo(c.getText(R.string.color_mode_option_natural),
+                    KEY_COLOR_MODE_NATURAL, enabled),
+            new ColorModeCandidateInfo(c.getText(R.string.color_mode_option_boosted),
+                    KEY_COLOR_MODE_BOOSTED, enabled),
+            new ColorModeCandidateInfo(c.getText(R.string.color_mode_option_saturated),
+                    KEY_COLOR_MODE_SATURATED, enabled),
+            new ColorModeCandidateInfo(c.getText(R.string.color_mode_option_automatic),
+                    KEY_COLOR_MODE_AUTOMATIC, enabled)
         );
     }
 
@@ -120,8 +134,8 @@
         private final CharSequence mLabel;
         private final String mKey;
 
-        ColorModeCandidateInfo(CharSequence label, String key) {
-            super(true);
+        ColorModeCandidateInfo(CharSequence label, String key, boolean enabled) {
+            super(enabled);
             mLabel = label;
             mKey = key;
         }
@@ -142,4 +156,18 @@
         }
     }
 
+    @Override
+    public void onAccessibilityTransformChanged(boolean state) {
+        // Disable controls when a11y transforms are enabled, and vice versa
+        final PreferenceScreen screen = getPreferenceScreen();
+        if (screen != null) {
+            final int count = screen.getPreferenceCount();
+            for (int i = 0; i < count; i++) {
+                final Preference pref = screen.getPreference(i);
+                if (pref instanceof RadioButtonPreference) {
+                    pref.setEnabled(!state);
+                }
+            }
+        }
+    }
 }
diff --git a/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelper.java b/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelper.java
index ff43e6e..1c1d2f3 100644
--- a/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelper.java
+++ b/src/com/android/settings/enterprise/ActionDisabledByAdminDialogHelper.java
@@ -72,7 +72,7 @@
                 mRestriction);
         return builder
             .setPositiveButton(R.string.okay, null)
-            .setNeutralButton(R.string.admin_more_details,
+            .setNeutralButton(R.string.learn_more,
                     (dialog, which) -> {
                         showAdminPolicies(mEnforcedAdmin, mActivity);
                         mActivity.finish();
diff --git a/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java b/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java
index eead69f..ab985f0 100644
--- a/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java
+++ b/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImpl.java
@@ -107,7 +107,7 @@
             disclosure.append(mResources.getString(R.string.do_disclosure_generic));
         }
         disclosure.append(mResources.getString(R.string.do_disclosure_learn_more_separator));
-        disclosure.append(mResources.getString(R.string.do_disclosure_learn_more),
+        disclosure.append(mResources.getString(R.string.learn_more),
                 new EnterprisePrivacySpan(mContext), 0);
         return disclosure;
     }
diff --git a/src/com/android/settings/fuelgauge/BatteryEntry.java b/src/com/android/settings/fuelgauge/BatteryEntry.java
index 1733a6e..a93d522 100644
--- a/src/com/android/settings/fuelgauge/BatteryEntry.java
+++ b/src/com/android/settings/fuelgauge/BatteryEntry.java
@@ -209,6 +209,10 @@
                 name = context.getResources().getString(R.string.power_camera);
                 iconId = R.drawable.ic_settings_camera;
                 break;
+            case AMBIENT_DISPLAY:
+                name = context.getResources().getString(R.string.ambient_display_screen_title);
+                iconId = R.drawable.ic_settings_aod;
+                break;
         }
         if (iconId > 0) {
             icon = context.getDrawable(iconId);
diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java
index 98eb23e..5686d6e 100644
--- a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java
+++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigJobService.java
@@ -39,9 +39,8 @@
 public class AnomalyConfigJobService extends JobService {
     private static final String TAG = "AnomalyConfigJobService";
 
-    @VisibleForTesting
-    static final String PREF_DB = "anomaly_pref";
-    private static final String KEY_ANOMALY_CONFIG_VERSION = "anomaly_config_version";
+    public static final String PREF_DB = "anomaly_pref";
+    public static final String KEY_ANOMALY_CONFIG_VERSION = "anomaly_config_version";
     private static final int DEFAULT_VERSION = 0;
 
     @VisibleForTesting
diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigReceiver.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigReceiver.java
index dcacaae..bad1c11 100644
--- a/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigReceiver.java
+++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyConfigReceiver.java
@@ -48,13 +48,4 @@
             }
         }
     }
-
-    @VisibleForTesting
-    void uploadPendingIntent(StatsManager statsManager, PendingIntent pendingIntent) {
-        Log.i(TAG, "Upload PendingIntent to StatsManager. configKey: "
-                + StatsManagerConfig.ANOMALY_CONFIG_KEY + " subId: "
-                + StatsManagerConfig.SUBSCRIBER_ID);
-        statsManager.setBroadcastSubscriber(StatsManagerConfig.ANOMALY_CONFIG_KEY,
-                StatsManagerConfig.SUBSCRIBER_ID, pendingIntent);
-    }
 }
diff --git a/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java b/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java
index 451b402..7720dcc 100644
--- a/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java
+++ b/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobService.java
@@ -30,6 +30,7 @@
 import android.content.ContentResolver;
 import android.content.Context;
 import android.content.Intent;
+import android.content.pm.PackageManager;
 import android.os.Bundle;
 import android.os.Process;
 import android.os.StatsDimensionsValue;
@@ -58,9 +59,11 @@
 /** A JobService to store anomaly data to anomaly database */
 public class AnomalyDetectionJobService extends JobService {
     private static final String TAG = "AnomalyDetectionService";
-    private static final int UID_NULL = 0;
-    private static final int STATSD_UID_FILED = 1;
     private static final int ON = 1;
+    @VisibleForTesting
+    static final int UID_NULL = -1;
+    @VisibleForTesting
+    static final int STATSD_UID_FILED = 1;
 
     @VisibleForTesting
     static final long MAX_DELAY_MS = TimeUnit.MINUTES.toMillis(30);
@@ -131,6 +134,7 @@
                 StatsManager.EXTRA_STATS_BROADCAST_SUBSCRIBER_COOKIES);
         final AnomalyInfo anomalyInfo = new AnomalyInfo(
                 !ArrayUtils.isEmpty(cookies) ? cookies.get(0) : "");
+        final PackageManager packageManager = context.getPackageManager();
         Log.i(TAG, "Extra stats value: " + intentDimsValue.toString());
 
         try {
@@ -141,8 +145,9 @@
                     : Settings.Global.getInt(contentResolver,
                             Settings.Global.APP_AUTO_RESTRICTION_ENABLED, ON) == ON;
             final String packageName = batteryUtils.getPackageName(uid);
-            if (!powerWhitelistBackend.isSysWhitelistedExceptIdle(packageName)
-                    && !isSystemUid(uid)) {
+            if (uid != UID_NULL && !isSystemUid(uid)
+                    && !powerWhitelistBackend.isSysWhitelistedExceptIdle(
+                    packageManager.getPackagesForUid(uid))) {
                 boolean anomalyDetected = true;
                 if (anomalyInfo.anomalyType
                         == StatsManagerConfig.AnomalyType.EXCESSIVE_BACKGROUND_SERVICE) {
@@ -189,7 +194,6 @@
      */
     @VisibleForTesting
     int extractUidFromStatsDimensionsValue(StatsDimensionsValue statsDimensionsValue) {
-        //TODO(b/73172999): Add robo test for this method
         if (statsDimensionsValue == null) {
             return UID_NULL;
         }
diff --git a/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceController.java b/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceController.java
index bad626a..03032c5 100644
--- a/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceController.java
+++ b/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceController.java
@@ -24,6 +24,7 @@
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.settings.accounts.AccountRestrictionHelper;
 import com.android.settings.core.PreferenceControllerMixin;
+import com.android.settings.core.SliderPreferenceController;
 import com.android.settingslib.RestrictedPreference;
 import com.android.settingslib.core.AbstractPreferenceController;
 
@@ -32,17 +33,18 @@
  * restriction
  */
 public abstract class AdjustVolumeRestrictedPreferenceController extends
-        AbstractPreferenceController implements PreferenceControllerMixin {
+        SliderPreferenceController implements PreferenceControllerMixin {
 
     private AccountRestrictionHelper mHelper;
 
-    public AdjustVolumeRestrictedPreferenceController(Context context) {
-        this(context, new AccountRestrictionHelper(context));
+    public AdjustVolumeRestrictedPreferenceController(Context context, String key) {
+        this(context, new AccountRestrictionHelper(context), key);
     }
 
     @VisibleForTesting
-    AdjustVolumeRestrictedPreferenceController(Context context, AccountRestrictionHelper helper) {
-        super(context);
+    AdjustVolumeRestrictedPreferenceController(Context context, AccountRestrictionHelper helper,
+            String key) {
+        super(context, key);
         mHelper = helper;
     }
 
diff --git a/src/com/android/settings/notification/AlarmVolumePreferenceController.java b/src/com/android/settings/notification/AlarmVolumePreferenceController.java
index c9b283b..0900e3c 100644
--- a/src/com/android/settings/notification/AlarmVolumePreferenceController.java
+++ b/src/com/android/settings/notification/AlarmVolumePreferenceController.java
@@ -20,32 +20,21 @@
 import android.media.AudioManager;
 
 import com.android.internal.annotations.VisibleForTesting;
-import com.android.settings.notification.VolumeSeekBarPreference.Callback;
 import com.android.settings.R;
-import com.android.settingslib.core.lifecycle.Lifecycle;
 
 public class AlarmVolumePreferenceController extends
     VolumeSeekBarPreferenceController {
 
     private static final String KEY_ALARM_VOLUME = "alarm_volume";
-    private AudioHelper mHelper;
 
-    public AlarmVolumePreferenceController(Context context, Callback callback,
-        Lifecycle lifecycle) {
-        this(context, callback, lifecycle, new AudioHelper(context));
-    }
-
-    @VisibleForTesting
-    AlarmVolumePreferenceController(Context context, Callback callback, Lifecycle lifecycle,
-        AudioHelper helper) {
-        super(context, callback, lifecycle);
-        mHelper = helper;
+    public AlarmVolumePreferenceController(Context context) {
+        super(context, KEY_ALARM_VOLUME);
     }
 
     @Override
-    public boolean isAvailable() {
+    public int getAvailabilityStatus() {
         return mContext.getResources().getBoolean(R.bool.config_show_alarm_volume)
-                && !mHelper.isSingleVolume();
+                && !mHelper.isSingleVolume() ? AVAILABLE : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -62,5 +51,4 @@
     public int getMuteIcon() {
         return com.android.internal.R.drawable.ic_audio_alarm_mute;
     }
-
 }
diff --git a/src/com/android/settings/notification/AudioHelper.java b/src/com/android/settings/notification/AudioHelper.java
index 51ba74c..5f745c8 100644
--- a/src/com/android/settings/notification/AudioHelper.java
+++ b/src/com/android/settings/notification/AudioHelper.java
@@ -18,6 +18,7 @@
 
 import android.annotation.UserIdInt;
 import android.content.Context;
+import android.media.AudioManager;
 import android.media.AudioSystem;
 import android.os.UserHandle;
 import android.os.UserManager;
@@ -29,9 +30,11 @@
 public class AudioHelper {
 
     private Context mContext;
+    private AudioManager mAudioManager;
 
     public AudioHelper(Context context) {
         mContext = context;
+        mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
     }
 
     public boolean isSingleVolume() {
@@ -49,4 +52,25 @@
     public Context createPackageContextAsUser(@UserIdInt int profileId) {
         return Utils.createPackageContextAsUser(mContext, profileId);
     }
+
+    public int getRingerModeInternal() {
+        return mAudioManager.getRingerModeInternal();
+    }
+
+    public int getLastAudibleStreamVolume(int stream) {
+        return mAudioManager.getLastAudibleStreamVolume(stream);
+    }
+
+    public int getStreamVolume(int stream) {
+        return mAudioManager.getStreamVolume(stream);
+    }
+
+    public boolean setStreamVolume(int stream, int volume) {
+        mAudioManager.setStreamVolume(stream, volume, 0);
+        return true;
+    }
+
+    public int getMaxVolume(int stream) {
+        return mAudioManager.getStreamMaxVolume(stream);
+    }
 }
diff --git a/src/com/android/settings/notification/MediaVolumePreferenceController.java b/src/com/android/settings/notification/MediaVolumePreferenceController.java
index 381135e..8f0a7f9 100644
--- a/src/com/android/settings/notification/MediaVolumePreferenceController.java
+++ b/src/com/android/settings/notification/MediaVolumePreferenceController.java
@@ -27,13 +27,15 @@
 
     private static final String KEY_MEDIA_VOLUME = "media_volume";
 
-    public MediaVolumePreferenceController(Context context, Callback callback, Lifecycle lifecycle) {
-        super(context, callback, lifecycle);
+    public MediaVolumePreferenceController(Context context) {
+        super(context, KEY_MEDIA_VOLUME);
     }
 
     @Override
-    public boolean isAvailable() {
-        return mContext.getResources().getBoolean(R.bool.config_show_media_volume);
+    public int getAvailabilityStatus() {
+        return mContext.getResources().getBoolean(R.bool.config_show_media_volume)
+                ? AVAILABLE
+                : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -50,5 +52,4 @@
     public int getMuteIcon() {
         return com.android.internal.R.drawable.ic_audio_media_mute;
     }
-
 }
diff --git a/src/com/android/settings/notification/NotificationVolumePreferenceController.java b/src/com/android/settings/notification/NotificationVolumePreferenceController.java
index 4024f9f..8e7171d 100644
--- a/src/com/android/settings/notification/NotificationVolumePreferenceController.java
+++ b/src/com/android/settings/notification/NotificationVolumePreferenceController.java
@@ -22,32 +22,21 @@
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.settings.R;
 import com.android.settings.Utils;
-import com.android.settings.notification.VolumeSeekBarPreference.Callback;
-import com.android.settingslib.core.lifecycle.Lifecycle;
 
 public class NotificationVolumePreferenceController extends
     RingVolumePreferenceController {
 
     private static final String KEY_NOTIFICATION_VOLUME = "notification_volume";
-    private AudioHelper mHelper;
 
-    public NotificationVolumePreferenceController(Context context, Callback callback,
-        Lifecycle lifecycle) {
-        this(context, callback, lifecycle, new AudioHelper(context));
+    public NotificationVolumePreferenceController(Context context) {
+        super(context, KEY_NOTIFICATION_VOLUME);
     }
 
-    @VisibleForTesting
-    NotificationVolumePreferenceController(Context context,
-        Callback callback, Lifecycle lifecycle, AudioHelper helper) {
-        super(context, callback, lifecycle);
-        mHelper = helper;
-    }
-
-
     @Override
-    public boolean isAvailable() {
+    public int getAvailabilityStatus() {
         return mContext.getResources().getBoolean(R.bool.config_show_notification_volume)
-                && !Utils.isVoiceCapable(mContext) && !mHelper.isSingleVolume();
+                && !Utils.isVoiceCapable(mContext) && !mHelper.isSingleVolume()
+                ? AVAILABLE : DISABLED_UNSUPPORTED;
     }
 
     @Override
diff --git a/src/com/android/settings/notification/RingVolumePreferenceController.java b/src/com/android/settings/notification/RingVolumePreferenceController.java
index 5acca04..ea071fa 100644
--- a/src/com/android/settings/notification/RingVolumePreferenceController.java
+++ b/src/com/android/settings/notification/RingVolumePreferenceController.java
@@ -31,8 +31,6 @@
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.settings.R;
 import com.android.settings.Utils;
-import com.android.settings.notification.VolumeSeekBarPreference.Callback;
-import com.android.settingslib.core.lifecycle.Lifecycle;
 
 import java.util.Objects;
 
@@ -41,24 +39,18 @@
     private static final String TAG = "RingVolumeController";
     private static final String KEY_RING_VOLUME = "ring_volume";
 
-    private AudioManager mAudioManager;
     private Vibrator mVibrator;
     private int mRingerMode = -1;
     private ComponentName mSuppressor;
     private final RingReceiver mReceiver = new RingReceiver();
     private final H mHandler = new H();
-    private AudioHelper mHelper;
 
-    public RingVolumePreferenceController(Context context, Callback callback, Lifecycle lifecycle) {
-        this(context, callback, lifecycle, new AudioHelper(context));
+    public RingVolumePreferenceController(Context context) {
+        this(context, KEY_RING_VOLUME);
     }
 
-    @VisibleForTesting
-    RingVolumePreferenceController(Context context, Callback callback, Lifecycle lifecycle,
-        AudioHelper helper) {
-        super(context, callback, lifecycle);
-        mHelper = helper;
-        mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
+    public RingVolumePreferenceController(Context context, String key) {
+        super(context, key);
         mVibrator = (Vibrator) mContext.getSystemService(Context.VIBRATOR_SERVICE);
         if (mVibrator != null && !mVibrator.hasVibrator()) {
             mVibrator = null;
@@ -86,8 +78,9 @@
     }
 
     @Override
-    public boolean isAvailable() {
-        return Utils.isVoiceCapable(mContext) && !mHelper.isSingleVolume();
+    public int getAvailabilityStatus() {
+        return Utils.isVoiceCapable(mContext) && !mHelper.isSingleVolume()
+                ? AVAILABLE : DISABLED_UNSUPPORTED;
     }
 
     @Override
@@ -101,7 +94,7 @@
     }
 
     private void updateRingerMode() {
-        final int ringerMode = mAudioManager.getRingerModeInternal();
+        final int ringerMode = mHelper.getRingerModeInternal();
         if (mRingerMode == ringerMode) return;
         mRingerMode = ringerMode;
         updatePreferenceIcon();
@@ -109,7 +102,7 @@
 
     private boolean wasRingerModeVibrate() {
         return mVibrator != null && mRingerMode == AudioManager.RINGER_MODE_SILENT
-            && mAudioManager.getLastAudibleStreamVolume(AudioManager.STREAM_RING) == 0;
+            && mHelper.getLastAudibleStreamVolume(getAudioStream()) == 0;
     }
 
     private void updateEffectsSuppressor() {
diff --git a/src/com/android/settings/notification/SoundSettings.java b/src/com/android/settings/notification/SoundSettings.java
index a7ba707..4c9ee38 100644
--- a/src/com/android/settings/notification/SoundSettings.java
+++ b/src/com/android/settings/notification/SoundSettings.java
@@ -124,7 +124,7 @@
 
     @Override
     protected List<AbstractPreferenceController> createPreferenceControllers(Context context) {
-        return buildPreferenceControllers(context, this, mVolumeCallback, getLifecycle());
+        return buildPreferenceControllers(context, this, getLifecycle());
     }
 
     @Override
@@ -143,6 +143,15 @@
         }
     }
 
+    @Override
+    public void onAttach(Context context) {
+        super.onAttach(context);
+        use(AlarmVolumePreferenceController.class).setCallback(mVolumeCallback);
+        use(MediaVolumePreferenceController.class).setCallback(mVolumeCallback);
+        use(RingVolumePreferenceController.class).setCallback(mVolumeCallback);
+        use(NotificationVolumePreferenceController.class).setCallback(mVolumeCallback);
+    }
+
     // === Volumes ===
 
     final class VolumePreferenceCallback implements VolumeSeekBarPreference.Callback {
@@ -176,18 +185,12 @@
     }
 
     private static List<AbstractPreferenceController> buildPreferenceControllers(Context context,
-            SoundSettings fragment, VolumeSeekBarPreference.Callback callback,
-            Lifecycle lifecycle) {
+            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 ===
-        controllers.add(new AlarmVolumePreferenceController(context, callback, lifecycle));
-        controllers.add(new MediaVolumePreferenceController(context, callback, lifecycle));
-        controllers.add(
-                new NotificationVolumePreferenceController(context, callback, lifecycle));
-        controllers.add(new RingVolumePreferenceController(context, callback, lifecycle));
+        // Volumes are added via xml
 
         // === Phone & notification ringtone ===
         controllers.add(new PhoneRingtonePreferenceController(context));
@@ -257,7 +260,7 @@
                 public List<AbstractPreferenceController> createPreferenceControllers(
                         Context context) {
                     return buildPreferenceControllers(context, null /* fragment */,
-                            null /* callback */, null /* lifecycle */);
+                            null /* lifecycle */);
                 }
 
                 @Override
diff --git a/src/com/android/settings/notification/VolumeSeekBarPreferenceController.java b/src/com/android/settings/notification/VolumeSeekBarPreferenceController.java
index 501cedc..74e801e 100644
--- a/src/com/android/settings/notification/VolumeSeekBarPreferenceController.java
+++ b/src/com/android/settings/notification/VolumeSeekBarPreferenceController.java
@@ -16,31 +16,37 @@
 
 package com.android.settings.notification;
 
+import android.arch.lifecycle.LifecycleObserver;
+import android.arch.lifecycle.OnLifecycleEvent;
 import android.content.Context;
 import android.support.v7.preference.PreferenceScreen;
 
+import com.android.internal.annotations.VisibleForTesting;
 import com.android.settings.notification.VolumeSeekBarPreference.Callback;
 import com.android.settingslib.core.lifecycle.Lifecycle;
-import com.android.settingslib.core.lifecycle.LifecycleObserver;
-import com.android.settingslib.core.lifecycle.events.OnPause;
-import com.android.settingslib.core.lifecycle.events.OnResume;
 
 /**
  * Base class for preference controller that handles VolumeSeekBarPreference
  */
 public abstract class VolumeSeekBarPreferenceController extends
-        AdjustVolumeRestrictedPreferenceController implements LifecycleObserver, OnResume, OnPause {
+        AdjustVolumeRestrictedPreferenceController implements LifecycleObserver {
 
     protected VolumeSeekBarPreference mPreference;
     protected VolumeSeekBarPreference.Callback mVolumePreferenceCallback;
+    protected AudioHelper mHelper;
 
-    public VolumeSeekBarPreferenceController(Context context, Callback callback,
-            Lifecycle lifecycle) {
-        super(context);
+    public VolumeSeekBarPreferenceController(Context context, String key) {
+        super(context, key);
+        setAudioHelper(new AudioHelper(context));
+    }
+
+    @VisibleForTesting
+    void setAudioHelper(AudioHelper helper) {
+        mHelper = helper;
+    }
+
+    public void setCallback(Callback callback) {
         mVolumePreferenceCallback = callback;
-        if (lifecycle != null) {
-            lifecycle.addObserver(this);
-        }
     }
 
     @Override
@@ -54,20 +60,44 @@
         }
     }
 
-    @Override
+    @OnLifecycleEvent(Lifecycle.Event.ON_RESUME)
     public void onResume() {
         if (mPreference != null) {
             mPreference.onActivityResume();
         }
     }
 
-    @Override
+    @OnLifecycleEvent(Lifecycle.Event.ON_PAUSE)
     public void onPause() {
         if (mPreference != null) {
             mPreference.onActivityPause();
         }
     }
 
+    @Override
+    public int getSliderPosition() {
+        if (mPreference != null) {
+            return mPreference.getProgress();
+        }
+        return mHelper.getStreamVolume(getAudioStream());
+    }
+
+    @Override
+    public boolean setSliderPosition(int position) {
+        if (mPreference != null) {
+            mPreference.setProgress(position);
+        }
+        return mHelper.setStreamVolume(getAudioStream(), position);
+    }
+
+    @Override
+    public int getMaxSteps() {
+        if (mPreference != null) {
+            return mPreference.getMax();
+        }
+        return mHelper.getMaxVolume(getAudioStream());
+    }
+
     protected abstract int getAudioStream();
 
     protected abstract int getMuteIcon();
diff --git a/src/com/android/settings/notification/ZenModePreferenceController.java b/src/com/android/settings/notification/ZenModePreferenceController.java
index 5b59000..5c9c33b 100644
--- a/src/com/android/settings/notification/ZenModePreferenceController.java
+++ b/src/com/android/settings/notification/ZenModePreferenceController.java
@@ -27,13 +27,15 @@
 import android.support.v7.preference.PreferenceScreen;
 import android.util.Slog;
 
+import com.android.settings.core.PreferenceControllerMixin;
+import com.android.settingslib.core.AbstractPreferenceController;
 import com.android.settingslib.core.lifecycle.Lifecycle;
 import com.android.settingslib.core.lifecycle.LifecycleObserver;
 import com.android.settingslib.core.lifecycle.events.OnPause;
 import com.android.settingslib.core.lifecycle.events.OnResume;
 
-public class ZenModePreferenceController extends AdjustVolumeRestrictedPreferenceController
-        implements LifecycleObserver, OnResume, OnPause {
+public class ZenModePreferenceController extends AbstractPreferenceController
+        implements LifecycleObserver, OnResume, OnPause, PreferenceControllerMixin {
 
     private final String mKey;
     private SettingObserver mSettingObserver;
diff --git a/src/com/android/settings/slices/SliceBuilderUtils.java b/src/com/android/settings/slices/SliceBuilderUtils.java
index 3e062c8..c54d138 100644
--- a/src/com/android/settings/slices/SliceBuilderUtils.java
+++ b/src/com/android/settings/slices/SliceBuilderUtils.java
@@ -253,11 +253,7 @@
     @VisibleForTesting
     static CharSequence getSubtitleText(Context context, AbstractPreferenceController controller,
             SliceData sliceData) {
-        CharSequence summaryText = sliceData.getSummary();
-        if (isValidSummary(context, summaryText)) {
-            return summaryText;
-        }
-
+        CharSequence summaryText;
         if (controller != null) {
             summaryText = controller.getSummary();
 
@@ -266,7 +262,12 @@
             }
         }
 
-        return sliceData.getScreenTitle();
+        summaryText = sliceData.getSummary();
+        if (isValidSummary(context, summaryText)) {
+            return summaryText;
+        }
+
+        return "";
     }
 
     private static boolean isValidSummary(Context context, CharSequence summary) {
diff --git a/src/com/android/settings/widget/AspectRatioFrameLayout.java b/src/com/android/settings/widget/AspectRatioFrameLayout.java
index bb4c28b..52dea0f 100644
--- a/src/com/android/settings/widget/AspectRatioFrameLayout.java
+++ b/src/com/android/settings/widget/AspectRatioFrameLayout.java
@@ -16,6 +16,7 @@
 
 import android.content.Context;
 import android.content.res.TypedArray;
+import android.support.annotation.VisibleForTesting;
 import android.util.AttributeSet;
 import android.widget.FrameLayout;
 
@@ -30,7 +31,8 @@
 
     private static final float ASPECT_RATIO_CHANGE_THREASHOLD = 0.01f;
 
-    private float mAspectRatio = 1.0f;
+    @VisibleForTesting
+    float mAspectRatio = 1.0f;
 
     public AspectRatioFrameLayout(Context context) {
         this(context, null);
@@ -51,6 +53,10 @@
         }
     }
 
+    public void setAspectRatio(float aspectRadio) {
+        mAspectRatio = aspectRadio;
+    }
+
     @Override
     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
         super.onMeasure(widthMeasureSpec, heightMeasureSpec);
@@ -65,11 +71,9 @@
             // Close enough, skip.
             return;
         }
-        if (aspectRatioDiff > 0) {
-            width = (int) (height * mAspectRatio);
-        } else {
-            height = (int) (width / mAspectRatio);
-        }
+
+        width = (int) (height * mAspectRatio);
+
         super.onMeasure(MeasureSpec.makeMeasureSpec(width, MeasureSpec.EXACTLY),
                 MeasureSpec.makeMeasureSpec(height, MeasureSpec.EXACTLY));
     }
diff --git a/src/com/android/settings/widget/VideoPreference.java b/src/com/android/settings/widget/VideoPreference.java
index a3ac6a3..03f8f0b 100644
--- a/src/com/android/settings/widget/VideoPreference.java
+++ b/src/com/android/settings/widget/VideoPreference.java
@@ -22,6 +22,7 @@
 import android.graphics.SurfaceTexture;
 import android.media.MediaPlayer;
 import android.net.Uri;
+import android.support.annotation.VisibleForTesting;
 import android.support.v7.preference.Preference;
 import android.support.v7.preference.PreferenceViewHolder;
 import android.util.AttributeSet;
@@ -42,10 +43,13 @@
     private final Context mContext;
 
     private Uri mVideoPath;
-    private MediaPlayer mMediaPlayer;
-    private boolean mAnimationAvailable;
+    @VisibleForTesting
+    MediaPlayer mMediaPlayer;
+    @VisibleForTesting
+    boolean mAnimationAvailable;
     private boolean mVideoReady;
     private boolean mVideoPaused;
+    private float mAspectRadio = 1.0f;
     private int mPreviewResource;
 
     public VideoPreference(Context context, AttributeSet attrs) {
@@ -73,6 +77,7 @@
 
                 mMediaPlayer.setOnPreparedListener(mediaPlayer -> mediaPlayer.setLooping(true));
                 mAnimationAvailable = true;
+                updateAspectRatio();
             } else {
                 setVisible(false);
             }
@@ -94,7 +99,11 @@
         final TextureView video = (TextureView) holder.findViewById(R.id.video_texture_view);
         final ImageView imageView = (ImageView) holder.findViewById(R.id.video_preview_image);
         final ImageView playButton = (ImageView) holder.findViewById(R.id.video_play_button);
+        final AspectRatioFrameLayout layout = (AspectRatioFrameLayout) holder.findViewById(
+                R.id.video_container);
+
         imageView.setImageResource(mPreviewResource);
+        layout.setAspectRatio(mAspectRadio);
 
         video.setOnClickListener(v -> {
             if (mMediaPlayer != null) {
@@ -178,4 +187,9 @@
         return mVideoPaused;
     }
 
+    @VisibleForTesting
+    void updateAspectRatio() {
+        mAspectRadio = mMediaPlayer.getVideoWidth() / (float)mMediaPlayer.getVideoHeight();
+    }
+
 }
diff --git a/src/com/android/settings/wifi/WifiScanningRequiredFragment.java b/src/com/android/settings/wifi/WifiScanningRequiredFragment.java
index 4ff023d..bf24bbc 100644
--- a/src/com/android/settings/wifi/WifiScanningRequiredFragment.java
+++ b/src/com/android/settings/wifi/WifiScanningRequiredFragment.java
@@ -92,7 +92,7 @@
     void addButtonIfNeeded(AlertDialog.Builder builder) {
         // Only show "learn more" if there is a help page to show
         if (!TextUtils.isEmpty(getContext().getString(R.string.help_uri_wifi_scanning_required))) {
-            builder.setNeutralButton(R.string.do_disclosure_learn_more, this);
+            builder.setNeutralButton(R.string.learn_more, this);
         }
     }
 
diff --git a/src/com/android/settings/wifi/p2p/WifiP2pSettings.java b/src/com/android/settings/wifi/p2p/WifiP2pSettings.java
index b8710c9..7ef10e5 100644
--- a/src/com/android/settings/wifi/p2p/WifiP2pSettings.java
+++ b/src/com/android/settings/wifi/p2p/WifiP2pSettings.java
@@ -168,6 +168,11 @@
     }
 
     @Override
+    public int getHelpResource() {
+        return R.string.help_url_wifi_p2p;
+    }
+
+    @Override
     protected List<AbstractPreferenceController> createPreferenceControllers(Context context) {
         final List<AbstractPreferenceController> controllers = new ArrayList<>();
         mPersistentCategoryController =
diff --git a/tests/robotests/assets/grandfather_slice_controller_not_in_xml b/tests/robotests/assets/grandfather_slice_controller_not_in_xml
index 1a67726..ae1c86a 100644
--- a/tests/robotests/assets/grandfather_slice_controller_not_in_xml
+++ b/tests/robotests/assets/grandfather_slice_controller_not_in_xml
@@ -1,2 +1,2 @@
 com.android.settings.testutils.FakeToggleController
-com.android.settings.core.TogglePreferenceControllerTest$FakeToggle
+com.android.settings.testutils.FakeSliderController
diff --git a/tests/robotests/src/com/android/settings/SettingsDumpServiceTest.java b/tests/robotests/src/com/android/settings/SettingsDumpServiceTest.java
index 615d1e7..8178641 100644
--- a/tests/robotests/src/com/android/settings/SettingsDumpServiceTest.java
+++ b/tests/robotests/src/com/android/settings/SettingsDumpServiceTest.java
@@ -16,13 +16,21 @@
 package com.android.settings;
 
 import static com.google.common.truth.Truth.assertThat;
+
+import static org.mockito.Matchers.anyInt;
+import static org.mockito.Matchers.anyString;
+import static org.mockito.Mockito.doReturn;
+import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.when;
 
+import android.content.Context;
+import android.content.SharedPreferences;
 import android.content.pm.ActivityInfo;
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.support.annotation.NonNull;
 
+import com.android.settings.fuelgauge.batterytip.AnomalyConfigJobService;
 import com.android.settings.testutils.SettingsRobolectricTestRunner;
 
 import org.json.JSONException;
@@ -32,6 +40,7 @@
 import org.junit.runner.RunWith;
 import org.mockito.Mock;
 import org.mockito.MockitoAnnotations;
+import org.robolectric.RuntimeEnvironment;
 
 import java.io.OutputStream;
 import java.io.PrintWriter;
@@ -41,6 +50,7 @@
 
     private static final String PACKAGE_BROWSER = "com.android.test.browser";
     private static final String PACKAGE_NULL = "android";
+    private static final int ANOMALY_VERSION = 2;
 
     @Mock
     private PackageManager mPackageManager;
@@ -54,7 +64,7 @@
 
         when(mPackageManager.resolveActivity(TestService.BROWSER_INTENT,
                 PackageManager.MATCH_DEFAULT_ONLY)).thenReturn(mResolveInfo);
-        mTestService = new TestService();
+        mTestService = spy(new TestService());
         mTestService.setPackageManager(mPackageManager);
     }
 
@@ -75,13 +85,29 @@
     }
 
     @Test
+    public void testDumpAnomalyDetection_returnAnomalyInfo() throws JSONException {
+        final SharedPreferences sharedPreferences =
+                RuntimeEnvironment.application.getSharedPreferences(AnomalyConfigJobService.PREF_DB,
+                        Context.MODE_PRIVATE);
+        SharedPreferences.Editor editor = sharedPreferences.edit();
+        editor.putInt(AnomalyConfigJobService.KEY_ANOMALY_CONFIG_VERSION, ANOMALY_VERSION);
+        editor.commit();
+        doReturn(sharedPreferences).when(mTestService).getSharedPreferences(anyString(), anyInt());
+
+        final JSONObject jsonObject = mTestService.dumpAnomalyDetection();
+
+        assertThat(jsonObject.getInt(AnomalyConfigJobService.KEY_ANOMALY_CONFIG_VERSION)).isEqualTo(
+                ANOMALY_VERSION);
+    }
+
+    @Test
     public void testDump_ReturnJsonObject() throws JSONException {
         mResolveInfo.activityInfo = new ActivityInfo();
         mResolveInfo.activityInfo.packageName = PACKAGE_BROWSER;
         TestPrintWriter printWriter = new TestPrintWriter(System.out);
 
         mTestService.dump(null, printWriter, null);
-        JSONObject object = (JSONObject)printWriter.getPrintObject();
+        JSONObject object = (JSONObject) printWriter.getPrintObject();
 
         assertThat(object.get(TestService.KEY_SERVICE)).isNotNull();
     }
diff --git a/tests/robotests/src/com/android/settings/core/codeinspection/CodeInspectionTest.java b/tests/robotests/src/com/android/settings/core/codeinspection/CodeInspectionTest.java
index c8ad4d6..64412cf 100644
--- a/tests/robotests/src/com/android/settings/core/codeinspection/CodeInspectionTest.java
+++ b/tests/robotests/src/com/android/settings/core/codeinspection/CodeInspectionTest.java
@@ -21,6 +21,7 @@
 import com.android.settings.core.BasePreferenceControllerSignatureInspector;
 import com.android.settings.core.instrumentation.InstrumentableFragmentCodeInspector;
 import com.android.settings.search.SearchIndexProviderCodeInspector;
+import com.android.settings.slices.SliceControllerInXmlCodeInspector;
 import com.android.settings.testutils.SettingsRobolectricTestRunner;
 
 import org.junit.Before;
@@ -51,6 +52,11 @@
     }
 
     @Test
+    public void runSliceControllerInXmlInspection() throws Exception {
+        new SliceControllerInXmlCodeInspector(mClasses).run();
+    }
+
+    @Test
     public void runBasePreferenceControllerConstructorSignatureInspection() {
         new BasePreferenceControllerSignatureInspector(mClasses).run();
     }
diff --git a/tests/robotests/src/com/android/settings/display/ColorModePreferenceFragmentTest.java b/tests/robotests/src/com/android/settings/display/ColorModePreferenceFragmentTest.java
index e962441..6df0c04 100644
--- a/tests/robotests/src/com/android/settings/display/ColorModePreferenceFragmentTest.java
+++ b/tests/robotests/src/com/android/settings/display/ColorModePreferenceFragmentTest.java
@@ -16,8 +16,10 @@
 package com.android.settings.display;
 
 import static com.google.common.truth.Truth.assertThat;
+import static org.mockito.Answers.RETURNS_DEEP_STUBS;
 import static org.mockito.ArgumentMatchers.anyInt;
 import static org.mockito.Mockito.doNothing;
+import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.times;
 import static org.mockito.Mockito.verify;
@@ -32,6 +34,7 @@
 import com.android.settings.R;
 import com.android.settings.applications.LayoutPreference;
 import com.android.settings.testutils.SettingsRobolectricTestRunner;
+import com.android.settings.widget.RadioButtonPreference;
 import com.android.settingslib.widget.CandidateInfo;
 
 import org.junit.Before;
@@ -39,11 +42,11 @@
 import org.junit.runner.RunWith;
 import org.mockito.ArgumentCaptor;
 import org.mockito.Mock;
-import org.mockito.Mockito;
 import org.mockito.MockitoAnnotations;
 import org.robolectric.RuntimeEnvironment;
 import org.robolectric.util.ReflectionHelpers;
 
+import java.util.ArrayList;
 import java.util.List;
 
 @RunWith(SettingsRobolectricTestRunner.class)
@@ -54,11 +57,14 @@
     @Mock
     private ColorDisplayController mController;
 
+    @Mock
+    private PreferenceScreen mScreen;
+
     @Before
     public void setup() {
         MockitoAnnotations.initMocks(this);
 
-        mFragment = spy(new ColorModePreferenceFragment());
+        mFragment = spy(new ColorModePreferenceFragmentTestable(mScreen));
         ReflectionHelpers.setField(mFragment, "mController", mController);
     }
 
@@ -86,7 +92,7 @@
 
     @Test
     public void getKey_natural() {
-        Mockito.when(mController.getColorMode())
+        when(mController.getColorMode())
             .thenReturn(ColorDisplayController.COLOR_MODE_NATURAL);
 
         assertThat(mFragment.getDefaultKey())
@@ -95,7 +101,7 @@
 
     @Test
     public void getKey_boosted() {
-        Mockito.when(mController.getColorMode())
+        when(mController.getColorMode())
             .thenReturn(ColorDisplayController.COLOR_MODE_BOOSTED);
 
         assertThat(mFragment.getDefaultKey())
@@ -104,7 +110,7 @@
 
     @Test
     public void getKey_saturated() {
-        Mockito.when(mController.getColorMode())
+        when(mController.getColorMode())
             .thenReturn(ColorDisplayController.COLOR_MODE_SATURATED);
 
         assertThat(mFragment.getDefaultKey())
@@ -141,15 +147,64 @@
 
     @Test
     public void addStaticPreferences_shouldAddPreviewImage() {
-        PreferenceScreen mockPreferenceScreen = Mockito.mock(PreferenceScreen.class);
-        LayoutPreference mockPreview = Mockito.mock(LayoutPreference.class);
+        PreferenceScreen mockPreferenceScreen = mock(PreferenceScreen.class);
+        LayoutPreference mockPreview = mock(LayoutPreference.class);
 
         ArgumentCaptor<Preference> preferenceCaptor = ArgumentCaptor.forClass(Preference.class);
 
         mFragment.configureAndInstallPreview(mockPreview, mockPreferenceScreen);
-        Mockito.verify(mockPreview, times(1)).setSelectable(false);
-        Mockito.verify(mockPreferenceScreen, times(1)).addPreference(preferenceCaptor.capture());
+        verify(mockPreview, times(1)).setSelectable(false);
+        verify(mockPreferenceScreen, times(1)).addPreference(preferenceCaptor.capture());
 
         assertThat(preferenceCaptor.getValue()).isEqualTo(mockPreview);
     }
+
+    @Test
+    public void onAccessibilityTransformChanged_toggles() {
+        final int radioPrefsCount = 3;
+        List<RadioButtonPreference> radioPrefs = new ArrayList<>();
+        for (int i = 0; i < radioPrefsCount; i++) {
+            radioPrefs.add(mock(RadioButtonPreference.class));
+        }
+
+        when(mScreen.getPreferenceCount()).thenReturn(radioPrefs.size());
+        when(mScreen.getPreference(anyInt())).thenAnswer(invocation -> {
+            final Object[] args = invocation.getArguments();
+            return radioPrefs.get((int) args[0]);
+        });
+
+        mFragment.onAccessibilityTransformChanged(true /* state */);
+        for (int i = 0; i < radioPrefsCount; i++) {
+            verify(radioPrefs.get(i)).setEnabled(false);
+        }
+
+        mFragment.onAccessibilityTransformChanged(false /* state */);
+        for (int i = 0; i < radioPrefsCount; i++) {
+            verify(radioPrefs.get(i)).setEnabled(true);
+        }
+    }
+
+    private static class ColorModePreferenceFragmentTestable
+            extends ColorModePreferenceFragment {
+
+        private final PreferenceScreen mPreferenceScreen;
+
+        private ColorModePreferenceFragmentTestable(PreferenceScreen screen) {
+            mPreferenceScreen = screen;
+        }
+
+        /**
+         * A method to return a mock PreferenceScreen.
+         * A real ColorModePreferenceFragment calls super.getPreferenceScreen() to get its
+         * PreferenceScreen handle, which internally dereferenced a PreferenceManager. But in this
+         * test scenario, the PreferenceManager object is uninitialized, so we need to supply the
+         * PreferenceScreen directly.
+         *
+         * @return a mock PreferenceScreen
+         */
+        @Override
+        public PreferenceScreen getPreferenceScreen() {
+            return mPreferenceScreen;
+        }
+    }
 }
diff --git a/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java b/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java
index 40371d7..fb65e5d 100644
--- a/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java
+++ b/tests/robotests/src/com/android/settings/enterprise/EnterprisePrivacyFeatureProviderImplTest.java
@@ -126,7 +126,7 @@
         SpannableStringBuilder disclosure = new SpannableStringBuilder();
         disclosure.append(mResources.getString(R.string.do_disclosure_generic));
         disclosure.append(mResources.getString(R.string.do_disclosure_learn_more_separator));
-        disclosure.append(mResources.getString(R.string.do_disclosure_learn_more),
+        disclosure.append(mResources.getString(R.string.learn_more),
                 new EnterprisePrivacyFeatureProviderImpl.EnterprisePrivacySpan(mContext), 0);
         when(mDevicePolicyManager.getDeviceOwnerComponentOnAnyUser()).thenReturn(OWNER);
         when(mDevicePolicyManager.getDeviceOwnerOrganizationName()).thenReturn(null);
@@ -136,7 +136,7 @@
         disclosure.append(mResources.getString(R.string.do_disclosure_with_name,
                 OWNER_ORGANIZATION));
         disclosure.append(mResources.getString(R.string.do_disclosure_learn_more_separator));
-        disclosure.append(mResources.getString(R.string.do_disclosure_learn_more),
+        disclosure.append(mResources.getString(R.string.learn_more),
                 new EnterprisePrivacyFeatureProviderImpl.EnterprisePrivacySpan(mContext), 0);
         when(mDevicePolicyManager.getDeviceOwnerOrganizationName()).thenReturn(OWNER_ORGANIZATION);
         assertThat(mProvider.getDeviceOwnerDisclosure()).isEqualTo(disclosure);
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/BatteryEntryTest.java b/tests/robotests/src/com/android/settings/fuelgauge/BatteryEntryTest.java
index b6be9ee..b89a3f0 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/BatteryEntryTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/BatteryEntryTest.java
@@ -29,6 +29,7 @@
 
 import com.android.internal.os.BatterySipper;
 import com.android.internal.os.BatterySipper.DrainType;
+import com.android.settings.R;
 
 import org.junit.Before;
 import org.junit.Rule;
@@ -38,6 +39,7 @@
 import org.mockito.junit.MockitoJUnit;
 import org.mockito.junit.MockitoRule;
 import org.robolectric.RobolectricTestRunner;
+import org.robolectric.RuntimeEnvironment;
 
 import java.util.Locale;
 
@@ -137,6 +139,17 @@
     }
 
     @Test
+    public void batteryEntryForAOD_containCorrectInfo() {
+        final BatterySipper batterySipper = mock(BatterySipper.class);
+        batterySipper.drainType = DrainType.AMBIENT_DISPLAY;
+        final BatteryEntry entry = new BatteryEntry(RuntimeEnvironment.application, mockHandler,
+                mockUserManager, batterySipper);
+
+        assertThat(entry.iconId).isEqualTo(R.drawable.ic_settings_aod);
+        assertThat(entry.name).isEqualTo("Ambient display");
+    }
+
+    @Test
     public void extractPackageFromSipper_systemSipper_returnSystemPackage() {
         BatteryEntry entry = createBatteryEntryForSystem();
 
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java
index 0894b66..55a8f4e 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/batterytip/AnomalyDetectionJobServiceTest.java
@@ -16,6 +16,10 @@
 
 package com.android.settings.fuelgauge.batterytip;
 
+import static android.os.StatsDimensionsValue.FLOAT_VALUE_TYPE;
+import static android.os.StatsDimensionsValue.INT_VALUE_TYPE;
+import static android.os.StatsDimensionsValue.TUPLE_VALUE_TYPE;
+
 import static com.google.common.truth.Truth.assertThat;
 
 import static org.mockito.Matchers.any;
@@ -24,9 +28,11 @@
 import static org.mockito.Matchers.anyString;
 import static org.mockito.Matchers.eq;
 import static org.mockito.Mockito.doReturn;
+import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.never;
 import static org.mockito.Mockito.spy;
 import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
 import static org.robolectric.RuntimeEnvironment.application;
 
 import android.app.StatsManager;
@@ -35,6 +41,8 @@
 import android.content.Context;
 import android.content.Intent;
 import android.os.Bundle;
+import android.os.Parcel;
+import android.os.Parcelable;
 import android.os.Process;
 import android.os.StatsDimensionsValue;
 import android.os.UserManager;
@@ -64,7 +72,7 @@
 
 @RunWith(SettingsRobolectricTestRunner.class)
 public class AnomalyDetectionJobServiceTest {
-    private static final int UID = 123;
+    private static final int UID = 12345;
     private static final String SYSTEM_PACKAGE = "com.android.system";
     private static final String SUBSCRIBER_COOKIES_AUTO_RESTRICTION =
             "anomaly_type=6,auto_restriction=true";
@@ -120,8 +128,8 @@
 
     @Test
     public void testSaveAnomalyToDatabase_systemWhitelisted_doNotSave() {
-        doReturn(SYSTEM_PACKAGE).when(mBatteryUtils).getPackageName(anyInt());
-        doReturn(true).when(mPowerWhitelistBackend).isSysWhitelisted(SYSTEM_PACKAGE);
+        doReturn(UID).when(mAnomalyDetectionJobService).extractUidFromStatsDimensionsValue(any());
+        doReturn(true).when(mPowerWhitelistBackend).isSysWhitelistedExceptIdle(any(String[].class));
 
         mAnomalyDetectionJobService.saveAnomalyToDatabase(mContext, mBatteryStatsHelper,
                 mUserManager, mBatteryDatabaseManager, mBatteryUtils, mPolicy,
@@ -149,6 +157,21 @@
     }
 
     @Test
+    public void testSaveAnomalyToDatabase_uidNull_doNotSave() {
+        doReturn(AnomalyDetectionJobService.UID_NULL).when(
+                mAnomalyDetectionJobService).extractUidFromStatsDimensionsValue(any());
+
+        mAnomalyDetectionJobService.saveAnomalyToDatabase(mContext, mBatteryStatsHelper,
+                mUserManager, mBatteryDatabaseManager, mBatteryUtils, mPolicy,
+                mPowerWhitelistBackend, mContext.getContentResolver(),
+                mFeatureFactory.powerUsageFeatureProvider, mFeatureFactory.metricsFeatureProvider,
+                mBundle);
+
+        verify(mBatteryDatabaseManager, never()).insertAnomaly(anyInt(), anyString(), anyInt(),
+                anyInt(), anyLong());
+    }
+
+    @Test
     public void testSaveAnomalyToDatabase_normalAppWithAutoRestriction_save() {
         final ArrayList<String> cookies = new ArrayList<>();
         cookies.add(SUBSCRIBER_COOKIES_AUTO_RESTRICTION);
@@ -196,4 +219,35 @@
                 SYSTEM_PACKAGE,
                 Pair.create(MetricsProto.MetricsEvent.FIELD_CONTEXT, ANOMALY_TYPE));
     }
+
+    @Test
+    public void testExtractUidFromStatsDimensionsValue_extractCorrectUid() {
+        // Build an integer dimensions value.
+        final StatsDimensionsValue intValue = mock(StatsDimensionsValue.class);
+        when(intValue.isValueType(INT_VALUE_TYPE)).thenReturn(true);
+        when(intValue.getField()).thenReturn(AnomalyDetectionJobService.STATSD_UID_FILED);
+        when(intValue.getIntValue()).thenReturn(UID);
+
+        // Build a tuple dimensions value and put the previous integer dimensions value inside.
+        final StatsDimensionsValue tupleValue = mock(StatsDimensionsValue.class);
+        when(tupleValue.isValueType(TUPLE_VALUE_TYPE)).thenReturn(true);
+        final List<StatsDimensionsValue> statsDimensionsValues = new ArrayList<>();
+        statsDimensionsValues.add(intValue);
+        when(tupleValue.getTupleValueList()).thenReturn(statsDimensionsValues);
+
+        assertThat(mAnomalyDetectionJobService.extractUidFromStatsDimensionsValue(
+                tupleValue)).isEqualTo(UID);
+    }
+
+    @Test
+    public void testExtractUidFromStatsDimensionsValue_wrongFormat_returnNull() {
+        // Build a float dimensions value
+        final StatsDimensionsValue floatValue = mock(StatsDimensionsValue.class);
+        when(floatValue.isValueType(FLOAT_VALUE_TYPE)).thenReturn(true);
+        when(floatValue.getField()).thenReturn(AnomalyDetectionJobService.STATSD_UID_FILED);
+        when(floatValue.getFloatValue()).thenReturn(0f);
+
+        assertThat(mAnomalyDetectionJobService.extractUidFromStatsDimensionsValue(
+                floatValue)).isEqualTo(AnomalyDetectionJobService.UID_NULL);
+    }
 }
diff --git a/tests/robotests/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceControllerTest.java
index 999f83a..31b2eb1 100644
--- a/tests/robotests/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/AdjustVolumeRestrictedPreferenceControllerTest.java
@@ -43,6 +43,7 @@
 @RunWith(SettingsRobolectricTestRunner.class)
 public class AdjustVolumeRestrictedPreferenceControllerTest {
 
+    private static final String KEY = "key";
     @Mock
     private AccountRestrictionHelper mAccountHelper;
 
@@ -54,7 +55,7 @@
         MockitoAnnotations.initMocks(this);
         mContext = spy(RuntimeEnvironment.application);
         mController =
-            new AdjustVolumeRestrictedPreferenceControllerTestable(mContext, mAccountHelper);
+            new AdjustVolumeRestrictedPreferenceControllerTestable(mContext, mAccountHelper, KEY);
     }
 
     @Test
@@ -88,13 +89,18 @@
         extends AdjustVolumeRestrictedPreferenceController {
 
         private AdjustVolumeRestrictedPreferenceControllerTestable(Context context,
-            AccountRestrictionHelper helper) {
-            super(context, helper);
+            AccountRestrictionHelper helper, String key) {
+            super(context, helper, key);
+        }
+
+        @Override
+        public int getAvailabilityStatus() {
+            return 0;
         }
 
         @Override
         public String getPreferenceKey() {
-            return null;
+            return KEY;
         }
 
         @Override
@@ -103,8 +109,18 @@
         }
 
         @Override
-        public boolean isAvailable() {
-            return true;
+        public int getSliderPosition() {
+            return 0;
+        }
+
+        @Override
+        public boolean setSliderPosition(int position) {
+            return false;
+        }
+
+        @Override
+        public int getMaxSteps() {
+            return 0;
         }
     }
 }
diff --git a/tests/robotests/src/com/android/settings/notification/AlarmVolumePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/AlarmVolumePreferenceControllerTest.java
index 017a26a..6e8476c 100644
--- a/tests/robotests/src/com/android/settings/notification/AlarmVolumePreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/AlarmVolumePreferenceControllerTest.java
@@ -45,7 +45,8 @@
     public void setUp() {
         MockitoAnnotations.initMocks(this);
         mContext = RuntimeEnvironment.application;
-        mController = new AlarmVolumePreferenceController(mContext, null, null, mHelper);
+        mController = new AlarmVolumePreferenceController(mContext);
+        mController.setAudioHelper(mHelper);
     }
 
     @Test
diff --git a/tests/robotests/src/com/android/settings/notification/MediaVolumePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/MediaVolumePreferenceControllerTest.java
index 65680b1..3659a30 100644
--- a/tests/robotests/src/com/android/settings/notification/MediaVolumePreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/MediaVolumePreferenceControllerTest.java
@@ -35,8 +35,7 @@
 
     @Before
     public void setUp() {
-        mController =
-            new MediaVolumePreferenceController(RuntimeEnvironment.application, null, null);
+        mController = new MediaVolumePreferenceController(RuntimeEnvironment.application);
     }
 
     @Test
diff --git a/tests/robotests/src/com/android/settings/notification/NotificationVolumePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/NotificationVolumePreferenceControllerTest.java
index 1c605b9..c209c1b 100644
--- a/tests/robotests/src/com/android/settings/notification/NotificationVolumePreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/NotificationVolumePreferenceControllerTest.java
@@ -57,7 +57,8 @@
         when(mContext.getSystemService(Context.TELEPHONY_SERVICE)).thenReturn(mTelephonyManager);
         when(mContext.getSystemService(Context.AUDIO_SERVICE)).thenReturn(mAudioManager);
         when(mContext.getSystemService(Context.VIBRATOR_SERVICE)).thenReturn(mVibrator);
-        mController = new NotificationVolumePreferenceController(mContext, null, null, mHelper);
+        mController = new NotificationVolumePreferenceController(mContext);
+        mController.setAudioHelper(mHelper);
     }
 
     @Test
diff --git a/tests/robotests/src/com/android/settings/notification/RingVolumePreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/RingVolumePreferenceControllerTest.java
index f5e87e7..e006530 100644
--- a/tests/robotests/src/com/android/settings/notification/RingVolumePreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/RingVolumePreferenceControllerTest.java
@@ -65,7 +65,8 @@
         shadowContext.setSystemService(Context.NOTIFICATION_SERVICE, mNotificationManager);
         mContext = RuntimeEnvironment.application;
         when(mNotificationManager.getEffectsSuppressor()).thenReturn(mSuppressor);
-        mController = new RingVolumePreferenceController(mContext, null, null, mHelper);
+        mController = new RingVolumePreferenceController(mContext);
+        mController.setAudioHelper(mHelper);
     }
 
     @Test
diff --git a/tests/robotests/src/com/android/settings/notification/VolumeSeekBarPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/notification/VolumeSeekBarPreferenceControllerTest.java
index a6addb3..675ac57 100644
--- a/tests/robotests/src/com/android/settings/notification/VolumeSeekBarPreferenceControllerTest.java
+++ b/tests/robotests/src/com/android/settings/notification/VolumeSeekBarPreferenceControllerTest.java
@@ -16,6 +16,7 @@
 
 package com.android.settings.notification;
 
+import static com.google.common.truth.Truth.assertThat;
 import static org.mockito.ArgumentMatchers.nullable;
 import static org.mockito.Matchers.any;
 import static org.mockito.Matchers.anyInt;
@@ -46,6 +47,8 @@
     private VolumeSeekBarPreference mPreference;
     @Mock
     private VolumeSeekBarPreference.Callback mCallback;
+    @Mock
+    private AudioHelper mHelper;
 
     private VolumeSeekBarPreferenceControllerTestable mController;
 
@@ -53,7 +56,10 @@
     public void setUp() {
         MockitoAnnotations.initMocks(this);
         when(mScreen.findPreference(nullable(String.class))).thenReturn(mPreference);
-        mController = new VolumeSeekBarPreferenceControllerTestable(mContext, mCallback);
+        when(mPreference.getKey()).thenReturn("key");
+        mController = new VolumeSeekBarPreferenceControllerTestable(mContext, mCallback,
+                mPreference.getKey());
+        mController.setAudioHelper(mHelper);
     }
 
     @Test
@@ -67,7 +73,8 @@
 
     @Test
     public void displayPreference_notAvailable_shouldNotUpdatePreference() {
-        mController = new VolumeSeekBarPreferenceControllerTestable(mContext, mCallback, false);
+        mController = new VolumeSeekBarPreferenceControllerTestable(mContext, mCallback, false,
+                mPreference.getKey());
 
         mController.displayPreference(mScreen);
 
@@ -94,6 +101,42 @@
         verify(mPreference).onActivityPause();
     }
 
+    @Test
+    public void sliderMethods_handleNullPreference() {
+        when(mHelper.getStreamVolume(mController.getAudioStream())).thenReturn(4);
+        when(mHelper.getMaxVolume(mController.getAudioStream())).thenReturn(10);
+
+        assertThat(mController.getMaxSteps()).isEqualTo(10);
+        assertThat(mController.getSliderPosition()).isEqualTo(4);
+
+        mController.setSliderPosition(9);
+        verify(mHelper).setStreamVolume(mController.getAudioStream(), 9);
+    }
+
+    @Test
+    public void setSliderPosition_passesAlongValue() {
+        mController.displayPreference(mScreen);
+
+        mController.setSliderPosition(2);
+        verify(mPreference).setProgress(2);
+    }
+
+    @Test
+    public void getMaxSteps_passesAlongValue() {
+        when(mPreference.getMax()).thenReturn(6);
+        mController.displayPreference(mScreen);
+
+        assertThat(mController.getMaxSteps()).isEqualTo(6);
+    }
+
+    @Test
+    public void getSliderPosition_passesAlongValue() {
+        when(mPreference.getProgress()).thenReturn(7);
+        mController.displayPreference(mScreen);
+
+        assertThat(mController.getSliderPosition()).isEqualTo(7);
+    }
+
     private class VolumeSeekBarPreferenceControllerTestable
         extends VolumeSeekBarPreferenceController {
 
@@ -103,19 +146,20 @@
         private boolean mAvailable;
 
         VolumeSeekBarPreferenceControllerTestable(Context context,
-            VolumeSeekBarPreference.Callback callback) {
-            this(context, callback, true);
+            VolumeSeekBarPreference.Callback callback, String key) {
+            this(context, callback, true, key);
         }
 
         VolumeSeekBarPreferenceControllerTestable(Context context,
-            VolumeSeekBarPreference.Callback callback, boolean available) {
-            super(context, callback, null);
+            VolumeSeekBarPreference.Callback callback, boolean available, String key) {
+            super(context, key);
+            setCallback(callback);
             mAvailable = available;
         }
 
         @Override
         public String getPreferenceKey() {
-            return null;
+            return "key";
         }
 
         @Override
@@ -124,8 +168,8 @@
         }
 
         @Override
-        public boolean isAvailable() {
-            return mAvailable;
+        public int getAvailabilityStatus() {
+            return mAvailable ? AVAILABLE : DISABLED_UNSUPPORTED;
         }
 
         @Override
diff --git a/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java b/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
index df6be44..1f3f40f 100644
--- a/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
+++ b/tests/robotests/src/com/android/settings/slices/SliceBuilderUtilsTest.java
@@ -188,26 +188,25 @@
     }
 
     @Test
-    public void testDynamicSummary_returnsSliceScreenTitle() {
+    public void testDynamicSummary_returnsSliceEmptyString() {
         final SliceData data = getDummyData((String) null);
         final FakePreferenceController controller = new FakePreferenceController(mContext, KEY);
-
         final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
 
-        assertThat(summary).isEqualTo(data.getScreenTitle());
+        assertThat(summary).isEqualTo("");
     }
 
     @Test
-    public void testDynamicSummary_placeHolderString_returnsScreenTitle() {
+    public void testDynamicSummary_placeHolderString_returnsEmptyString() {
         final SliceData data = getDummyData(mContext.getString(R.string.summary_placeholder));
         final FakePreferenceController controller = new FakePreferenceController(mContext, KEY);
         final CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
 
-        assertThat(summary).isEqualTo(data.getScreenTitle());
+        assertThat(summary).isEqualTo("");
     }
 
     @Test
-    public void testDynamicSummary_sliceDataAndFragmentPlaceholder_returnsSliceScreenTitle() {
+    public void testDynamicSummary_sliceDataAndFragmentPlaceholder_returnsSliceEmptyString() {
         final String summaryPlaceholder = mContext.getString(R.string.summary_placeholder);
         final SliceData data = getDummyData(summaryPlaceholder);
         final FakePreferenceController controller = spy(
@@ -216,7 +215,19 @@
 
         CharSequence summary = SliceBuilderUtils.getSubtitleText(mContext, controller, data);
 
-        assertThat(summary).isEqualTo(data.getScreenTitle());
+        assertThat(summary).isEqualTo("");
+    }
+
+    @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
diff --git a/tests/robotests/src/com/android/settings/slices/SliceControllerInXmlTest.java b/tests/robotests/src/com/android/settings/slices/SliceControllerInXmlCodeInspector.java
similarity index 85%
rename from tests/robotests/src/com/android/settings/slices/SliceControllerInXmlTest.java
rename to tests/robotests/src/com/android/settings/slices/SliceControllerInXmlCodeInspector.java
index 7de9c2b..9c8b946 100644
--- a/tests/robotests/src/com/android/settings/slices/SliceControllerInXmlTest.java
+++ b/tests/robotests/src/com/android/settings/slices/SliceControllerInXmlCodeInspector.java
@@ -19,7 +19,6 @@
 import static com.android.settings.core.PreferenceXmlParserUtils.METADATA_CONTROLLER;
 import static com.google.common.truth.Truth.assertThat;
 import static com.google.common.truth.Truth.assertWithMessage;
-import static org.mockito.Mockito.spy;
 
 import android.content.Context;
 import android.os.Bundle;
@@ -27,8 +26,8 @@
 import android.text.TextUtils;
 
 import com.android.settings.core.PreferenceXmlParserUtils;
+import com.android.settings.core.SliderPreferenceController;
 import com.android.settings.core.TogglePreferenceController;
-import com.android.settings.core.codeinspection.ClassScanner;
 import com.android.settings.core.codeinspection.CodeInspector;
 import com.android.settings.overlay.FeatureFactory;
 import com.android.settings.search.DatabaseIndexingUtils;
@@ -36,25 +35,21 @@
 import com.android.settings.search.SearchFeatureProvider;
 import com.android.settings.search.SearchFeatureProviderImpl;
 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.robolectric.RuntimeEnvironment;
 import org.xmlpull.v1.XmlPullParserException;
 
 import java.io.IOException;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collection;
-import java.util.Collections;
 import java.util.List;
 
-@RunWith(SettingsRobolectricTestRunner.class)
-public class SliceControllerInXmlTest {
+public class SliceControllerInXmlCodeInspector extends CodeInspector {
 
-    private static final List<Class> mSliceControllerClasses = Collections.singletonList(
-            TogglePreferenceController.class
+    private static final List<Class> mSliceControllerClasses = Arrays.asList(
+            TogglePreferenceController.class,
+            SliderPreferenceController.class
     );
 
     private final List<String> mXmlDeclaredControllers = new ArrayList<>();
@@ -66,15 +61,13 @@
                     + "If it should not appear in XML, add the controller's classname to "
                     + "grandfather_slice_controller_not_in_xml. Controllers:\n";
 
-    private Context mContext;
+    private final Context mContext;
+    private final SearchFeatureProvider mSearchProvider;
+    private final FakeFeatureFactory mFakeFeatureFactory;
 
-    private SearchFeatureProvider mSearchProvider;
-    private FakeFeatureFactory mFakeFeatureFactory;
-
-    @Before
-    public void setUp() throws IOException, XmlPullParserException {
-        mContext = spy(RuntimeEnvironment.application);
-
+    public SliceControllerInXmlCodeInspector(List<Class<?>> classes) throws Exception {
+        super(classes);
+        mContext = RuntimeEnvironment.application;
         mSearchProvider = new SearchFeatureProviderImpl();
         mFakeFeatureFactory = FakeFeatureFactory.setupForTest();
         mFakeFeatureFactory.searchFeatureProvider = mSearchProvider;
@@ -102,13 +95,15 @@
         assertThat(mXmlDeclaredControllers).isNotEmpty();
     }
 
-    @Test
-    public void testAllControllersDeclaredInXml() throws Exception {
-        final List<Class<?>> classes =
-                new ClassScanner().getClassesForPackage(mContext.getPackageName());
+    @Override
+    public void run() {
         final List<String> missingControllersInXml = new ArrayList<>();
 
-        for (Class<?> clazz : classes) {
+        for (Class<?> clazz : mClasses) {
+            if (!isConcreteSettingsClass(clazz)) {
+                // Only care about non-abstract classes.
+                continue;
+            }
             if (!isInlineSliceClass(clazz)) {
                 // Only care about inline-slice controller classes.
                 continue;
diff --git a/tests/robotests/src/com/android/settings/widget/AspectRatioFrameLayoutTest.java b/tests/robotests/src/com/android/settings/widget/AspectRatioFrameLayoutTest.java
index bb55692..59a90c5 100644
--- a/tests/robotests/src/com/android/settings/widget/AspectRatioFrameLayoutTest.java
+++ b/tests/robotests/src/com/android/settings/widget/AspectRatioFrameLayoutTest.java
@@ -41,7 +41,7 @@
     }
 
     @Test
-    public void measure_squareAspectRatio_stretchHeight() {
+    public void measure_squareAspectRatio_squeezeWidth() {
         mLayout = new AspectRatioFrameLayout(mContext);
 
         int widthMeasureSpec = View.MeasureSpec.makeMeasureSpec(100, View.MeasureSpec.EXACTLY);
@@ -49,8 +49,8 @@
 
         mLayout.measure(widthMeasureSpec, heightMeasureSpec);
 
-        assertThat(mLayout.getMeasuredWidth()).isEqualTo(100);
-        assertThat(mLayout.getMeasuredHeight()).isEqualTo(100);
+        assertThat(mLayout.getMeasuredWidth()).isEqualTo(50);
+        assertThat(mLayout.getMeasuredHeight()).isEqualTo(50);
     }
 
     @Test
diff --git a/tests/robotests/src/com/android/settings/widget/VideoPreferenceTest.java b/tests/robotests/src/com/android/settings/widget/VideoPreferenceTest.java
new file mode 100644
index 0000000..fee7bcc
--- /dev/null
+++ b/tests/robotests/src/com/android/settings/widget/VideoPreferenceTest.java
@@ -0,0 +1,73 @@
+/*
+ * 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.widget;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import static org.mockito.Mockito.when;
+
+import android.content.Context;
+import android.media.MediaPlayer;
+import android.support.v7.preference.PreferenceViewHolder;
+import android.view.LayoutInflater;
+
+import com.android.settings.R;
+import com.android.settings.testutils.SettingsRobolectricTestRunner;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+import org.robolectric.RuntimeEnvironment;
+
+@RunWith(SettingsRobolectricTestRunner.class)
+public class VideoPreferenceTest {
+    private static final int VIDEO_WIDTH = 100;
+    private static final int VIDEO_HEIGHT = 150;
+    @Mock
+    private MediaPlayer mMediaPlayer;
+    private Context mContext;
+    private VideoPreference mVideoPreference;
+    private PreferenceViewHolder mPreferenceViewHolder;
+
+    @Before
+    public void setUp() {
+        MockitoAnnotations.initMocks(this);
+
+        mContext = RuntimeEnvironment.application;
+        mVideoPreference = new VideoPreference(mContext, null /* attrs */);
+        mVideoPreference.mMediaPlayer = mMediaPlayer;
+        when(mMediaPlayer.getVideoWidth()).thenReturn(VIDEO_WIDTH);
+        when(mMediaPlayer.getVideoHeight()).thenReturn(VIDEO_HEIGHT);
+
+        mPreferenceViewHolder = PreferenceViewHolder.createInstanceForTests(
+                LayoutInflater.from(mContext).inflate(R.layout.video_preference, null));
+    }
+
+    @Test
+    public void onBindViewHolder_hasCorrectRatio() {
+        mVideoPreference.mAnimationAvailable = true;
+
+        mVideoPreference.updateAspectRatio();
+        mVideoPreference.onBindViewHolder(mPreferenceViewHolder);
+
+        final AspectRatioFrameLayout layout =
+                (AspectRatioFrameLayout) mPreferenceViewHolder.findViewById(R.id.video_container);
+        assertThat(layout.mAspectRatio).isWithin(0.01f).of(VIDEO_WIDTH / (float) VIDEO_HEIGHT);
+    }
+}
diff --git a/tests/uitests/AndroidTest.xml b/tests/uitests/AndroidTest.xml
index 4f9e377..4162207 100644
--- a/tests/uitests/AndroidTest.xml
+++ b/tests/uitests/AndroidTest.xml
@@ -25,5 +25,6 @@
     <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
         <option name="package" value="com.android.settings.ui" />
         <option name="runner" value="android.support.test.runner.AndroidJUnitRunner" />
+        <option name="hidden-api-checks" value="false"/>
     </test>
 </configuration>
diff --git a/tests/unit/AndroidTest.xml b/tests/unit/AndroidTest.xml
index 34be41f..0c4b1dd 100644
--- a/tests/unit/AndroidTest.xml
+++ b/tests/unit/AndroidTest.xml
@@ -25,5 +25,6 @@
     <test class="com.android.tradefed.testtype.AndroidJUnitTest" >
         <option name="package" value="com.android.settings.tests.unit" />
         <option name="runner" value="android.support.test.runner.AndroidJUnitRunner" />
+        <option name="hidden-api-checks" value="false"/>
     </test>
 </configuration>