Add footer to app usage page

 - Add a footer to present the description text, will present specific text once this app is optimized or unrestricted only
 Screenshots:
   https://screenshot.googleplex.com/4HZGQU6SDni3PdR.png
   https://screenshot.googleplex.com/9gLSgftmaYuZepf.png
   https://screenshot.googleplex.com/55masP3VoAtAFMo.png

Bug: 178197718
Test: make SettingsRoboTests
Change-Id: Iced0fa591faf72874e2e3dff942122c90d35a4e7
diff --git a/res/xml/power_usage_detail.xml b/res/xml/power_usage_detail.xml
index 4746625..0258f8d 100644
--- a/res/xml/power_usage_detail.xml
+++ b/res/xml/power_usage_detail.xml
@@ -87,4 +87,11 @@
 
     </PreferenceCategory>
 
+    <com.android.settingslib.widget.FooterPreference
+        android:order="100"
+        android:key="app_usage_footer_preference"
+        android:title="@string/manager_battery_usage_footer"
+        android:selectable="true"
+        settings:searchable="false"/>
+
 </PreferenceScreen>
\ No newline at end of file
diff --git a/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java b/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java
index 79b5479..f28ae00 100644
--- a/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java
+++ b/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetail.java
@@ -25,6 +25,7 @@
 import android.content.pm.PackageManager;
 import android.os.Bundle;
 import android.os.UserHandle;
+import android.text.Html;
 import android.text.TextUtils;
 import android.util.Log;
 import android.view.View;
@@ -79,6 +80,7 @@
     private static final String KEY_PREF_UNRESTRICTED = "unrestricted_pref";
     private static final String KEY_PREF_OPTIMIZED = "optimized_pref";
     private static final String KEY_PREF_RESTRICTED = "restricted_pref";
+    private static final String KEY_FOOTER_PREFERENCE = "app_usage_footer_preference";
 
     private static final int REQUEST_UNINSTALL = 0;
     private static final int REQUEST_REMOVE_DEVICE_ADMIN = 1;
@@ -91,12 +93,16 @@
     ApplicationsState.AppEntry mAppEntry;
     @VisibleForTesting
     BatteryUtils mBatteryUtils;
+    @VisibleForTesting
+    BatteryOptimizeUtils mBatteryOptimizeUtils;
 
     @VisibleForTesting
     Preference mForegroundPreference;
     @VisibleForTesting
     Preference mBackgroundPreference;
     @VisibleForTesting
+    Preference mFooterPreference;
+    @VisibleForTesting
     RadioButtonPreference mRestrictedPreference;
     @VisibleForTesting
     RadioButtonPreference mOptimizePreference;
@@ -187,6 +193,7 @@
         mPackageName = getArguments().getString(EXTRA_PACKAGE_NAME);
         mForegroundPreference = findPreference(KEY_PREF_FOREGROUND);
         mBackgroundPreference = findPreference(KEY_PREF_BACKGROUND);
+        mFooterPreference = findPreference(KEY_FOOTER_PREFERENCE);
         mHeaderPreference = (LayoutPreference) findPreference(KEY_PREF_HEADER);
 
         mUnrestrictedPreference  = findPreference(KEY_PREF_UNRESTRICTED);
@@ -196,6 +203,9 @@
         mOptimizePreference.setOnClickListener(this);
         mRestrictedPreference.setOnClickListener(this);
 
+        mBatteryOptimizeUtils = new BatteryOptimizeUtils(
+                getContext(), getArguments().getInt(EXTRA_UID), mPackageName);
+
         if (mPackageName != null) {
             mAppEntry = mState.getEntry(mPackageName, UserHandle.myUserId());
         }
@@ -261,6 +271,26 @@
                                 backgroundTimeMs,
                                 /* withSeconds */ false,
                                 /* collapseTimeUnit */ false)));
+
+        final String stateString;
+        final String footerString;
+        //TODO(b/178197718) Update strings
+        if (!mBatteryOptimizeUtils.isValidPackageName()) {
+            //Present optimized only string when the package name is invalid.
+            stateString = context.getString(R.string.manager_battery_usage_optimized_title);
+            footerString = context.getString(
+                    R.string.manager_battery_usage_footer_limited, stateString);
+        } else if (mBatteryOptimizeUtils.isSystemOrDefaultApp()) {
+            //Present unrestricted only string when the package is system or default active app.
+            stateString = context.getString(R.string.manager_battery_usage_unrestricted_title);
+            footerString = context.getString(
+                    R.string.manager_battery_usage_footer_limited, stateString);
+        } else {
+            //Present default string to normal app.
+            footerString = context.getString(R.string.manager_battery_usage_footer);
+
+        }
+        mFooterPreference.setTitle(Html.fromHtml(footerString, Html.FROM_HTML_MODE_COMPACT));
     }
 
     @Override
diff --git a/tests/robotests/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetailTest.java b/tests/robotests/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetailTest.java
index 8eb7212..820607f 100644
--- a/tests/robotests/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetailTest.java
+++ b/tests/robotests/src/com/android/settings/fuelgauge/AdvancedPowerUsageDetailTest.java
@@ -23,6 +23,7 @@
 import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.ArgumentMatchers.anyInt;
 import static org.mockito.ArgumentMatchers.anyLong;
+import static org.mockito.ArgumentMatchers.anyString;
 import static org.mockito.ArgumentMatchers.eq;
 import static org.mockito.ArgumentMatchers.nullable;
 import static org.mockito.Mockito.doAnswer;
@@ -125,9 +126,12 @@
     private BatteryStats.Timer mForegroundActivityTimer;
     @Mock
     private BatteryUtils mBatteryUtils;
+    @Mock
+    private BatteryOptimizeUtils mBatteryOptimizeUtils;
     private Context mContext;
     private Preference mForegroundPreference;
     private Preference mBackgroundPreference;
+    private Preference mFooterPreference;
     private RadioButtonPreference mRestrictedPreference;
     private RadioButtonPreference mOptimizePreference;
     private RadioButtonPreference mUnrestrictedPreference;
@@ -177,6 +181,7 @@
         mFragment.mHeaderPreference = mHeaderPreference;
         mFragment.mState = mState;
         mFragment.mBatteryUtils = new BatteryUtils(RuntimeEnvironment.application);
+        mFragment.mBatteryOptimizeUtils = mBatteryOptimizeUtils;
         mAppEntry.info = mock(ApplicationInfo.class);
 
         mTestActivity = spy(new SettingsActivity());
@@ -201,11 +206,13 @@
 
         mForegroundPreference = new Preference(mContext);
         mBackgroundPreference = new Preference(mContext);
+        mFooterPreference = new Preference(mContext);
         mRestrictedPreference = new RadioButtonPreference(mContext);
         mOptimizePreference = new RadioButtonPreference(mContext);
         mUnrestrictedPreference = new RadioButtonPreference(mContext);
         mFragment.mForegroundPreference = mForegroundPreference;
         mFragment.mBackgroundPreference = mBackgroundPreference;
+        mFragment.mFooterPreference = mFooterPreference;
         mFragment.mRestrictedPreference = mRestrictedPreference;
         mFragment.mOptimizePreference = mOptimizePreference;
         mFragment.mUnrestrictedPreference = mUnrestrictedPreference;
@@ -367,6 +374,38 @@
     }
 
     @Test
+    public void testInitPreference_isValidPackageName_hasCorrectString() {
+        when(mBatteryOptimizeUtils.isValidPackageName()).thenReturn(false);
+
+        mFragment.initPreference();
+
+        assertThat(mFooterPreference.getTitle().toString())
+                .isEqualTo("This app requires Optimized battery usage.");
+    }
+
+    @Test
+    public void testInitPreference_isSystemOrDefaultApp_hasCorrectString() {
+        when(mBatteryOptimizeUtils.isValidPackageName()).thenReturn(true);
+        when(mBatteryOptimizeUtils.isSystemOrDefaultApp()).thenReturn(true);
+
+        mFragment.initPreference();
+
+        assertThat(mFooterPreference.getTitle()
+                .toString()).isEqualTo("This app requires Unrestricted battery usage.");
+    }
+
+    @Test
+    public void testInitPreference_hasCorrectString() {
+        when(mBatteryOptimizeUtils.isValidPackageName()).thenReturn(true);
+        when(mBatteryOptimizeUtils.isSystemOrDefaultApp()).thenReturn(false);
+
+        mFragment.initPreference();
+
+        assertThat(mFooterPreference.getTitle().toString())
+                .isEqualTo("Changing how an app uses your battery can affect its performance.");
+    }
+
+    @Test
     public void testOnRadioButtonClicked_clickOptimizePref_optimizePreferenceChecked() {
         mOptimizePreference.setKey(KEY_PREF_OPTIMIZED);
         mRestrictedPreference.setKey(KEY_PREF_RESTRICTED);