Data usage app labels, protect system, hide empty.

Derive better labels from PackageManager, including for sharedUid
case.  Disable "App settings" button when no ResolveInfo found, and
hide "Restrict" checkbox for system UIDs.  Also hide apps with 0
bytes usage.

Change-Id: I4b0a66f6912c02c56bfcbcb5b46f3ae2ba0df504
This commit is contained in:
Jeff Sharkey
2011-06-14 22:41:21 -07:00
parent 5a259aae18
commit 8e911d7b1a
3 changed files with 97 additions and 26 deletions

View File

@@ -32,6 +32,7 @@ import android.content.pm.PackageManager;
import android.graphics.Color; import android.graphics.Color;
import android.net.INetworkPolicyManager; import android.net.INetworkPolicyManager;
import android.net.INetworkStatsService; import android.net.INetworkStatsService;
import android.net.NetworkPolicyManager;
import android.net.NetworkStatsHistory; import android.net.NetworkStatsHistory;
import android.os.Bundle; import android.os.Bundle;
import android.os.RemoteException; import android.os.RemoteException;
@@ -58,6 +59,7 @@ public class DataUsageAppDetail extends Fragment {
private static final boolean LOGD = true; private static final boolean LOGD = true;
private int mUid; private int mUid;
private Intent mAppSettingsIntent;
private static final String TAG_CONFIRM_RESTRICT = "confirmRestrict"; private static final String TAG_CONFIRM_RESTRICT = "confirmRestrict";
@@ -127,23 +129,38 @@ public class DataUsageAppDetail extends Fragment {
public void onResume() { public void onResume() {
super.onResume(); super.onResume();
final Context context = getActivity();
mUid = getArguments().getInt(Intent.EXTRA_UID);
mTitle.setText(context.getPackageManager().getNameForUid(mUid));
updateBody(); updateBody();
} }
private void updateBody() { private void updateBody() {
final PackageManager pm = getActivity().getPackageManager();
mUid = getArguments().getInt(Intent.EXTRA_UID);
mTitle.setText(pm.getNameForUid(mUid));
// enable settings button when package provides it
// TODO: target torwards entire UID instead of just first package
final String[] packageNames = pm.getPackagesForUid(mUid);
if (packageNames != null && packageNames.length > 0) {
mAppSettingsIntent = new Intent(Intent.ACTION_MANAGE_NETWORK_USAGE);
mAppSettingsIntent.setPackage(packageNames[0]);
mAppSettingsIntent.addCategory(Intent.CATEGORY_DEFAULT);
final boolean matchFound = pm.resolveActivity(mAppSettingsIntent, 0) != null;
mAppSettings.setEnabled(matchFound);
} else {
mAppSettingsIntent = null;
mAppSettings.setEnabled(false);
}
try { try {
// load stats for current uid and template // load stats for current uid and template
// TODO: read template from extras // TODO: read template from extras
mUidPolicy = mPolicyService.getUidPolicy(mUid);
mHistory = mStatsService.getHistoryForUid(mUid, TEMPLATE_MOBILE_ALL); mHistory = mStatsService.getHistoryForUid(mUid, TEMPLATE_MOBILE_ALL);
} catch (RemoteException e) { } catch (RemoteException e) {
// since we can't do much without policy or history, and we don't // since we can't do much without history, and we don't want to
// want to leave with half-baked UI, we bail hard. // leave with half-baked UI, we bail hard.
throw new RuntimeException("problem reading network stats", e); throw new RuntimeException("problem reading network stats", e);
} }
@@ -155,12 +172,28 @@ public class DataUsageAppDetail extends Fragment {
mChart.setVisibleRange(bounds[0], bounds[1] + DateUtils.WEEK_IN_MILLIS, bounds[1]); mChart.setVisibleRange(bounds[0], bounds[1] + DateUtils.WEEK_IN_MILLIS, bounds[1]);
updateDetailData(); updateDetailData();
final Context context = getActivity();
if (NetworkPolicyManager.isUidValidForPolicy(context, mUid)) {
mRestrictBackgroundView.setVisibility(View.VISIBLE);
final int uidPolicy;
try {
uidPolicy = mPolicyService.getUidPolicy(mUid);
} catch (RemoteException e) {
// since we can't do much without policy, we bail hard.
throw new RuntimeException("problem reading network policy", e);
}
// update policy checkbox // update policy checkbox
final boolean restrictBackground = (mUidPolicy & POLICY_REJECT_PAID_BACKGROUND) != 0; final boolean restrictBackground = (mUidPolicy & POLICY_REJECT_PAID_BACKGROUND) != 0;
mRestrictBackground.setChecked(restrictBackground); mRestrictBackground.setChecked(restrictBackground);
// kick preference views so they rebind from changes above // kick preference views so they rebind from changes above
refreshPreferenceViews(); refreshPreferenceViews();
} else {
mRestrictBackgroundView.setVisibility(View.GONE);
}
} }
private void updateDetailData() { private void updateDetailData() {
@@ -215,12 +248,7 @@ public class DataUsageAppDetail extends Fragment {
/** {@inheritDoc} */ /** {@inheritDoc} */
public void onClick(View v) { public void onClick(View v) {
// TODO: target torwards entire UID instead of just first package // TODO: target torwards entire UID instead of just first package
final PackageManager pm = getActivity().getPackageManager(); startActivity(mAppSettingsIntent);
final String packageName = pm.getPackagesForUid(mUid)[0];
final Intent intent = new Intent(Intent.ACTION_MANAGE_NETWORK_USAGE);
intent.setPackage(packageName);
startActivity(intent);
} }
}; };

View File

@@ -32,7 +32,10 @@ import android.app.Fragment;
import android.content.Context; import android.content.Context;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.content.Intent; import android.content.Intent;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.net.INetworkPolicyManager; import android.net.INetworkPolicyManager;
import android.net.INetworkStatsService; import android.net.INetworkStatsService;
import android.net.NetworkPolicy; import android.net.NetworkPolicy;
@@ -46,6 +49,7 @@ import android.preference.Preference;
import android.preference.PreferenceActivity; import android.preference.PreferenceActivity;
import android.preference.SwitchPreference; import android.preference.SwitchPreference;
import android.telephony.TelephonyManager; import android.telephony.TelephonyManager;
import android.text.TextUtils;
import android.text.format.DateUtils; import android.text.format.DateUtils;
import android.text.format.Formatter; import android.text.format.Formatter;
import android.text.format.Time; import android.text.format.Time;
@@ -537,7 +541,10 @@ public class DataUsageSummary extends Fragment {
mCycleSpinner.setSelection(0); mCycleSpinner.setSelection(0);
} else { } else {
if (LOGD) Log.d(TAG, "showing cycle " + cycle); if (LOGD) {
Log.d(TAG, "showing cycle " + cycle + ", start=" + cycle.start + ", end="
+ cycle.end + "]");
}
// update chart to show selected cycle, and update detail data // update chart to show selected cycle, and update detail data
// to match updated sweep bounds. // to match updated sweep bounds.
@@ -670,11 +677,14 @@ public class DataUsageSummary extends Fragment {
mItems.clear(); mItems.clear();
for (int i = 0; i < stats.size; i++) { for (int i = 0; i < stats.size; i++) {
final long total = stats.rx[i] + stats.tx[i];
if (total > 0) {
final AppUsageItem item = new AppUsageItem(); final AppUsageItem item = new AppUsageItem();
item.uid = stats.uid[i]; item.uid = stats.uid[i];
item.total = stats.rx[i] + stats.tx[i]; item.total = total;
mItems.add(item); mItems.add(item);
} }
}
Collections.sort(mItems); Collections.sort(mItems);
notifyDataSetChanged(); notifyDataSetChanged();
@@ -709,7 +719,7 @@ public class DataUsageSummary extends Fragment {
final TextView text2 = (TextView) convertView.findViewById(android.R.id.text2); final TextView text2 = (TextView) convertView.findViewById(android.R.id.text2);
final AppUsageItem item = mItems.get(position); final AppUsageItem item = mItems.get(position);
text1.setText(pm.getNameForUid(item.uid)); text1.setText(resolveLabelForUid(pm, item.uid));
text2.setText(Formatter.formatFileSize(context, item.total)); text2.setText(Formatter.formatFileSize(context, item.total));
return convertView; return convertView;
@@ -829,4 +839,36 @@ public class DataUsageSummary extends Fragment {
} }
} }
/**
* Resolve best descriptive label for the given UID.
*/
public static CharSequence resolveLabelForUid(PackageManager pm, int uid) {
final String[] packageNames = pm.getPackagesForUid(uid);
final int length = packageNames != null ? packageNames.length : 0;
CharSequence label = pm.getNameForUid(uid);
try {
if (length == 1) {
final ApplicationInfo info = pm.getApplicationInfo(packageNames[0], 0);
label = info.loadLabel(pm);
} else if (length > 1) {
for (String packageName : packageNames) {
final PackageInfo info = pm.getPackageInfo(packageName, 0);
if (info.sharedUserLabel != 0) {
label = pm.getText(packageName, info.sharedUserLabel, info.applicationInfo);
if (!TextUtils.isEmpty(label)) {
break;
}
}
}
}
} catch (NameNotFoundException e) {
}
if (TextUtils.isEmpty(label)) {
label = Integer.toString(uid);
}
return label;
}
} }

View File

@@ -157,7 +157,8 @@ public class ChartNetworkSeriesView extends View {
if (LOGD) { if (LOGD) {
final RectF bounds = new RectF(); final RectF bounds = new RectF();
mPathFill.computeBounds(bounds, true); mPathFill.computeBounds(bounds, true);
Log.d(TAG, "onLayout() rendered with bounds=" + bounds.toString()); Log.d(TAG, "onLayout() rendered with bounds=" + bounds.toString() + " and totalData="
+ totalData);
} }
// drop to bottom of graph from current location // drop to bottom of graph from current location