Adjust battery tips action

- Change low battery tips action to launch battery saver page
 - Enable smart battery tip when battery level is lower than expected and battery saver is off

Bug: 183582881
Test: make RunSettingsRoboTests -j40
Change-Id: I38b0ff7109d5ea95703edeade26cdfeed50f1403
This commit is contained in:
Wesley.CW Wang
2021-03-24 16:56:16 +08:00
committed by Wesley Wang
parent 89222adb7f
commit f1e41c0bd9
5 changed files with 61 additions and 31 deletions

View File

@@ -69,7 +69,8 @@ public class BatteryTipLoader extends AsyncLoaderCompat<List<BatteryTip>> {
tips.add(new LowBatteryDetector(context, policy, batteryInfo).detect()); tips.add(new LowBatteryDetector(context, policy, batteryInfo).detect());
tips.add(new HighUsageDetector(context, policy, mBatteryUsageStats, batteryInfo).detect()); tips.add(new HighUsageDetector(context, policy, mBatteryUsageStats, batteryInfo).detect());
tips.add(new SmartBatteryDetector(policy, context.getContentResolver()).detect()); tips.add(new SmartBatteryDetector(
context, policy, batteryInfo, context.getContentResolver()).detect());
tips.add(new EarlyWarningDetector(policy, context).detect()); tips.add(new EarlyWarningDetector(policy, context).detect());
tips.add(new BatteryDefenderDetector(batteryInfo).detect()); tips.add(new BatteryDefenderDetector(batteryInfo).detect());
// Disable this feature now since it introduces false positive cases. We will try to improve // Disable this feature now since it introduces false positive cases. We will try to improve

View File

@@ -30,7 +30,6 @@ import com.android.internal.util.CollectionUtils;
import com.android.settings.SettingsActivity; import com.android.settings.SettingsActivity;
import com.android.settings.core.InstrumentedPreferenceFragment; import com.android.settings.core.InstrumentedPreferenceFragment;
import com.android.settings.fuelgauge.batterytip.actions.BatteryDefenderAction; import com.android.settings.fuelgauge.batterytip.actions.BatteryDefenderAction;
import com.android.settings.fuelgauge.batterytip.actions.BatterySaverAction;
import com.android.settings.fuelgauge.batterytip.actions.BatteryTipAction; import com.android.settings.fuelgauge.batterytip.actions.BatteryTipAction;
import com.android.settings.fuelgauge.batterytip.actions.OpenBatterySaverAction; import com.android.settings.fuelgauge.batterytip.actions.OpenBatterySaverAction;
import com.android.settings.fuelgauge.batterytip.actions.OpenRestrictAppFragmentAction; import com.android.settings.fuelgauge.batterytip.actions.OpenRestrictAppFragmentAction;
@@ -99,11 +98,7 @@ public class BatteryTipUtils {
return new SmartBatteryAction(settingsActivity, fragment); return new SmartBatteryAction(settingsActivity, fragment);
case BatteryTip.TipType.BATTERY_SAVER: case BatteryTip.TipType.BATTERY_SAVER:
case BatteryTip.TipType.LOW_BATTERY: case BatteryTip.TipType.LOW_BATTERY:
if (batteryTip.getState() == BatteryTip.StateType.HANDLED) { return new OpenBatterySaverAction(settingsActivity);
return new OpenBatterySaverAction(settingsActivity);
} else {
return new BatterySaverAction(settingsActivity);
}
case BatteryTip.TipType.APP_RESTRICTION: case BatteryTip.TipType.APP_RESTRICTION:
if (batteryTip.getState() == BatteryTip.StateType.HANDLED) { if (batteryTip.getState() == BatteryTip.StateType.HANDLED) {
return new OpenRestrictAppFragmentAction(fragment, (RestrictAppTip) batteryTip); return new OpenRestrictAppFragmentAction(fragment, (RestrictAppTip) batteryTip);

View File

@@ -17,8 +17,11 @@
package com.android.settings.fuelgauge.batterytip.detectors; package com.android.settings.fuelgauge.batterytip.detectors;
import android.content.ContentResolver; import android.content.ContentResolver;
import android.content.Context;
import android.os.PowerManager;
import android.provider.Settings; import android.provider.Settings;
import com.android.settings.fuelgauge.BatteryInfo;
import com.android.settings.fuelgauge.batterytip.BatteryTipPolicy; import com.android.settings.fuelgauge.batterytip.BatteryTipPolicy;
import com.android.settings.fuelgauge.batterytip.tips.BatteryTip; import com.android.settings.fuelgauge.batterytip.tips.BatteryTip;
import com.android.settings.fuelgauge.batterytip.tips.SmartBatteryTip; import com.android.settings.fuelgauge.batterytip.tips.SmartBatteryTip;
@@ -27,22 +30,33 @@ import com.android.settings.fuelgauge.batterytip.tips.SmartBatteryTip;
* Detect whether to show smart battery tip. * Detect whether to show smart battery tip.
*/ */
public class SmartBatteryDetector implements BatteryTipDetector { public class SmartBatteryDetector implements BatteryTipDetector {
private static final int EXPECTED_BATTERY_LEVEL = 30;
private BatteryInfo mBatteryInfo;
private BatteryTipPolicy mPolicy; private BatteryTipPolicy mPolicy;
private ContentResolver mContentResolver; private ContentResolver mContentResolver;
private PowerManager mPowerManager;
public SmartBatteryDetector(BatteryTipPolicy policy, ContentResolver contentResolver) { public SmartBatteryDetector(Context context, BatteryTipPolicy policy, BatteryInfo batteryInfo,
ContentResolver contentResolver) {
mPolicy = policy; mPolicy = policy;
mBatteryInfo = batteryInfo;
mContentResolver = contentResolver; mContentResolver = contentResolver;
mPowerManager = context.getSystemService(PowerManager.class);
} }
@Override @Override
public BatteryTip detect() { public BatteryTip detect() {
// Show it if there is no other tips shown
final boolean smartBatteryOff = Settings.Global.getInt(mContentResolver, final boolean smartBatteryOff = Settings.Global.getInt(mContentResolver,
Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 1) == 0 Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 1) == 0;
final boolean isUnderExpectedBatteryLevel =
mBatteryInfo.batteryLevel <= EXPECTED_BATTERY_LEVEL;
// Show it if in test or smart battery is off.
final boolean enableSmartBatteryTip =
smartBatteryOff && !mPowerManager.isPowerSaveMode() && isUnderExpectedBatteryLevel
|| mPolicy.testSmartBatteryTip; || mPolicy.testSmartBatteryTip;
final int state = final int state =
smartBatteryOff ? BatteryTip.StateType.NEW : BatteryTip.StateType.INVISIBLE; enableSmartBatteryTip ? BatteryTip.StateType.NEW : BatteryTip.StateType.INVISIBLE;
return new SmartBatteryTip(state); return new SmartBatteryTip(state);
} }
} }

View File

@@ -24,7 +24,6 @@ import static org.mockito.Mockito.when;
import com.android.settings.SettingsActivity; import com.android.settings.SettingsActivity;
import com.android.settings.core.InstrumentedPreferenceFragment; import com.android.settings.core.InstrumentedPreferenceFragment;
import com.android.settings.fuelgauge.batterytip.actions.BatteryDefenderAction; import com.android.settings.fuelgauge.batterytip.actions.BatteryDefenderAction;
import com.android.settings.fuelgauge.batterytip.actions.BatterySaverAction;
import com.android.settings.fuelgauge.batterytip.actions.OpenBatterySaverAction; import com.android.settings.fuelgauge.batterytip.actions.OpenBatterySaverAction;
import com.android.settings.fuelgauge.batterytip.actions.OpenRestrictAppFragmentAction; import com.android.settings.fuelgauge.batterytip.actions.OpenRestrictAppFragmentAction;
import com.android.settings.fuelgauge.batterytip.actions.RestrictAppAction; import com.android.settings.fuelgauge.batterytip.actions.RestrictAppAction;
@@ -90,33 +89,17 @@ public class BatteryTipUtilsTest {
} }
@Test @Test
public void testGetActionForBatteryTip_typeEarlyWarningStateNew_returnActionBatterySaver() { public void testGetActionForBatteryTip_typeEarlyWarningStateNew_returnActionOpen() {
when(mEarlyWarningTip.getState()).thenReturn(BatteryTip.StateType.NEW); when(mEarlyWarningTip.getState()).thenReturn(BatteryTip.StateType.NEW);
assertThat(BatteryTipUtils.getActionForBatteryTip(mEarlyWarningTip, mSettingsActivity,
mFragment)).isInstanceOf(BatterySaverAction.class);
}
@Test
public void testGetActionForBatteryTip_typeEarlyWarningStateHandled_returnActionOpen() {
when(mEarlyWarningTip.getState()).thenReturn(BatteryTip.StateType.HANDLED);
assertThat(BatteryTipUtils.getActionForBatteryTip(mEarlyWarningTip, mSettingsActivity, assertThat(BatteryTipUtils.getActionForBatteryTip(mEarlyWarningTip, mSettingsActivity,
mFragment)).isInstanceOf(OpenBatterySaverAction.class); mFragment)).isInstanceOf(OpenBatterySaverAction.class);
} }
@Test @Test
public void testGetActionForBatteryTip_typeLowBatteryStateNew_returnActionBatterySaver() { public void testGetActionForBatteryTip_typeLowBatteryStateNew_returnActionOpen() {
when(mLowBatteryTip.getState()).thenReturn(BatteryTip.StateType.NEW); when(mLowBatteryTip.getState()).thenReturn(BatteryTip.StateType.NEW);
assertThat(BatteryTipUtils.getActionForBatteryTip(mLowBatteryTip, mSettingsActivity,
mFragment)).isInstanceOf(BatterySaverAction.class);
}
@Test
public void testGetActionForBatteryTip_typeLowBatteryStateHandled_returnActionOpen() {
when(mLowBatteryTip.getState()).thenReturn(BatteryTip.StateType.HANDLED);
assertThat(BatteryTipUtils.getActionForBatteryTip(mLowBatteryTip, mSettingsActivity, assertThat(BatteryTipUtils.getActionForBatteryTip(mLowBatteryTip, mSettingsActivity,
mFragment)).isInstanceOf(OpenBatterySaverAction.class); mFragment)).isInstanceOf(OpenBatterySaverAction.class);
} }

View File

@@ -22,26 +22,37 @@ import static org.mockito.Mockito.spy;
import android.content.ContentResolver; import android.content.ContentResolver;
import android.content.Context; import android.content.Context;
import android.os.PowerManager;
import android.provider.Settings; import android.provider.Settings;
import com.android.settings.fuelgauge.BatteryInfo;
import com.android.settings.fuelgauge.batterytip.BatteryTipPolicy; import com.android.settings.fuelgauge.batterytip.BatteryTipPolicy;
import com.android.settings.fuelgauge.batterytip.tips.BatteryTip; import com.android.settings.fuelgauge.batterytip.tips.BatteryTip;
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;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations; import org.mockito.MockitoAnnotations;
import org.robolectric.RobolectricTestRunner; import org.robolectric.RobolectricTestRunner;
import org.robolectric.RuntimeEnvironment; import org.robolectric.RuntimeEnvironment;
import org.robolectric.Shadows;
import org.robolectric.shadows.ShadowPowerManager;
import org.robolectric.util.ReflectionHelpers; import org.robolectric.util.ReflectionHelpers;
@RunWith(RobolectricTestRunner.class) @RunWith(RobolectricTestRunner.class)
public class SmartBatteryDetectorTest { public class SmartBatteryDetectorTest {
private static final int EXPECTED_BATTERY_LEVEL = 30;
private static final int UNEXPECTED_BATTERY_LEVEL = 31;
private Context mContext; private Context mContext;
private ContentResolver mContentResolver; private ContentResolver mContentResolver;
private SmartBatteryDetector mSmartBatteryDetector; private SmartBatteryDetector mSmartBatteryDetector;
private BatteryTipPolicy mPolicy; private BatteryTipPolicy mPolicy;
private ShadowPowerManager mShadowPowerManager;
@Mock
private BatteryInfo mBatteryInfo;
@Before @Before
public void setUp() { public void setUp() {
@@ -50,7 +61,9 @@ public class SmartBatteryDetectorTest {
mContext = RuntimeEnvironment.application; mContext = RuntimeEnvironment.application;
mContentResolver = mContext.getContentResolver(); mContentResolver = mContext.getContentResolver();
mPolicy = spy(new BatteryTipPolicy(mContext)); mPolicy = spy(new BatteryTipPolicy(mContext));
mSmartBatteryDetector = new SmartBatteryDetector(mPolicy, mContentResolver); mShadowPowerManager = Shadows.shadowOf(mContext.getSystemService(PowerManager.class));
mSmartBatteryDetector =
new SmartBatteryDetector(mContext, mPolicy, mBatteryInfo, mContentResolver);
} }
@Test @Test
@@ -64,14 +77,38 @@ public class SmartBatteryDetectorTest {
public void testDetect_smartBatteryOff_tipVisible() { public void testDetect_smartBatteryOff_tipVisible() {
Settings.Global.putInt(mContentResolver, Settings.Global.putInt(mContentResolver,
Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 0); Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 0);
mShadowPowerManager.setIsPowerSaveMode(false);
mBatteryInfo.batteryLevel = EXPECTED_BATTERY_LEVEL;
assertThat(mSmartBatteryDetector.detect().isVisible()).isTrue(); assertThat(mSmartBatteryDetector.detect().isVisible()).isTrue();
} }
@Test
public void testDetect_batterySaverOn_tipInvisible() {
Settings.Global.putInt(mContentResolver,
Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 0);
mShadowPowerManager.setIsPowerSaveMode(true);
mBatteryInfo.batteryLevel = EXPECTED_BATTERY_LEVEL;
assertThat(mSmartBatteryDetector.detect().isVisible()).isFalse();
}
@Test
public void testDetect_unexpectedBatteryLevel_tipInvisible() {
Settings.Global.putInt(mContentResolver,
Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 0);
mShadowPowerManager.setIsPowerSaveMode(true);
mBatteryInfo.batteryLevel = UNEXPECTED_BATTERY_LEVEL;
assertThat(mSmartBatteryDetector.detect().isVisible()).isFalse();
}
@Test @Test
public void testDetect_smartBatteryOn_tipInvisible() { public void testDetect_smartBatteryOn_tipInvisible() {
Settings.Global.putInt(mContentResolver, Settings.Global.putInt(mContentResolver,
Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 1); Settings.Global.ADAPTIVE_BATTERY_MANAGEMENT_ENABLED, 1);
mShadowPowerManager.setIsPowerSaveMode(false);
mBatteryInfo.batteryLevel = EXPECTED_BATTERY_LEVEL;
assertThat(mSmartBatteryDetector.detect().isVisible()).isFalse(); assertThat(mSmartBatteryDetector.detect().isVisible()).isFalse();
} }