参考链接:https://stackoverflow.com/questions/49606077/android-packagestats-gives-always-zero
简单来说,就是我代码里面用的反射的方法获取应用大小,但是会报Shame on you for calling the hidden API getPackageSizeInfoAsUser(). Shame!的异常信息,查询之后发现是api26以下可以用反射的这种方法,但是26以上会报错
解决方法参见链接
api<26 就是我项目里是这样写的
Method method = getMethod("getPackageSizeInfo");
for (int i = 0; i < packages.size(); i++) {
ApplicationInfo pkg = packages.get(i);
if (Build.VERSION.SDK\_INT < Build.VERSION\_CODES.O) {
try {
method.invoke(pm, pkg.packageName, new IPackageStatsObserver.Stub() {
@Override
public void onGetStatsCompleted(PackageStats pStats, boolean succeeded) throws RemoteException {
if (succeeded) {
ArrayList<AppsListItem> listItems = mAppsMapItem.get(pStats.packageName);
for (AppsListItem appsListItem:listItems){
appsListItem.mDataSize = pStats.dataSize;
appsListItem.mCacheSize = pStats.cacheSize;
appsListItem.mCodeSize = pStats.codeSize;
}
if (index >= packages.size()) {
index = 0;
} else {
index++;
}
lock.lock();
try {
count++;
if (count >= packages.size()) {
Message msg = myHandler.obtainMessage();
msg.what = INSTALL;
myHandler.sendMessage(msg);
index = 0;
}
} catch (Exception e) {
}
lock.unlock();
}
}
});
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();//api 26以上会走这里
}
api大于26的时候可以用以下代码(根据实际使用更改,下面的是我代码里面的),
@SuppressLint("WrongConstant")
final StorageStatsManager storageStatsManager = (StorageStatsManager)getSystemService(Context.STORAGE_STATS_SERVICE);
final StorageManager storageManager = (StorageManager)getSystemService(Context.STORAGE_SERVICE);
try {
ApplicationInfo ai = getPackageManager().getApplicationInfo(pkg.packageName, 0);
StorageStats storageStats = storageStatsManager.queryStatsForUid(ai.storageUuid, pkg.uid);
ArrayList<AppsListItem> listItems = mAppsMapItem.get(pkg.packageName);
for (AppsListItem appsListItem : listItems) {
appsListItem.mDataSize = storageStats.getDataBytes();
appsListItem.mCacheSize = storageStats.getCacheBytes();
appsListItem.mCodeSize = storageStats.getAppBytes();
}
// Log.d("zjw", mAppsListItem.get(index).mPackageName + "//" + pStats.packageName);
if (index >= packages.size()) {
index = 0;
} else {
index++;
}
lock.lock();
try {
count++;
if (count >= packages.size()) {
Message msg = myHandler.obtainMessage();
msg.what = INSTALL;
myHandler.sendMessage(msg);
index = 0;
}
} catch (Exception e) {
}
lock.unlock();
} catch (Exception e) {
e.printStackTrace();
}
需要 USAGE ACCESS PERMISSION 权限,申请权限如下
清单文件里面:
<uses-permission android:name="android.permission.PACKAGE_USAGE_STATS"/>
代码里面:
public static boolean checkAppUsagePermission(Context context) {
UsageStatsManager usageStatsManager = (UsageStatsManager) context.getSystemService(Context.USAGE_STATS_SERVICE);
if(usageStatsManager == null) {
return false;
}
long currentTime = System.currentTimeMillis();
// try to get app usage state in last 1 min
List<UsageStats> stats = usageStatsManager.queryUsageStats(UsageStatsManager.INTERVAL_DAILY, currentTime - 60 * 1000, currentTime);
if (stats.size() == 0) {
return false;
}
return true;
}
public static void requestAppUsagePermission(Context context) {
Intent intent = new Intent(android.provider.Settings.ACTION_USAGE_ACCESS_SETTINGS);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
try {
context.startActivity(intent);
} catch (ActivityNotFoundException e) {
e.printStackTrace();
}
}
本文详细介绍了在不同Android API版本下获取应用大小的方法。对于API小于26的版本,可以通过反射调用getPackageSizeInfo方法;而在API大于等于26的版本中,则需使用StorageStatsManager来查询应用的使用情况。同时,文章提供了代码示例,并说明了所需权限。
——获取应用大小时出现异常报错Shame on you for calling the hidden API getPackageSizeInfoAsUser. Shame!...&spm=1001.2101.3001.5002&articleId=100809950&d=1&t=3&u=c1ecdfd26ce8440a8f19d6a33789dc79)
8356

被折叠的 条评论
为什么被折叠?



