Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using BatteryStatsImpl internal class via Reflection in android

Tags:

android

I am trying to get a list of running applications and the amount of battery used by each of them. I have google for a long time but didnt come up with a solution. However there have been a few references on the PowerProfile, PowerUsageSummary internal classes.

I used them through Reflection technique but didnt get what i was looking for. PowerUsageSummary shows the same details as you can see by going to Device Settings->Applications->Battery Use(This is how it can be seen in a Samsund device).

Then i used PowerProfile class but i got only the mA of current utilized by WIFI, AUDIO, VIDEO,GPS, BLUETOOTH etc(The mA values dont change so often. I am not sure if the values are correct). Another reference was the BatteryStatsImpl class. I tested this class but the values are 0 always. Still i am looking for the list of running applications and the amount of battery used by each of them. Any help is appreciated.

Thanks,

Here is the sample code that i tried for BatteryStatsImpl class.

        String BATTERY_PROFILE_CLASS = "com.android.internal.os.BatteryStatsImpl";
        Object mBatteryProfile = Class.forName(BATTERY_PROFILE_CLASS).getConstructor().newInstance();
        Method batteryMeth = Class.forName(BATTERY_PROFILE_CLASS).getMethod("getBatteryUptime", long.class);
        Object arglist1[] = new Object[1];
        arglist1[0] = System.currentTimeMillis();
        // This is to calculate the batteryUpTime since the current time.
        Long batteryUptime = (Long) batteryMeth.invoke(mBatteryProfile, arglist1);

        Method dischargeMeth = Class.forName(BATTERY_PROFILE_CLASS).getMethod("getDischargeStartLevel");
        // This is to calculate the dischargeTime of the device battery
        Integer dischargeTime = (Integer) dischargeMeth.invoke(mBatteryProfile);
like image 648
Vansi Avatar asked Apr 25 '12 06:04

Vansi


1 Answers

First please note that you can't make use of this API unless you are installed on the system image and so can hold the BATTERY_STATS permission. This is not available to third part apps installed separately from the system.

To use this, you don't directly instantiate BatteryStatsImpl. You request an instance of it from the current stats being collected by BatteryStatsService. You can look for the source code of the settings app for how to do this: https://code.google.com/p/android-source-browsing/source/browse/src/com/android/settings/fuelgauge/PowerUsageSummary.java?repo=platform--packages--apps--settings

In particular:

import android.os.BatteryStats;

import com.android.internal.app.IBatteryStats;
import com.android.internal.os.BatteryStatsImpl;

IBatteryStats mBatteryInfo;
UserManager mUm;
BatteryStatsImpl mStats;

mBatteryInfo = IBatteryStats.Stub.asInterface(
        ServiceManager.getService("batteryinfo"));

private void load() {
    try {
        byte[] data = mBatteryInfo.getStatistics();
        Parcel parcel = Parcel.obtain();
        parcel.unmarshall(data, 0, data.length);
        parcel.setDataPosition(0);
        mStats = com.android.internal.os.BatteryStatsImpl.CREATOR
                .createFromParcel(parcel);
        mStats.distributeWorkLocked(BatteryStats.STATS_SINCE_CHARGED);
    } catch (RemoteException e) {
        Log.e(TAG, "RemoteException:", e);
    }
}
like image 116
hackbod Avatar answered Nov 02 '22 23:11

hackbod