Multi-user battery settings.
Aggregates battery use from other users into one line item. Change-Id: I811e681891a9ff098491de1e096232f38bf061a9
This commit is contained in:
@@ -3234,6 +3234,9 @@
|
||||
<!-- Suggestion for getting apps to consume less power -->
|
||||
<string name="battery_sugg_apps_settings">The app may offer settings to reduce battery use</string>
|
||||
|
||||
<!-- [CHAR LIMIT=50] Description for power consumed by users -->
|
||||
<string name="battery_desc_users">Battery used by user</string>
|
||||
|
||||
<!-- Menu label for viewing battery usage since unplugged -->
|
||||
<string name="menu_stats_unplugged"><xliff:g id="unplugged">%1$s</xliff:g> since unplugged</string>
|
||||
<!-- Menu label for viewing battery usage since unplugged -->
|
||||
|
@@ -105,6 +105,7 @@ public class Settings extends PreferenceActivity
|
||||
R.id.display_settings,
|
||||
R.id.storage_settings,
|
||||
R.id.application_settings,
|
||||
R.id.battery_settings,
|
||||
R.id.personal_section,
|
||||
R.id.security_settings,
|
||||
R.id.user_settings,
|
||||
|
@@ -107,7 +107,6 @@ class BatterySipper implements Comparable<BatterySipper> {
|
||||
return;
|
||||
}
|
||||
PackageManager pm = mContext.getPackageManager();
|
||||
final Drawable defaultActivityIcon = pm.getDefaultActivityIcon();
|
||||
String[] packages = pm.getPackagesForUid(uid);
|
||||
icon = pm.getDefaultActivityIcon();
|
||||
if (packages == null) {
|
||||
|
@@ -17,6 +17,7 @@
|
||||
package com.android.settings.fuelgauge;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.drawable.ColorDrawable;
|
||||
import android.graphics.drawable.Drawable;
|
||||
import android.preference.Preference;
|
||||
import android.view.View;
|
||||
@@ -37,7 +38,7 @@ public class PowerGaugePreference extends Preference {
|
||||
public PowerGaugePreference(Context context, Drawable icon, BatterySipper info) {
|
||||
super(context);
|
||||
setLayoutResource(R.layout.app_percentage_item);
|
||||
setIcon(icon);
|
||||
setIcon(icon != null ? icon : new ColorDrawable(0));
|
||||
mInfo = info;
|
||||
}
|
||||
|
||||
|
@@ -62,7 +62,8 @@ public class PowerUsageDetail extends Fragment implements Button.OnClickListener
|
||||
WIFI,
|
||||
BLUETOOTH,
|
||||
SCREEN,
|
||||
APP
|
||||
APP,
|
||||
USER
|
||||
}
|
||||
|
||||
// Note: Must match the sequence of the DrainType
|
||||
@@ -73,7 +74,8 @@ public class PowerUsageDetail extends Fragment implements Button.OnClickListener
|
||||
R.string.battery_desc_wifi,
|
||||
R.string.battery_desc_bluetooth,
|
||||
R.string.battery_desc_display,
|
||||
R.string.battery_desc_apps
|
||||
R.string.battery_desc_apps,
|
||||
R.string.battery_desc_users,
|
||||
};
|
||||
|
||||
public static final int ACTION_DISPLAY_SETTINGS = 1;
|
||||
|
@@ -20,6 +20,8 @@ import android.content.BroadcastReceiver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.IntentFilter;
|
||||
import android.content.pm.UserInfo;
|
||||
import android.graphics.drawable.Drawable;
|
||||
import android.hardware.SensorManager;
|
||||
import android.net.Uri;
|
||||
import android.os.BatteryStats;
|
||||
@@ -32,6 +34,8 @@ import android.os.Process;
|
||||
import android.os.RemoteException;
|
||||
import android.os.ServiceManager;
|
||||
import android.os.SystemClock;
|
||||
import android.os.UserHandle;
|
||||
import android.os.UserManager;
|
||||
import android.preference.Preference;
|
||||
import android.preference.PreferenceActivity;
|
||||
import android.preference.PreferenceFragment;
|
||||
@@ -79,10 +83,14 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
private static BatteryStatsImpl sStatsXfer;
|
||||
|
||||
IBatteryStats mBatteryInfo;
|
||||
UserManager mUm;
|
||||
BatteryStatsImpl mStats;
|
||||
private final List<BatterySipper> mUsageList = new ArrayList<BatterySipper>();
|
||||
private final List<BatterySipper> mWifiSippers = new ArrayList<BatterySipper>();
|
||||
private final List<BatterySipper> mBluetoothSippers = new ArrayList<BatterySipper>();
|
||||
private final SparseArray<List<BatterySipper>> mUserSippers
|
||||
= new SparseArray<List<BatterySipper>>();
|
||||
private final SparseArray<Double> mUserPower = new SparseArray<Double>();
|
||||
|
||||
private PreferenceGroup mAppListGroup;
|
||||
private Preference mBatteryStatusPref;
|
||||
@@ -134,6 +142,7 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
addPreferencesFromResource(R.xml.power_usage_summary);
|
||||
mBatteryInfo = IBatteryStats.Stub.asInterface(
|
||||
ServiceManager.getService("batteryinfo"));
|
||||
mUm = (UserManager)getActivity().getSystemService(Context.USER_SERVICE);
|
||||
mAppListGroup = (PreferenceGroup) findPreference(KEY_APP_LIST);
|
||||
mBatteryStatusPref = mAppListGroup.findPreference(KEY_BATTERY_STATUS);
|
||||
mPowerProfile = new PowerProfile(getActivity());
|
||||
@@ -204,6 +213,7 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
double[] values;
|
||||
switch (sipper.drainType) {
|
||||
case APP:
|
||||
case USER:
|
||||
{
|
||||
Uid uid = sipper.uidObj;
|
||||
types = new int[] {
|
||||
@@ -229,15 +239,18 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
0
|
||||
};
|
||||
|
||||
Writer result = new StringWriter();
|
||||
PrintWriter printWriter = new PrintWriter(result);
|
||||
mStats.dumpLocked(printWriter, "", mStatsType, uid.getUid());
|
||||
args.putString(PowerUsageDetail.EXTRA_REPORT_DETAILS, result.toString());
|
||||
|
||||
result = new StringWriter();
|
||||
printWriter = new PrintWriter(result);
|
||||
mStats.dumpCheckinLocked(printWriter, mStatsType, uid.getUid());
|
||||
args.putString(PowerUsageDetail.EXTRA_REPORT_CHECKIN_DETAILS, result.toString());
|
||||
if (sipper.drainType == DrainType.APP) {
|
||||
Writer result = new StringWriter();
|
||||
PrintWriter printWriter = new PrintWriter(result);
|
||||
mStats.dumpLocked(printWriter, "", mStatsType, uid.getUid());
|
||||
args.putString(PowerUsageDetail.EXTRA_REPORT_DETAILS, result.toString());
|
||||
|
||||
result = new StringWriter();
|
||||
printWriter = new PrintWriter(result);
|
||||
mStats.dumpCheckinLocked(printWriter, mStatsType, uid.getUid());
|
||||
args.putString(PowerUsageDetail.EXTRA_REPORT_CHECKIN_DETAILS,
|
||||
result.toString());
|
||||
}
|
||||
}
|
||||
break;
|
||||
case CELL:
|
||||
@@ -373,6 +386,8 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
mUsageList.clear();
|
||||
mWifiSippers.clear();
|
||||
mBluetoothSippers.clear();
|
||||
mUserSippers.clear();
|
||||
mUserPower.clear();
|
||||
mAppListGroup.setOrderingAsAdded(false);
|
||||
|
||||
mBatteryStatusPref.setOrder(-2);
|
||||
@@ -570,6 +585,8 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
if (DEBUG) Log.i(TAG, String.format("UID %d total power=%.2f", u.getUid(), power));
|
||||
|
||||
// Add the app to the list if it is consuming power
|
||||
boolean isOtherUser = false;
|
||||
final int userId = UserHandle.getUserId(u.getUid());
|
||||
if (power != 0 || u.getUid() == 0) {
|
||||
BatterySipper app = new BatterySipper(getActivity(), mRequestQueue, mHandler,
|
||||
packageWithHighestDrain, DrainType.APP, 0, u,
|
||||
@@ -585,6 +602,15 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
mWifiSippers.add(app);
|
||||
} else if (u.getUid() == Process.BLUETOOTH_GID) {
|
||||
mBluetoothSippers.add(app);
|
||||
} else if (userId != UserHandle.myUserId()
|
||||
&& UserHandle.getAppId(u.getUid()) >= Process.FIRST_APPLICATION_UID) {
|
||||
isOtherUser = true;
|
||||
List<BatterySipper> list = mUserSippers.get(userId);
|
||||
if (list == null) {
|
||||
list = new ArrayList<BatterySipper>();
|
||||
mUserSippers.put(userId, list);
|
||||
}
|
||||
list.add(app);
|
||||
} else {
|
||||
mUsageList.add(app);
|
||||
}
|
||||
@@ -592,13 +618,23 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
osApp = app;
|
||||
}
|
||||
}
|
||||
if (u.getUid() == Process.WIFI_UID) {
|
||||
mWifiPower += power;
|
||||
} else if (u.getUid() == Process.BLUETOOTH_GID) {
|
||||
mBluetoothPower += power;
|
||||
} else {
|
||||
if (power > mMaxPower) mMaxPower = power;
|
||||
mTotalPower += power;
|
||||
if (power != 0) {
|
||||
if (u.getUid() == Process.WIFI_UID) {
|
||||
mWifiPower += power;
|
||||
} else if (u.getUid() == Process.BLUETOOTH_GID) {
|
||||
mBluetoothPower += power;
|
||||
} else if (isOtherUser) {
|
||||
Double userPower = mUserPower.get(userId);
|
||||
if (userPower == null) {
|
||||
userPower = power;
|
||||
} else {
|
||||
userPower += power;
|
||||
}
|
||||
mUserPower.put(userId, userPower);
|
||||
} else {
|
||||
if (power > mMaxPower) mMaxPower = power;
|
||||
mTotalPower += power;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -725,6 +761,32 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
aggregateSippers(bs, mBluetoothSippers, "Bluetooth");
|
||||
}
|
||||
|
||||
private void addUserUsage() {
|
||||
for (int i=0; i<mUserSippers.size(); i++) {
|
||||
final int userId = mUserSippers.keyAt(i);
|
||||
final List<BatterySipper> sippers = mUserSippers.valueAt(i);
|
||||
UserInfo info = mUm.getUserInfo(userId);
|
||||
Drawable icon = null;
|
||||
if (info != null && info.iconPath != null) {
|
||||
try {
|
||||
icon = Drawable.createFromPath(info.iconPath);
|
||||
} catch (Exception e) {
|
||||
Log.w(TAG, "Failure loading user picture " + info.iconPath, e);
|
||||
}
|
||||
}
|
||||
String name = info != null ? info.name : null;
|
||||
if (name == null) {
|
||||
name = Integer.toString(info.id);
|
||||
}
|
||||
double power = mUserPower.get(userId);
|
||||
String label = getActivity().getResources().getString(
|
||||
R.string.running_process_item_user_label, name);
|
||||
BatterySipper bs = addEntry(label, DrainType.USER, 0, 0, power);
|
||||
bs.icon = icon;
|
||||
aggregateSippers(bs, sippers, "User");
|
||||
}
|
||||
}
|
||||
|
||||
private double getAverageDataCost() {
|
||||
final long WIFI_BPS = 1000000; // TODO: Extract average bit rates from system
|
||||
final long MOBILE_BPS = 200000; // TODO: Extract average bit rates from system
|
||||
@@ -760,6 +822,7 @@ public class PowerUsageSummary extends PreferenceFragment implements Runnable {
|
||||
Log.i(TAG, "Uptime since last unplugged = " + (timeSinceUnplugged / 1000));
|
||||
}
|
||||
|
||||
addUserUsage();
|
||||
addPhoneUsage(uSecNow);
|
||||
addScreenUsage(uSecNow);
|
||||
addWiFiUsage(uSecNow);
|
||||
|
Reference in New Issue
Block a user