Transition BatteryInfo and BatteryUtils to BatteryUsageStats API
Bug: 173745486 Test: make RunSettingsRoboTests ROBOTEST_FILTER=com.android.settings.fuelgauge.BatteryHistoryPreferenceTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=com.android.settings.fuelgauge.BatteryInfoLoaderTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=com.android.settings.fuelgauge.BatteryInfoTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=com.android.settings.fuelgauge.BatteryUtilsTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=com.android.settings.fuelgauge.batterytip.detectors Change-Id: I469ff8b88aa3307422c02f51943df4ef1759db56
This commit is contained in:
@@ -20,16 +20,18 @@ import android.content.IntentFilter;
|
||||
import android.content.res.Resources;
|
||||
import android.os.AsyncTask;
|
||||
import android.os.BatteryManager;
|
||||
import android.os.BatteryStats;
|
||||
import android.os.BatteryStats.HistoryItem;
|
||||
import android.os.Bundle;
|
||||
import android.os.BatteryStatsManager;
|
||||
import android.os.BatteryUsageStats;
|
||||
import android.os.SystemClock;
|
||||
import android.text.format.Formatter;
|
||||
import android.util.SparseIntArray;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.annotation.WorkerThread;
|
||||
|
||||
import com.android.internal.os.BatteryStatsHelper;
|
||||
import com.android.internal.os.BatteryStatsHistoryIterator;
|
||||
import com.android.settings.Utils;
|
||||
import com.android.settings.overlay.FeatureFactory;
|
||||
import com.android.settings.widget.UsageView;
|
||||
@@ -52,7 +54,7 @@ public class BatteryInfo {
|
||||
public String statusLabel;
|
||||
public String suggestionLabel;
|
||||
private boolean mCharging;
|
||||
private BatteryStats mStats;
|
||||
private BatteryUsageStats mBatteryUsageStats;
|
||||
private static final String LOG_TAG = "BatteryInfo";
|
||||
private long timePeriod;
|
||||
|
||||
@@ -126,7 +128,7 @@ public class BatteryInfo {
|
||||
parserList[i] = parsers[i];
|
||||
}
|
||||
parserList[parsers.length] = parser;
|
||||
parse(mStats, parserList);
|
||||
parseBatteryHistory(parserList);
|
||||
String timeString = context.getString(R.string.charge_length_format,
|
||||
Formatter.formatShortElapsedTime(context, timePeriod));
|
||||
String remaining = "";
|
||||
@@ -137,22 +139,25 @@ public class BatteryInfo {
|
||||
view.setBottomLabels(new CharSequence[]{timeString, remaining});
|
||||
}
|
||||
|
||||
public static void getBatteryInfo(final Context context, final Callback callback) {
|
||||
BatteryInfo.getBatteryInfo(context, callback, null /* statsHelper */,
|
||||
false /* shortString */);
|
||||
}
|
||||
|
||||
public static void getBatteryInfo(final Context context, final Callback callback,
|
||||
boolean shortString) {
|
||||
BatteryInfo.getBatteryInfo(context, callback, null /* statsHelper */, shortString);
|
||||
BatteryInfo.getBatteryInfo(context, callback, /* batteryUsageStats */ null, shortString);
|
||||
}
|
||||
|
||||
public static void getBatteryInfo(final Context context, final Callback callback,
|
||||
final BatteryStatsHelper statsHelper, boolean shortString) {
|
||||
@Nullable final BatteryUsageStats batteryUsageStats,
|
||||
boolean shortString) {
|
||||
new AsyncTask<Void, Void, BatteryInfo>() {
|
||||
@Override
|
||||
protected BatteryInfo doInBackground(Void... params) {
|
||||
return getBatteryInfo(context, statsHelper, shortString);
|
||||
BatteryUsageStats stats;
|
||||
if (batteryUsageStats != null) {
|
||||
stats = batteryUsageStats;
|
||||
} else {
|
||||
stats = context.getSystemService(BatteryStatsManager.class)
|
||||
.getBatteryUsageStats();
|
||||
}
|
||||
return getBatteryInfo(context, stats, shortString);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -164,18 +169,13 @@ public class BatteryInfo {
|
||||
}.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a BatteryInfo based on BatteryUsageStats
|
||||
*/
|
||||
@WorkerThread
|
||||
public static BatteryInfo getBatteryInfo(final Context context,
|
||||
final BatteryStatsHelper statsHelper, boolean shortString) {
|
||||
final BatteryStats stats;
|
||||
@NonNull final BatteryUsageStats batteryUsageStats, boolean shortString) {
|
||||
final long batteryStatsTime = System.currentTimeMillis();
|
||||
if (statsHelper == null) {
|
||||
final BatteryStatsHelper localStatsHelper = new BatteryStatsHelper(context,
|
||||
true);
|
||||
localStatsHelper.create((Bundle) null);
|
||||
stats = localStatsHelper.getStats();
|
||||
} else {
|
||||
stats = statsHelper.getStats();
|
||||
}
|
||||
BatteryUtils.logRuntime(LOG_TAG, "time for getStats", batteryStatsTime);
|
||||
|
||||
final long startTime = System.currentTimeMillis();
|
||||
@@ -197,38 +197,38 @@ public class BatteryInfo {
|
||||
Estimate.storeCachedEstimate(context, estimate);
|
||||
BatteryUtils
|
||||
.logRuntime(LOG_TAG, "time for enhanced BatteryInfo", startTime);
|
||||
return BatteryInfo.getBatteryInfo(context, batteryBroadcast, stats,
|
||||
return BatteryInfo.getBatteryInfo(context, batteryBroadcast, batteryUsageStats,
|
||||
estimate, elapsedRealtimeUs, shortString);
|
||||
}
|
||||
}
|
||||
final long prediction = discharging
|
||||
? stats.computeBatteryTimeRemaining(elapsedRealtimeUs) : 0;
|
||||
final long prediction = discharging ? batteryUsageStats.getBatteryTimeRemainingMs() : 0;
|
||||
final Estimate estimate = new Estimate(
|
||||
PowerUtil.convertUsToMs(prediction),
|
||||
false, /* isBasedOnUsage */
|
||||
EstimateKt.AVERAGE_TIME_TO_DISCHARGE_UNKNOWN);
|
||||
BatteryUtils.logRuntime(LOG_TAG, "time for regular BatteryInfo", startTime);
|
||||
return BatteryInfo.getBatteryInfo(context, batteryBroadcast, stats,
|
||||
return BatteryInfo.getBatteryInfo(context, batteryBroadcast, batteryUsageStats,
|
||||
estimate, elapsedRealtimeUs, shortString);
|
||||
}
|
||||
|
||||
@WorkerThread
|
||||
public static BatteryInfo getBatteryInfoOld(Context context, Intent batteryBroadcast,
|
||||
BatteryStats stats, long elapsedRealtimeUs, boolean shortString) {
|
||||
BatteryUsageStats batteryUsageStats, long elapsedRealtimeUs, boolean shortString) {
|
||||
Estimate estimate = new Estimate(
|
||||
PowerUtil.convertUsToMs(stats.computeBatteryTimeRemaining(elapsedRealtimeUs)),
|
||||
batteryUsageStats.getBatteryTimeRemainingMs(),
|
||||
false,
|
||||
EstimateKt.AVERAGE_TIME_TO_DISCHARGE_UNKNOWN);
|
||||
return getBatteryInfo(context, batteryBroadcast, stats, estimate, elapsedRealtimeUs,
|
||||
shortString);
|
||||
return getBatteryInfo(context, batteryBroadcast, batteryUsageStats, estimate,
|
||||
elapsedRealtimeUs, shortString);
|
||||
}
|
||||
|
||||
@WorkerThread
|
||||
public static BatteryInfo getBatteryInfo(Context context, Intent batteryBroadcast,
|
||||
BatteryStats stats, Estimate estimate, long elapsedRealtimeUs, boolean shortString) {
|
||||
@NonNull BatteryUsageStats batteryUsageStats, Estimate estimate,
|
||||
long elapsedRealtimeUs, boolean shortString) {
|
||||
final long startTime = System.currentTimeMillis();
|
||||
BatteryInfo info = new BatteryInfo();
|
||||
info.mStats = stats;
|
||||
info.mBatteryUsageStats = batteryUsageStats;
|
||||
info.batteryLevel = Utils.getBatteryLevel(batteryBroadcast);
|
||||
info.batteryPercentString = Utils.formatPercentage(info.batteryLevel);
|
||||
info.mCharging = batteryBroadcast.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0) != 0;
|
||||
@@ -241,16 +241,17 @@ public class BatteryInfo {
|
||||
if (!info.mCharging) {
|
||||
updateBatteryInfoDischarging(context, shortString, estimate, info);
|
||||
} else {
|
||||
updateBatteryInfoCharging(context, batteryBroadcast, stats, elapsedRealtimeUs, info);
|
||||
updateBatteryInfoCharging(context, batteryBroadcast, batteryUsageStats,
|
||||
info);
|
||||
}
|
||||
BatteryUtils.logRuntime(LOG_TAG, "time for getBatteryInfo", startTime);
|
||||
return info;
|
||||
}
|
||||
|
||||
private static void updateBatteryInfoCharging(Context context, Intent batteryBroadcast,
|
||||
BatteryStats stats, long elapsedRealtimeUs, BatteryInfo info) {
|
||||
BatteryUsageStats stats, BatteryInfo info) {
|
||||
final Resources resources = context.getResources();
|
||||
final long chargeTime = stats.computeChargeTimeRemaining(elapsedRealtimeUs);
|
||||
final long chargeTimeMs = stats.getChargeTimeRemainingMs();
|
||||
final int status = batteryBroadcast.getIntExtra(BatteryManager.EXTRA_STATUS,
|
||||
BatteryManager.BATTERY_STATUS_UNKNOWN);
|
||||
info.discharging = false;
|
||||
@@ -260,8 +261,8 @@ public class BatteryInfo {
|
||||
int chargingLimitedResId = R.string.power_charging_limited;
|
||||
info.chargeLabel =
|
||||
context.getString(chargingLimitedResId, info.batteryPercentString);
|
||||
} else if (chargeTime > 0 && status != BatteryManager.BATTERY_STATUS_FULL) {
|
||||
info.remainingTimeUs = chargeTime;
|
||||
} else if (chargeTimeMs > 0 && status != BatteryManager.BATTERY_STATUS_FULL) {
|
||||
info.remainingTimeUs = PowerUtil.convertMsToUs(chargeTimeMs);
|
||||
CharSequence timeString = StringUtil.formatElapsedTime(context,
|
||||
PowerUtil.convertUsToMs(info.remainingTimeUs), false /* withSeconds */);
|
||||
int resId = R.string.power_charging_duration;
|
||||
@@ -313,7 +314,11 @@ public class BatteryInfo {
|
||||
void onParsingDone();
|
||||
}
|
||||
|
||||
public static void parse(BatteryStats stats, BatteryDataParser... parsers) {
|
||||
/**
|
||||
* Iterates over battery history included in the BatteryUsageStats that this object
|
||||
* was initialized with.
|
||||
*/
|
||||
public void parseBatteryHistory(BatteryDataParser... parsers) {
|
||||
long startWalltime = 0;
|
||||
long endWalltime = 0;
|
||||
long historyStart = 0;
|
||||
@@ -324,41 +329,41 @@ public class BatteryInfo {
|
||||
int lastInteresting = 0;
|
||||
int pos = 0;
|
||||
boolean first = true;
|
||||
if (stats.startIteratingHistoryLocked()) {
|
||||
final HistoryItem rec = new HistoryItem();
|
||||
while (stats.getNextHistoryLocked(rec)) {
|
||||
pos++;
|
||||
if (first) {
|
||||
first = false;
|
||||
historyStart = rec.time;
|
||||
final BatteryStatsHistoryIterator iterator1 =
|
||||
mBatteryUsageStats.iterateBatteryStatsHistory();
|
||||
final HistoryItem rec = new HistoryItem();
|
||||
while (iterator1.next(rec)) {
|
||||
pos++;
|
||||
if (first) {
|
||||
first = false;
|
||||
historyStart = rec.time;
|
||||
}
|
||||
if (rec.cmd == HistoryItem.CMD_CURRENT_TIME
|
||||
|| rec.cmd == HistoryItem.CMD_RESET) {
|
||||
// If there is a ridiculously large jump in time, then we won't be
|
||||
// able to create a good chart with that data, so just ignore the
|
||||
// times we got before and pretend like our data extends back from
|
||||
// the time we have now.
|
||||
// Also, if we are getting a time change and we are less than 5 minutes
|
||||
// since the start of the history real time, then also use this new
|
||||
// time to compute the base time, since whatever time we had before is
|
||||
// pretty much just noise.
|
||||
if (rec.currentTime > (lastWallTime + (180 * 24 * 60 * 60 * 1000L))
|
||||
|| rec.time < (historyStart + (5 * 60 * 1000L))) {
|
||||
startWalltime = 0;
|
||||
}
|
||||
if (rec.cmd == HistoryItem.CMD_CURRENT_TIME
|
||||
|| rec.cmd == HistoryItem.CMD_RESET) {
|
||||
// If there is a ridiculously large jump in time, then we won't be
|
||||
// able to create a good chart with that data, so just ignore the
|
||||
// times we got before and pretend like our data extends back from
|
||||
// the time we have now.
|
||||
// Also, if we are getting a time change and we are less than 5 minutes
|
||||
// since the start of the history real time, then also use this new
|
||||
// time to compute the base time, since whatever time we had before is
|
||||
// pretty much just noise.
|
||||
if (rec.currentTime > (lastWallTime + (180 * 24 * 60 * 60 * 1000L))
|
||||
|| rec.time < (historyStart + (5 * 60 * 1000L))) {
|
||||
startWalltime = 0;
|
||||
}
|
||||
lastWallTime = rec.currentTime;
|
||||
lastRealtime = rec.time;
|
||||
if (startWalltime == 0) {
|
||||
startWalltime = lastWallTime - (lastRealtime - historyStart);
|
||||
}
|
||||
}
|
||||
if (rec.isDeltaData()) {
|
||||
lastInteresting = pos;
|
||||
historyEnd = rec.time;
|
||||
lastWallTime = rec.currentTime;
|
||||
lastRealtime = rec.time;
|
||||
if (startWalltime == 0) {
|
||||
startWalltime = lastWallTime - (lastRealtime - historyStart);
|
||||
}
|
||||
}
|
||||
if (rec.isDeltaData()) {
|
||||
lastInteresting = pos;
|
||||
historyEnd = rec.time;
|
||||
}
|
||||
}
|
||||
stats.finishIteratingHistoryLocked();
|
||||
|
||||
endWalltime = lastWallTime + historyEnd - lastRealtime;
|
||||
|
||||
int i = 0;
|
||||
@@ -367,9 +372,11 @@ public class BatteryInfo {
|
||||
for (int j = 0; j < parsers.length; j++) {
|
||||
parsers[j].onParsingStarted(startWalltime, endWalltime);
|
||||
}
|
||||
if (endWalltime > startWalltime && stats.startIteratingHistoryLocked()) {
|
||||
final HistoryItem rec = new HistoryItem();
|
||||
while (stats.getNextHistoryLocked(rec) && i < N) {
|
||||
|
||||
if (endWalltime > startWalltime) {
|
||||
final BatteryStatsHistoryIterator iterator2 =
|
||||
mBatteryUsageStats.iterateBatteryStatsHistory();
|
||||
while (iterator2.next(rec) && i < N) {
|
||||
if (rec.isDeltaData()) {
|
||||
curWalltime += rec.time - lastRealtime;
|
||||
lastRealtime = rec.time;
|
||||
@@ -404,8 +411,6 @@ public class BatteryInfo {
|
||||
}
|
||||
}
|
||||
|
||||
stats.finishIteratingHistoryLocked();
|
||||
|
||||
for (int j = 0; j < parsers.length; j++) {
|
||||
parsers[j].onParsingDone();
|
||||
}
|
||||
|
Reference in New Issue
Block a user