最近接到一个任务是模仿自动化测试APP的应用,其中就有一个功能是测试一个应用的耗电量。
于是习惯性搜了下百度,google。发现android到目前为止都没有开放相关API给我们使用。
刚开始我构思的解决方法是仿照官方系统设置里的电量排行来进行耗电量计算。
参考android5.0系统源码可知实现应用耗电量统计需要得到两方面的数据。
1. 购物清单(BatteryStatsImpl)提供APP各部件的运行时间,记录了每一个APP需要用到的器件(有CPU,LCD显示,WIFI,GPS,移动网络等)以及运行时间;
2. 价格表(PowerProfile)提供每个器件的单位时间功耗
分析PowerProfile 这个手机都有一个这个文件Power_pro_file.xml,具体device///frameworks/base/core/res/res/xml/power_profile.xml
这个Xml资源文件由手机OEM厂场提供,通常打包进系统里,外头没有独立的资源文件存在。
这两个类都是internal类,是不公开的。
解决方法:将手机中的framework.apk里面的被SDK屏蔽的API和类加入到开发项目中。这种例子网上有不少了。
下面我分享一个由android5.0新出的一个耗电量统计工具来实现(前提手机要Root),dumpsys batterystats 的使用
先来看看这个电量工具的效果 我的手机是MX5 系统是android5.0(非原生系统,经过厂商加工,市面上有不少耗电量软件只能统计原生系统)
先使用ADB工具示范一次
首先reset重置一下
然后拔掉USB线 操作一下再重新接上查看
比如我想查看微信在刚才的耗电量
、
以下是反馈信息:
Statistics since last charge:
System starts: 0, currently on battery: false
Time on battery: 8s 172ms (2.6%) realtime, 8s 172ms (2.6%) uptime
Time on battery screen off: 70ms (0.0%) realtime, 70ms (0.0%) uptime
Total run time: 5m 19s 751ms realtime, 5m 19s 751ms uptime
Start clock time: 2016-09-12-10-26-33
Screen on: 8s 102ms (99.1%) 1x, Interactive: 8s 103ms (99.2%)
Screen brightnesses:
dark 8s 102ms (100.0%)
Mobile total received: 0B, sent: 0B (packets received 0, sent 0)
Phone signal levels:
very 8s 172ms (100.0%) 0x
Signal scanning time: 0ms
Radio types:
hspa 6s 392ms (78.2%) 2x
hspap 1s 780ms (21.8%) 1x
Mobile radio active time: 0ms (0.0%) 0x
Wi-Fi total received: 0B, sent: 0B (packets received 0, sent 0)
Wifi on: 0ms (0.0%), Wifi running: 0ms (0.0%)
Wifi states: (no activity)
Wifi supplicant states:
scanning 8s 172ms (100.0%) 0x
Wifi signal levels:
level(4) 8s 172ms (100.0%) 0x
Bluetooth on: 0ms (0.0%)
Bluetooth states: (no activity)
Device battery use since last full charge
Amount discharged (lower bound): 0
Amount discharged (upper bound): 0
Amount discharged while screen on: 0
Amount discharged while screen off: 0
Estimated power use (mAh):
Capacity: 3000, Computed drain: 0.830, actual drain: 0.00000000
Screen: 0.309
Uid 1000: 0.242
Uid 0: 0.0699
Uid u0a80: 0.0613
Uid u0a11: 0.0472
Uid u0a112: 0.0337
Uid u0a105: 0.00981
Uid 1001: 0.00920
Uid u0a111: 0.00920
Uid u0a79: 0.00677
Uid u0a71: 0.00613
Uid u0a108: 0.00307
Uid u0a76: 0.00245
Uid u0a86: 0.00245
Uid u0a94: 0.00245
Cell standby: 0.00227
Uid u0a27: 0.00184
Uid u0a89: 0.00184
Uid u0a14: 0.00123
Uid u0a18: 0.00123
Uid u0a66: 0.00123
Uid u0a82: 0.00123
Uid u0a83: 0.00123
Uid u0a4: 0.000613
Uid u0a7: 0.000613
Uid u0a19: 0.000613
Uid u0a78: 0.000613
Uid u0a92: 0.000613
Idle: 0.000194
1000:
User activity: 10 other, 5 touch
Wake lock SyncLoopWakeLock realtime
Wake lock ActivityManager-Launch realtime
Wake lock PhoneWindowManager.mProximityWakeLock realtime
Wake lock GpsLocationProvider realtime
Wake lock show keyguard realtime
Wake lock SyncManagerHandleSyncAlarm realtime
Wake lock AudioMix realtime
Wake lock *alarm* realtime
Wake lock WifiSuspend realtime
Wake lock ActivityManager-Sleep realtime
Sensor 35: 1s 164ms realtime (1 times)
Sensor 36: 1s 153ms realtime (1 times)
Foreground for: 8s 172ms
Proc system:
CPU: 1s 200ms usr + 1s 600ms krn ; 0ms fg
Proc com.meizu.safe:
CPU: 0ms usr + 10ms krn ; 0ms fg
Proc surfaceflinger:
CPU: 290ms usr + 240ms krn ; 0ms fg
Proc aal:
CPU: 10ms usr + 0ms krn ; 0ms fg
Proc servicemanager:
CPU: 30ms usr + 20ms krn ; 0ms fg
Proc com.android.systemui:
CPU: 360ms usr + 190ms krn ; 0ms fg
u0a80:
Wake lock *alarm* realtime
Sensor 12: 4s 86ms realtime (0 times)
Foreground activities: 8s 172ms realtime (0 times)
Foreground for: 8s 172ms
Proc com.tencent.mm:push:
CPU: 50ms usr + 20ms krn ; 0ms fg
Proc com.tencent.mm:
CPU: 800ms usr + 110ms krn ; 0ms fg
对于以上信息你只需要知道两个点的数据即可
第三行 Time on battery: 8s 172ms (2.6%) realtime, 8s 172ms (2.6%) uptime 表示使用手机电源运行的时间
Estimated power use (mAh): 这一句以下所有UID 后面的数据想加就是该应用在这段时间的耗电量(mah)
下面要做的只需要在代码中将该信息分析,可以使用字符串的索引等相关知识
private float searchStrng(String successInfo){ //<span style="font-family:宋体;">参数是反馈信息</span>
List<String> uidPowerList = new ArrayList<>();
uidPowerList.clear();
float returnResult = 0;
String beginStr = "Estimated power use"; //应该耗电量信息标志
String beginUid1 = "Uid"; //每条UID耗电量标志
String beginUid2 = ": "; //数据开始标志
String endUid = " "; //数据结束标志
int begin,end;
String beginIn = "";
begin = successInfo.indexOf(beginStr);
if (begin != -1)
beginIn = successInfo.substring(begin);
/**
* 依次获取UID后面对应的耗电量
* beginIn 为检索字符串段
*/
for(;;) {
if (beginIn.indexOf(beginUid1)!= -1) {
begin = beginIn.indexOf(beginUid1);
beginIn = beginIn.substring(begin+4);
begin = beginIn.indexOf(beginUid2);
beginIn = beginIn.substring(begin+2);
Log.d("字段",beginIn);
end = beginIn.indexOf(endUid);
uidPowerList.add(beginIn.substring(0, end));
beginIn = beginIn.substring(end);
}else
break;
}
for(int i = 0;i < uidPowerList.size();i++){ //将List里面每个UID的数值转化为float再加起来
returnResult = returnResult + Float.valueOf(uidPowerList.get(i));
}
<span style="font-family:宋体;">//</span> myData.get(0).add(returnResult);
return returnResult; <span style="font-family:宋体;">//返回该时间段的耗电量</span>
}
应该很好看懂吧,至于shell工具类我就不分享了,网上很多。
PS:当手机外接充电源(包括USB)的时候,此时的耗电量总是0,因为这里统计的是应用损耗电池的电量,当手机不使用电池时自然为0,所以使用时确保拔掉充电器进行使用。至于调试的话,推荐你使用无线调试。
本人android菜鸟,如果有不对的地方请多包涵指正