Ui changes in battery main page

1. Refine the battery header view
2. Move stats section to the place above power management
3. Add last full charge battery stat
4. Add the disclaimer as a footer

Also update the method name in test file, and this ui changes
also fix the header flash problem.

Bug: 36576021
Bug: 36494178
Test: RunSettingsRoboTests
Change-Id: I9784dbbbe16e61da7287f300183347dd4eee6a2b
(cherry picked from commit edfd09d590)
This commit is contained in:
jackqdyulei
2017-03-28 16:22:20 -07:00
parent 9b271041a9
commit 273ad50a3a
6 changed files with 154 additions and 173 deletions

View File

@@ -27,44 +27,35 @@
android:background="@drawable/selectable_card_grey" android:background="@drawable/selectable_card_grey"
style="@style/EntityHeader"> style="@style/EntityHeader">
<com.android.settings.fuelgauge.BatteryMeterView
android:id="@+id/battery_header_icon"
android:layout_width="@dimen/battery_meter_width"
android:layout_height="@dimen/battery_meter_height"/>
<LinearLayout <LinearLayout
android:layout_width="wrap_content" android:layout_width="216dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginStart="12dp" android:layout_marginStart="48dp"
android:layout_marginEnd="12dp" android:layout_marginEnd="12dp"
android:orientation="vertical"> android:orientation="vertical">
<TextView <TextView
android:id="@+id/time" android:id="@+id/battery_percent"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginTop="12dp" android:layout_marginTop="12dp"
android:gravity="center" android:textAppearance="@android:style/TextAppearance.Material.Display1"/>
android:textAppearance="@android:style/TextAppearance.Material.Medium"/>
<TextView <TextView
android:id="@+id/summary1" android:id="@+id/summary1"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginTop="12dp" android:layout_marginTop="12dp"
android:gravity="center"
android:textAppearance="@android:style/TextAppearance.Material.Small" android:textAppearance="@android:style/TextAppearance.Material.Small"
android:text="@string/estimated_time_left"/> android:text="@string/estimated_time_left"/>
<TextView
android:id="@+id/summary2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="12dp"
android:gravity="center"
android:textAppearance="@android:style/TextAppearance.Material.Small"
android:text="@string/estimated_time_description"/>
</LinearLayout> </LinearLayout>
<com.android.settings.fuelgauge.BatteryMeterView
android:id="@+id/battery_header_icon"
android:layout_width="@dimen/battery_meter_width"
android:layout_height="@dimen/battery_meter_height"
android:layout_gravity="end"
android:layout_marginEnd="24dp"/>
</LinearLayout> </LinearLayout>

View File

@@ -25,6 +25,19 @@
android:selectable="true" android:selectable="true"
android:layout="@layout/battery_header"/> android:layout="@layout/battery_header"/>
<PreferenceCategory
android:key="device_usage_list">
<com.android.settings.fuelgauge.PowerGaugePreference
android:key="last_full_charge"
android:title="@string/battery_last_full_charge"/>
<com.android.settings.fuelgauge.PowerGaugePreference
android:key="screen_usage"
android:title="@string/device_screen_usage"/>
</PreferenceCategory>
<PreferenceCategory <PreferenceCategory
android:key="power_management" android:key="power_management"
android:title="@string/battery_power_management"> android:title="@string/battery_power_management">
@@ -60,22 +73,4 @@
android:key="app_list" android:key="app_list"
android:title="@string/power_usage_list_summary"/> android:title="@string/power_usage_list_summary"/>
<PreferenceCategory
android:key="device_usage_list"
android:title="@string/device_usage_list_summary">
<Preference
android:key="screen_usage"
android:title="@string/device_screen_usage"/>
<Preference
android:key="screen_consumption"
android:title="@string/device_screen_consumption"/>
<Preference
android:key="cellular_network"
android:title="@string/device_cellular_network"/>
</PreferenceCategory>
</PreferenceScreen> </PreferenceScreen>

View File

@@ -46,7 +46,7 @@ public class BatteryMeterView extends ImageView {
mDrawable = new BatteryMeterDrawable(context, frameColor); mDrawable = new BatteryMeterDrawable(context, frameColor);
mDrawable.setColorFilter(new PorterDuffColorFilter(tintColor, PorterDuff.Mode.SRC_IN)); mDrawable.setColorFilter(new PorterDuffColorFilter(tintColor, PorterDuff.Mode.SRC_IN));
mDrawable.setShowPercent(true); mDrawable.setShowPercent(false);
setImageDrawable(mDrawable); setImageDrawable(mDrawable);
} }

View File

@@ -29,8 +29,11 @@ import com.android.settings.TintablePreference;
import com.android.settings.Utils; import com.android.settings.Utils;
/** /**
* Custom preference for displaying power consumption as a bar and an icon on * Custom preference for displaying battery usage info as a bar and an icon on
* the left for the subsystem/app type. * the left for the subsystem/app type.
*
* The battery usage info could be usage percentage or usage time. The preference
* won't show any icon if it is null.
*/ */
public class PowerGaugePreference extends TintablePreference { public class PowerGaugePreference extends TintablePreference {
private final int mIconSize; private final int mIconSize;
@@ -41,7 +44,20 @@ public class PowerGaugePreference extends TintablePreference {
public PowerGaugePreference(Context context, Drawable icon, CharSequence contentDescription, public PowerGaugePreference(Context context, Drawable icon, CharSequence contentDescription,
BatteryEntry info) { BatteryEntry info) {
super(context, null); this(context, null, icon, contentDescription, info);
}
public PowerGaugePreference(Context context) {
this(context, null, null, null, null);
}
public PowerGaugePreference(Context context, AttributeSet attrs) {
this(context, attrs, null, null, null);
}
private PowerGaugePreference(Context context, AttributeSet attrs, Drawable icon,
CharSequence contentDescription, BatteryEntry info) {
super(context, attrs);
setIcon(icon != null ? icon : new ColorDrawable(0)); setIcon(icon != null ? icon : new ColorDrawable(0));
setWidgetLayoutResource(R.layout.preference_widget_summary); setWidgetLayoutResource(R.layout.preference_widget_summary);
mInfo = info; mInfo = info;
@@ -49,10 +65,6 @@ public class PowerGaugePreference extends TintablePreference {
mIconSize = context.getResources().getDimensionPixelSize(R.dimen.app_icon_size); mIconSize = context.getResources().getDimensionPixelSize(R.dimen.app_icon_size);
} }
public PowerGaugePreference(Context context) {
this(context, null, null, null);
}
public void setContentDescription(String name) { public void setContentDescription(String name) {
mContentDescription = name; mContentDescription = name;
notifyChanged(); notifyChanged();
@@ -67,6 +79,11 @@ public class PowerGaugePreference extends TintablePreference {
return mProgress.toString(); return mProgress.toString();
} }
public void setSubtitle(String subtitle) {
mProgress = subtitle;
notifyChanged();
}
BatteryEntry getInfo() { BatteryEntry getInfo() {
return mInfo; return mInfo;
} }

View File

@@ -16,7 +16,6 @@
package com.android.settings.fuelgauge; package com.android.settings.fuelgauge;
import android.annotation.StringRes;
import android.app.Activity; import android.app.Activity;
import android.content.Context; import android.content.Context;
import android.graphics.drawable.Drawable; import android.graphics.drawable.Drawable;
@@ -26,6 +25,7 @@ import android.os.Bundle;
import android.os.Handler; import android.os.Handler;
import android.os.Message; import android.os.Message;
import android.os.Process; import android.os.Process;
import android.os.SystemClock;
import android.os.UserHandle; import android.os.UserHandle;
import android.provider.SearchIndexableResource; import android.provider.SearchIndexableResource;
import android.support.annotation.VisibleForTesting; import android.support.annotation.VisibleForTesting;
@@ -39,7 +39,6 @@ import android.util.TypedValue;
import android.view.Menu; import android.view.Menu;
import android.view.MenuInflater; import android.view.MenuInflater;
import android.view.MenuItem; import android.view.MenuItem;
import android.view.View;
import android.widget.TextView; import android.widget.TextView;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
@@ -60,6 +59,7 @@ import com.android.settings.display.BatteryPercentagePreferenceController;
import com.android.settings.display.TimeoutPreferenceController; import com.android.settings.display.TimeoutPreferenceController;
import com.android.settings.overlay.FeatureFactory; import com.android.settings.overlay.FeatureFactory;
import com.android.settings.search.BaseSearchIndexProvider; import com.android.settings.search.BaseSearchIndexProvider;
import com.android.settings.widget.FooterPreferenceMixin;
import com.android.settingslib.BatteryInfo; import com.android.settingslib.BatteryInfo;
import java.util.ArrayList; import java.util.ArrayList;
@@ -87,8 +87,7 @@ public class PowerUsageSummary extends PowerUsageBase {
private static final int SECONDS_IN_HOUR = 60 * 60; private static final int SECONDS_IN_HOUR = 60 * 60;
private static final String KEY_SCREEN_USAGE = "screen_usage"; private static final String KEY_SCREEN_USAGE = "screen_usage";
private static final String KEY_SCREEN_CONSUMPTION = "screen_consumption"; private static final String KEY_TIME_SINCE_LAST_FULL_CHARGE = "last_full_charge";
private static final String KEY_CELLULAR_NETWORK = "cellular_network";
private static final int MENU_STATS_TYPE = Menu.FIRST; private static final int MENU_STATS_TYPE = Menu.FIRST;
@@ -100,14 +99,15 @@ public class PowerUsageSummary extends PowerUsageBase {
static final int MENU_TOGGLE_APPS = Menu.FIRST + 5; static final int MENU_TOGGLE_APPS = Menu.FIRST + 5;
private static final int MENU_HELP = Menu.FIRST + 6; private static final int MENU_HELP = Menu.FIRST + 6;
private final FooterPreferenceMixin mFooterPreferenceMixin =
new FooterPreferenceMixin(this, getLifecycle());
@VisibleForTesting @VisibleForTesting
boolean mShowAllApps = false; boolean mShowAllApps = false;
@VisibleForTesting @VisibleForTesting
Preference mScreenUsagePref; PowerGaugePreference mScreenUsagePref;
@VisibleForTesting @VisibleForTesting
Preference mScreenConsumptionPref; PowerGaugePreference mLastFullChargePref;
@VisibleForTesting
Preference mCellularNetworkPref;
@VisibleForTesting @VisibleForTesting
PowerUsageFeatureProvider mPowerFeatureProvider; PowerUsageFeatureProvider mPowerFeatureProvider;
@@ -122,9 +122,10 @@ public class PowerUsageSummary extends PowerUsageBase {
mBatteryLayoutPref = (LayoutPreference) findPreference(KEY_BATTERY_HEADER); mBatteryLayoutPref = (LayoutPreference) findPreference(KEY_BATTERY_HEADER);
mAppListGroup = (PreferenceGroup) findPreference(KEY_APP_LIST); mAppListGroup = (PreferenceGroup) findPreference(KEY_APP_LIST);
mScreenUsagePref = findPreference(KEY_SCREEN_USAGE); mScreenUsagePref = (PowerGaugePreference) findPreference(KEY_SCREEN_USAGE);
mScreenConsumptionPref = findPreference(KEY_SCREEN_CONSUMPTION); mLastFullChargePref = (PowerGaugePreference) findPreference(
mCellularNetworkPref = findPreference(KEY_CELLULAR_NETWORK); KEY_TIME_SINCE_LAST_FULL_CHARGE);
mFooterPreferenceMixin.createFooterPreference().setTitle(R.string.battery_footer_summary);
initFeatureProvider(); initFeatureProvider();
} }
@@ -417,8 +418,11 @@ public class PowerUsageSummary extends PowerUsageBase {
final int dischargeAmount = USE_FAKE_DATA ? 5000 final int dischargeAmount = USE_FAKE_DATA ? 5000
: stats != null ? stats.getDischargeAmount(mStatsType) : 0; : stats != null ? stats.getDischargeAmount(mStatsType) : 0;
updateScreenPreference(dischargeAmount); final long runningTime = calculateRunningTimeBasedOnStatsType();
updateCellularPreference(dischargeAmount); updateScreenPreference();
updateLastFullChargePreference(runningTime);
mAppListGroup.setTitle(getString(R.string.power_usage_list_summary,
Utils.formatElapsedTime(context, runningTime, false)));
if (averagePower >= MIN_AVERAGE_POWER_THRESHOLD_MILLI_AMP || USE_FAKE_DATA) { if (averagePower >= MIN_AVERAGE_POWER_THRESHOLD_MILLI_AMP || USE_FAKE_DATA) {
final List<BatterySipper> usageList = getCoalescedUsageList( final List<BatterySipper> usageList = getCoalescedUsageList(
@@ -527,28 +531,27 @@ public class PowerUsageSummary extends PowerUsageBase {
} }
@VisibleForTesting @VisibleForTesting
void updateScreenPreference(final int dischargeAmount) { void updateScreenPreference() {
final BatterySipper sipper = findBatterySipperByType( final BatterySipper sipper = findBatterySipperByType(
mStatsHelper.getUsageList(), DrainType.SCREEN); mStatsHelper.getUsageList(), DrainType.SCREEN);
final Context context = getContext(); final Context context = getContext();
final double totalPowerMah = sipper != null ? sipper.totalPowerMah : 0;
final long usageTimeMs = sipper != null ? sipper.usageTimeMs : 0; final long usageTimeMs = sipper != null ? sipper.usageTimeMs : 0;
final double percentOfTotal = calculatePercentage(totalPowerMah, dischargeAmount);
mScreenUsagePref.setSummary(getString(R.string.battery_used_for, mScreenUsagePref.setSubtitle(Utils.formatElapsedTime(context, usageTimeMs, false));
Utils.formatElapsedTime(context, usageTimeMs, false)));
mScreenConsumptionPref.setSummary(getString(R.string.battery_overall_usage,
Utils.formatPercentage(percentOfTotal, true)));
} }
@VisibleForTesting @VisibleForTesting
void updateCellularPreference(final int dischargeAmount) { void updateLastFullChargePreference(long timeMs) {
final BatterySipper sipper = findBatterySipperByType( mLastFullChargePref.setSubtitle(getString(R.string.power_last_full_charge_summary,
mStatsHelper.getUsageList(), DrainType.CELL); Utils.formatElapsedTime(getContext(), timeMs, false)));
final double totalPowerMah = sipper != null ? sipper.totalPowerMah : 0; }
final double percentOfTotal = calculatePercentage(totalPowerMah, dischargeAmount);
mCellularNetworkPref.setSummary(getString(R.string.battery_overall_usage, @VisibleForTesting
Utils.formatPercentage(percentOfTotal, true))); long calculateRunningTimeBasedOnStatsType() {
final long elapsedRealtimeUs = SystemClock.elapsedRealtime() * 1000;
// Return the battery time (millisecond) on status mStatsType
return mStatsHelper.getStats().computeBatteryRealtime(elapsedRealtimeUs,
mStatsType /* STATS_SINCE_CHARGED */) / 1000;
} }
@VisibleForTesting @VisibleForTesting
@@ -559,22 +562,15 @@ public class PowerUsageSummary extends PowerUsageBase {
} }
final BatteryMeterView batteryView = (BatteryMeterView) mBatteryLayoutPref final BatteryMeterView batteryView = (BatteryMeterView) mBatteryLayoutPref
.findViewById(R.id.battery_header_icon); .findViewById(R.id.battery_header_icon);
final TextView timeText = (TextView) mBatteryLayoutPref.findViewById(R.id.time); final TextView timeText = (TextView) mBatteryLayoutPref.findViewById(R.id.battery_percent);
final TextView summary1 = (TextView) mBatteryLayoutPref.findViewById(R.id.summary1); final TextView summary1 = (TextView) mBatteryLayoutPref.findViewById(R.id.summary1);
final TextView summary2 = (TextView) mBatteryLayoutPref.findViewById(R.id.summary2); timeText.setText(Utils.formatPercentage(info.mBatteryLevel));
final int visible = info.remainingTimeUs != 0 ? View.VISIBLE : View.INVISIBLE; if (info.remainingLabel == null ) {
final int summaryResId = info.mDischarging ? summary1.setText(info.statusLabel);
R.string.estimated_time_left : R.string.estimated_charging_time_left;
if (info.remainingTimeUs != 0) {
timeText.setText(Utils.formatElapsedTime(context, info.remainingTimeUs / 1000, false));
} else { } else {
timeText.setText(info.statusLabel); summary1.setText(info.remainingLabel);
} }
summary1.setText(summaryResId);
summary1.setVisibility(visible);
summary2.setVisibility(visible);
batteryView.setBatteryInfo(info.mBatteryLevel); batteryView.setBatteryInfo(info.mBatteryLevel);
} }

View File

@@ -15,19 +15,17 @@
*/ */
package com.android.settings.fuelgauge; package com.android.settings.fuelgauge;
import android.app.Activity;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.os.PowerManager; import android.os.PowerManager;
import android.os.Process; import android.os.Process;
import android.support.v7.preference.Preference;
import android.text.TextUtils; import android.text.TextUtils;
import android.text.format.DateUtils; import android.text.format.DateUtils;
import android.view.Menu; import android.view.Menu;
import android.view.MenuInflater; import android.view.MenuInflater;
import android.view.MenuItem; import android.view.MenuItem;
import android.view.View;
import android.widget.TextView; import android.widget.TextView;
import com.android.internal.logging.nano.MetricsProto; import com.android.internal.logging.nano.MetricsProto;
import com.android.internal.os.BatterySipper; import com.android.internal.os.BatterySipper;
import com.android.internal.os.BatteryStatsHelper; import com.android.internal.os.BatteryStatsHelper;
@@ -40,6 +38,7 @@ import com.android.settings.Utils;
import com.android.settings.applications.LayoutPreference; import com.android.settings.applications.LayoutPreference;
import com.android.settings.testutils.FakeFeatureFactory; import com.android.settings.testutils.FakeFeatureFactory;
import com.android.settingslib.BatteryInfo; import com.android.settingslib.BatteryInfo;
import org.junit.Before; import org.junit.Before;
import org.junit.Test; import org.junit.Test;
import org.junit.runner.RunWith; import org.junit.runner.RunWith;
@@ -53,13 +52,15 @@ import org.robolectric.annotation.Config;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import static com.android.settings.fuelgauge.PowerUsageBase.MENU_STATS_REFRESH;
import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_ADDITIONAL_BATTERY_INFO; import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_ADDITIONAL_BATTERY_INFO;
import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_HIGH_POWER_APPS; import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_HIGH_POWER_APPS;
import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_TOGGLE_APPS; import static com.android.settings.fuelgauge.PowerUsageSummary.MENU_TOGGLE_APPS;
import static com.google.common.truth.Truth.assertThat; import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Matchers.anyInt; import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.any; import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyLong;
import static org.mockito.Matchers.anyString; import static org.mockito.Matchers.anyString;
import static org.mockito.Matchers.eq; import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.doReturn; import static org.mockito.Mockito.doReturn;
@@ -77,9 +78,13 @@ import static org.mockito.Mockito.when;
public class PowerUsageSummaryTest { public class PowerUsageSummaryTest {
private static final String[] PACKAGE_NAMES = {"com.app1", "com.app2"}; private static final String[] PACKAGE_NAMES = {"com.app1", "com.app2"};
private static final String TIME_LEFT = "2h30min"; private static final String TIME_LEFT = "2h30min";
private static final int BATTERY_LEVEL = 55;
private static final int UID = 123; private static final int UID = 123;
private static final int POWER_MAH = 100; private static final int POWER_MAH = 100;
private static final long REMAINING_TIME_US = 100000; private static final long REMAINING_TIME_US = 100000;
private static final long TIME_SINCE_LAST_FULL_CHARGE_MS = 25000;
private static final long TIME_SINCE_LAST_FULL_CHARGE_US =
TIME_SINCE_LAST_FULL_CHARGE_MS * 1000;
private static final int DISCHARGE_AMOUNT = 100; private static final int DISCHARGE_AMOUNT = 100;
private static final long USAGE_TIME_MS = 10000; private static final long USAGE_TIME_MS = 10000;
private static final double TOTAL_POWER = 200; private static final double TOTAL_POWER = 200;
@@ -117,20 +122,16 @@ public class PowerUsageSummaryTest {
@Mock @Mock
private BatteryMeterView mBatteryMeterView; private BatteryMeterView mBatteryMeterView;
@Mock @Mock
private TextView mTimeText; private TextView mBatteryPercentText;
@Mock @Mock
private TextView mSummary1; private TextView mSummary1;
@Mock @Mock
private TextView mSummary2;
@Mock
private BatteryInfo mBatteryInfo; private BatteryInfo mBatteryInfo;
@Mock @Mock
private Preference mScreenUsagePref; private PowerGaugePreference mScreenUsagePref;
@Mock
private Preference mScreenConsumptionPref;
@Mock
private Preference mCellularNetworkPref;
@Mock @Mock
private PowerGaugePreference mLastFullChargePref;
@Mock(answer = Answers.RETURNS_DEEP_STUBS)
private BatteryStatsHelper mBatteryHelper; private BatteryStatsHelper mBatteryHelper;
@Mock @Mock
private PowerManager mPowerManager; private PowerManager mPowerManager;
@@ -162,6 +163,8 @@ public class PowerUsageSummaryTest {
when(mFeatureFactory.powerUsageFeatureProvider.getAdditionalBatteryInfoIntent()) when(mFeatureFactory.powerUsageFeatureProvider.getAdditionalBatteryInfoIntent())
.thenReturn(ADDITIONAL_BATTERY_INFO_INTENT); .thenReturn(ADDITIONAL_BATTERY_INFO_INTENT);
when(mBatteryHelper.getTotalPower()).thenReturn(TOTAL_POWER); when(mBatteryHelper.getTotalPower()).thenReturn(TOTAL_POWER);
when(mBatteryHelper.getStats().computeBatteryRealtime(anyLong(), anyInt())).thenReturn(
TIME_SINCE_LAST_FULL_CHARGE_US);
when(mNormalBatterySipper.getPackages()).thenReturn(PACKAGE_NAMES); when(mNormalBatterySipper.getPackages()).thenReturn(PACKAGE_NAMES);
when(mNormalBatterySipper.getUid()).thenReturn(UID); when(mNormalBatterySipper.getUid()).thenReturn(UID);
@@ -172,8 +175,7 @@ public class PowerUsageSummaryTest {
mCellBatterySipper.totalPowerMah = POWER_MAH; mCellBatterySipper.totalPowerMah = POWER_MAH;
when(mBatteryLayoutPref.findViewById(R.id.summary1)).thenReturn(mSummary1); when(mBatteryLayoutPref.findViewById(R.id.summary1)).thenReturn(mSummary1);
when(mBatteryLayoutPref.findViewById(R.id.summary2)).thenReturn(mSummary2); when(mBatteryLayoutPref.findViewById(R.id.battery_percent)).thenReturn(mBatteryPercentText);
when(mBatteryLayoutPref.findViewById(R.id.time)).thenReturn(mTimeText);
when(mBatteryLayoutPref.findViewById(R.id.battery_header_icon)) when(mBatteryLayoutPref.findViewById(R.id.battery_header_icon))
.thenReturn(mBatteryMeterView); .thenReturn(mBatteryMeterView);
mFragment.setBatteryLayoutPreference(mBatteryLayoutPref); mFragment.setBatteryLayoutPreference(mBatteryLayoutPref);
@@ -194,8 +196,9 @@ public class PowerUsageSummaryTest {
mFragment.mStatsHelper = mBatteryHelper; mFragment.mStatsHelper = mBatteryHelper;
when(mBatteryHelper.getUsageList()).thenReturn(mUsageList); when(mBatteryHelper.getUsageList()).thenReturn(mUsageList);
mFragment.mScreenUsagePref = mScreenUsagePref; mFragment.mScreenUsagePref = mScreenUsagePref;
mFragment.mScreenConsumptionPref = mScreenConsumptionPref; mFragment.mLastFullChargePref = mLastFullChargePref;
mFragment.mCellularNetworkPref = mCellularNetworkPref;
mBatteryInfo.mBatteryLevel = BATTERY_LEVEL;
} }
@Test @Test
@@ -226,7 +229,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testOptionsMenu_MenuHighPower_MetricEventInvoked() { public void testOptionsMenu_menuHighPower_metricEventInvoked() {
mFragment.onOptionsItemSelected(mHighPowerMenu); mFragment.onOptionsItemSelected(mHighPowerMenu);
verify(mFeatureFactory.metricsFeatureProvider).action(mContext, verify(mFeatureFactory.metricsFeatureProvider).action(mContext,
@@ -234,7 +237,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testOptionsMenu_MenuAdditionalBattery_MetricEventInvoked() { public void testOptionsMenu_menuAdditionalBattery_metricEventInvoked() {
mFragment.onOptionsItemSelected(mAdditionalBatteryInfoMenu); mFragment.onOptionsItemSelected(mAdditionalBatteryInfoMenu);
verify(mFeatureFactory.metricsFeatureProvider).action(mContext, verify(mFeatureFactory.metricsFeatureProvider).action(mContext,
@@ -242,7 +245,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testOptionsMenu_MenuAppToggle_MetricEventInvoked() { public void testOptionsMenu_menuAppToggle_metricEventInvoked() {
mFragment.onOptionsItemSelected(mToggleAppsMenu); mFragment.onOptionsItemSelected(mToggleAppsMenu);
mFragment.mShowAllApps = false; mFragment.mShowAllApps = false;
@@ -251,7 +254,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testOptionsMenu_ToggleAppsEnabled() { public void testOptionsMenu_toggleAppsEnabled() {
when(mFeatureFactory.powerUsageFeatureProvider.isPowerAccountingToggleEnabled()) when(mFeatureFactory.powerUsageFeatureProvider.isPowerAccountingToggleEnabled())
.thenReturn(true); .thenReturn(true);
mFragment.mShowAllApps = false; mFragment.mShowAllApps = false;
@@ -262,13 +265,13 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testOptionsMenu_ClickToggleAppsMenu_DataChanged() { public void testOptionsMenu_clickToggleAppsMenu_dataChanged() {
testToggleAllApps(true); testToggleAllApps(true);
testToggleAllApps(false); testToggleAllApps(false);
} }
@Test @Test
public void testExtractKeyFromSipper_TypeAPPUidObjectNull_ReturnPackageNames() { public void testExtractKeyFromSipper_typeAPPUidObjectNull_returnPackageNames() {
mNormalBatterySipper.uidObj = null; mNormalBatterySipper.uidObj = null;
mNormalBatterySipper.drainType = BatterySipper.DrainType.APP; mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
@@ -277,7 +280,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testExtractKeyFromSipper_TypeOther_ReturnDrainType() { public void testExtractKeyFromSipper_typeOther_returnDrainType() {
mNormalBatterySipper.uidObj = null; mNormalBatterySipper.uidObj = null;
mNormalBatterySipper.drainType = BatterySipper.DrainType.BLUETOOTH; mNormalBatterySipper.drainType = BatterySipper.DrainType.BLUETOOTH;
@@ -286,7 +289,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testExtractKeyFromSipper_TypeAPPUidObjectNotNull_ReturnUid() { public void testExtractKeyFromSipper_typeAPPUidObjectNotNull_returnUid() {
mNormalBatterySipper.uidObj = new BatteryStatsImpl.Uid(new BatteryStatsImpl(), UID); mNormalBatterySipper.uidObj = new BatteryStatsImpl.Uid(new BatteryStatsImpl(), UID);
mNormalBatterySipper.drainType = BatterySipper.DrainType.APP; mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
@@ -295,7 +298,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testRemoveHiddenBatterySippers_ContainsHiddenSippers_RemoveAndReturnValue() { public void testRemoveHiddenBatterySippers_containsHiddenSippers_removeAndReturnValue() {
final List<BatterySipper> sippers = new ArrayList<>(); final List<BatterySipper> sippers = new ArrayList<>();
sippers.add(mNormalBatterySipper); sippers.add(mNormalBatterySipper);
sippers.add(mScreenBatterySipper); sippers.add(mScreenBatterySipper);
@@ -309,37 +312,37 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testShouldHideSipper_TypeIdle_ReturnTrue() { public void testShouldHideSipper_typeIdle_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.IDLE; mNormalBatterySipper.drainType = BatterySipper.DrainType.IDLE;
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue();
} }
@Test @Test
public void testShouldHideSipper_TypeWifi_ReturnTrue() { public void testShouldHideSipper_typeWifi_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.WIFI; mNormalBatterySipper.drainType = BatterySipper.DrainType.WIFI;
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue();
} }
@Test @Test
public void testShouldHideSipper_TypeCell_ReturnTrue() { public void testShouldHideSipper_typeCell_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.CELL; mNormalBatterySipper.drainType = BatterySipper.DrainType.CELL;
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue();
} }
@Test @Test
public void testShouldHideSipper_TypeScreen_ReturnTrue() { public void testShouldHideSipper_typeScreen_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.SCREEN; mNormalBatterySipper.drainType = BatterySipper.DrainType.SCREEN;
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue();
} }
@Test @Test
public void testShouldHideSipper_TypeBluetooth_ReturnTrue() { public void testShouldHideSipper_typeBluetooth_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.BLUETOOTH; mNormalBatterySipper.drainType = BatterySipper.DrainType.BLUETOOTH;
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isTrue();
} }
@Test @Test
public void testShouldHideSipper_TypeSystem_ReturnTrue() { public void testShouldHideSipper_typeSystem_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.APP; mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
when(mNormalBatterySipper.getUid()).thenReturn(Process.ROOT_UID); when(mNormalBatterySipper.getUid()).thenReturn(Process.ROOT_UID);
when(mFeatureFactory.powerUsageFeatureProvider.isTypeSystem(Matchers.<BatterySipper>any())) when(mFeatureFactory.powerUsageFeatureProvider.isTypeSystem(Matchers.<BatterySipper>any()))
@@ -348,14 +351,14 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testShouldHideSipper_UidNormal_ReturnFalse() { public void testShouldHideSipper_uidNormal_returnFalse() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.APP; mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
when(mNormalBatterySipper.getUid()).thenReturn(UID); when(mNormalBatterySipper.getUid()).thenReturn(UID);
assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isFalse(); assertThat(mFragment.shouldHideSipper(mNormalBatterySipper)).isFalse();
} }
@Test @Test
public void testShouldHideSipper_TypeService_ReturnTrue() { public void testShouldHideSipper_typeService_returnTrue() {
mNormalBatterySipper.drainType = BatterySipper.DrainType.APP; mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
when(mNormalBatterySipper.getUid()).thenReturn(UID); when(mNormalBatterySipper.getUid()).thenReturn(UID);
when(mFeatureFactory.powerUsageFeatureProvider.isTypeService(Matchers.<BatterySipper>any())) when(mFeatureFactory.powerUsageFeatureProvider.isTypeService(Matchers.<BatterySipper>any()))
@@ -365,7 +368,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testSetUsageSummary_TimeLessThanOneMinute_DoNotSetSummary() { public void testSetUsageSummary_timeLessThanOneMinute_doNotSetSummary() {
final long usageTimeMs = 59 * DateUtils.SECOND_IN_MILLIS; final long usageTimeMs = 59 * DateUtils.SECOND_IN_MILLIS;
mFragment.setUsageSummary(mPreference, "", usageTimeMs); mFragment.setUsageSummary(mPreference, "", usageTimeMs);
@@ -373,7 +376,7 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testSetUsageSummary_TimeMoreThanOneMinute_SetSummary() { public void testSetUsageSummary_timeMoreThanOneMinute_setSummary() {
final long usageTimeMs = 2 * DateUtils.MINUTE_IN_MILLIS; final long usageTimeMs = 2 * DateUtils.MINUTE_IN_MILLIS;
mFragment.setUsageSummary(mPreference, "", usageTimeMs); mFragment.setUsageSummary(mPreference, "", usageTimeMs);
@@ -381,45 +384,25 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testUpdatePreference_NoEstimatedTime_DoNotShowSummary() { public void testUpdatePreference_hasRemainingTime_showRemainingLabel() {
mBatteryInfo.remainingTimeUs = 0;
mBatteryInfo.remainingLabel = TIME_LEFT; mBatteryInfo.remainingLabel = TIME_LEFT;
mFragment.updateHeaderPreference(mBatteryInfo); mFragment.updateHeaderPreference(mBatteryInfo);
verify(mSummary1).setVisibility(View.INVISIBLE); verify(mSummary1).setText(mBatteryInfo.remainingLabel);
verify(mSummary2).setVisibility(View.INVISIBLE);
} }
@Test @Test
public void testUpdatePreference_HasEstimatedTime_ShowSummary() { public void testUpdatePreference_noRemainingTime_showStatusLabel() {
mBatteryInfo.remainingTimeUs = REMAINING_TIME_US; mBatteryInfo.remainingLabel = null;
mBatteryInfo.remainingLabel = TIME_LEFT;
mFragment.updateHeaderPreference(mBatteryInfo); mFragment.updateHeaderPreference(mBatteryInfo);
verify(mSummary1).setVisibility(View.VISIBLE); verify(mSummary1).setText(mBatteryInfo.statusLabel);
verify(mSummary2).setVisibility(View.VISIBLE);
} }
@Test @Test
public void testUpdatePreference_Charging_ShowChargingTimeLeft() { public void testUpdateHeaderPreference_asyncUpdate_shouldNotCrash() {
mBatteryInfo.remainingTimeUs = REMAINING_TIME_US;
mBatteryInfo.mDischarging = false;
mFragment.updateHeaderPreference(mBatteryInfo);
verify(mSummary1).setText(R.string.estimated_charging_time_left);
}
@Test
public void testUpdatePreference_NotCharging_ShowTimeLeft() {
mBatteryInfo.remainingTimeUs = REMAINING_TIME_US;
mBatteryInfo.mDischarging = true;
mFragment.updateHeaderPreference(mBatteryInfo);
verify(mSummary1).setText(R.string.estimated_time_left);
}
@Test
public void testUpdateHeaderPreference_AsyncUpdate_ShouldNotCrash() {
when(mFragment.getContext()).thenReturn(null); when(mFragment.getContext()).thenReturn(null);
mBatteryInfo.remainingTimeUs = REMAINING_TIME_US; mBatteryInfo.remainingTimeUs = REMAINING_TIME_US;
@@ -451,43 +434,36 @@ public class PowerUsageSummaryTest {
} }
@Test @Test
public void testUpdateCellularPreference_ShowCorrectSummary() { public void testUpdateScreenPreference_showCorrectSummary() {
final double percent = POWER_MAH / TOTAL_POWER * DISCHARGE_AMOUNT; final String expectedUsedTime = Utils.formatElapsedTime(mRealContext, USAGE_TIME_MS, false);
final String expectedSummary = mRealContext.getString(R.string.battery_overall_usage, doReturn(mScreenBatterySipper).when(mFragment).findBatterySipperByType(any(), any());
Utils.formatPercentage((int) percent)); doReturn(mRealContext).when(mFragment).getContext();
doReturn(expectedSummary).when(mFragment)
.getString(eq(R.string.battery_overall_usage), anyInt());
mFragment.updateCellularPreference(DISCHARGE_AMOUNT);
verify(mCellularNetworkPref).setSummary(expectedSummary); mFragment.updateScreenPreference();
verify(mScreenUsagePref).setSubtitle(expectedUsedTime);
} }
@Test @Test
public void testUpdateScreenPreference_ShowCorrectSummary() { public void testUpdateLastFullChargePreference_showCorrectSummary() {
final String expectedUsedTime = mRealContext.getString(R.string.battery_used_for, doReturn(mRealContext).when(mFragment).getContext();
Utils.formatElapsedTime(mRealContext, USAGE_TIME_MS, false)); final String expected = mRealContext.getString(R.string.power_last_full_charge_summary,
final double percent = BATTERY_SCREEN_USAGE / TOTAL_POWER * DISCHARGE_AMOUNT; Utils.formatElapsedTime(mRealContext, TIME_SINCE_LAST_FULL_CHARGE_MS, false));
final String expectedOverallUsage = mRealContext.getString(R.string.battery_overall_usage, doReturn(expected).when(mFragment).getString(eq(R.string.power_last_full_charge_summary),
Utils.formatPercentage((int) percent)); any());
doReturn(expectedUsedTime).when(mFragment).getString(
eq(R.string.battery_used_for), anyInt());
doReturn(expectedOverallUsage).when(mFragment).getString(
eq(R.string.battery_overall_usage), anyInt());
mFragment.updateScreenPreference(DISCHARGE_AMOUNT); mFragment.updateLastFullChargePreference(TIME_SINCE_LAST_FULL_CHARGE_MS);
verify(mScreenUsagePref).setSummary(expectedUsedTime); verify(mLastFullChargePref).setSubtitle(expected);
verify(mScreenConsumptionPref).setSummary(expectedOverallUsage);
} }
@Test @Test
public void testUpdatePreference_UsageListEmpty_ShouldNotCrash() { public void testUpdatePreference_usageListEmpty_shouldNotCrash() {
when(mBatteryHelper.getUsageList()).thenReturn(new ArrayList<BatterySipper>()); when(mBatteryHelper.getUsageList()).thenReturn(new ArrayList<BatterySipper>());
doReturn("").when(mFragment).getString(anyInt(), Matchers.anyObject()); doReturn("").when(mFragment).getString(anyInt(), any());
// Should not crash when update // Should not crash when update
mFragment.updateScreenPreference(DISCHARGE_AMOUNT); mFragment.updateScreenPreference();
mFragment.updateCellularPreference(DISCHARGE_AMOUNT);
} }
@Test @Test
@@ -496,6 +472,12 @@ public class PowerUsageSummaryTest {
assertThat(percent).isWithin(PRECISION).of(POWER_USAGE_PERCENTAGE); assertThat(percent).isWithin(PRECISION).of(POWER_USAGE_PERCENTAGE);
} }
@Test
public void testCalculateRunningTimeBasedOnStatsType() {
assertThat(mFragment.calculateRunningTimeBasedOnStatsType()).isEqualTo(
TIME_SINCE_LAST_FULL_CHARGE_MS);
}
public static class TestFragment extends PowerUsageSummary { public static class TestFragment extends PowerUsageSummary {
private Context mContext; private Context mContext;