Loading core/java/com/android/internal/app/ChooserActivity.java +20 −0 Original line number Diff line number Diff line Loading @@ -202,6 +202,9 @@ public class ChooserActivity extends ResolverActivity { private long mChooserShownTime; protected boolean mIsSuccessfullySelected; private long mQueriedTargetServicesTimeMs; private long mQueriedSharingShortcutsTimeMs; private ChooserListAdapter mChooserListAdapter; private ChooserRowAdapter mChooserRowAdapter; private int mChooserRowServiceSpacing; Loading Loading @@ -273,6 +276,8 @@ public class ChooserActivity extends ResolverActivity { sri.connection.destroy(); mServiceConnections.remove(sri.connection); if (mServiceConnections.isEmpty()) { logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE); sendVoiceChoicesIfNeeded(); } break; Loading @@ -283,6 +288,8 @@ public class ChooserActivity extends ResolverActivity { } unbindRemainingServices(); logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE); sendVoiceChoicesIfNeeded(); mChooserListAdapter.completeServiceTargetLoading(); break; Loading @@ -305,6 +312,8 @@ public class ChooserActivity extends ResolverActivity { break; case SHORTCUT_MANAGER_SHARE_TARGET_RESULT_COMPLETED: logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER); sendVoiceChoicesIfNeeded(); break; Loading Loading @@ -1155,6 +1164,8 @@ public class ChooserActivity extends ResolverActivity { } void queryTargetServices(ChooserListAdapter adapter) { mQueriedTargetServicesTimeMs = System.currentTimeMillis(); final PackageManager pm = getPackageManager(); ShortcutManager sm = (ShortcutManager) getSystemService(ShortcutManager.class); int targetsToQuery = 0; Loading Loading @@ -1281,6 +1292,7 @@ public class ChooserActivity extends ResolverActivity { private void queryDirectShareTargets( ChooserListAdapter adapter, boolean skipAppPredictionService) { mQueriedSharingShortcutsTimeMs = System.currentTimeMillis(); if (!skipAppPredictionService) { AppPredictor appPredictor = getAppPredictorForDirectShareIfEnabled(); if (appPredictor != null) { Loading Loading @@ -1391,6 +1403,14 @@ public class ChooserActivity extends ResolverActivity { // Do nothing. We'll send the voice stuff ourselves. } private void logDirectShareTargetReceived(int logCategory) { final long queryTime = logCategory == MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER ? mQueriedSharingShortcutsTimeMs : mQueriedTargetServicesTimeMs; final int apiLatency = (int) (System.currentTimeMillis() - queryTime); getMetricsLogger().write(new LogMaker(logCategory).setSubtype(apiLatency)); } void updateModelAndChooserCounts(TargetInfo info) { if (info != null) { sendClickToAppPredictor(info); Loading proto/src/metrics_constants/metrics_constants.proto +21 −0 Original line number Diff line number Diff line Loading @@ -263,6 +263,14 @@ message MetricsEvent { PREVIOUSLY_VISIBLE = 2; } // Types for ACTION_SHORTCUTS_CHANGED enum ShortcutsChangesInfo { SHORTCUTS_CHANGED_UNKNOWN = 0; SHORTCUTS_CHANGED_USER_ID = 1; SHORTCUTS_CHANGED_PACKAGE_COUNT = 2; SHORTCUTS_CHANGED_SHORTCUT_COUNT = 3; } // Explanations for notification importance, derived from // NotificationRecord.mImportanceExplanation. enum NotificationImportanceExplanation { Loading Loading @@ -7222,6 +7230,19 @@ message MetricsEvent { // OS: Q ASSISTANT = 1716; // ACTION: Published shortcuts in ShortcutManager changed // TYPE: All the SHORTCUTS_CHANGED_* values in ShortcutsChangesInfo // OS: Q ACTION_SHORTCUTS_CHANGED = 1717; // ACTION: Direct share targets loaded via ShortcutManager // OS: Q ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER = 1718; // ACTION: Direct share targets loaded via ChooserService // OS: Q ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE = 1719; // ---- End Q Constants, all Q constants go above this line ---- // Add new aosp constants above this line. // END OF AOSP CONSTANTS Loading services/core/java/com/android/server/pm/ShortcutPackage.java +46 −4 Original line number Diff line number Diff line Loading @@ -680,20 +680,23 @@ class ShortcutPackage extends ShortcutPackageItem { final List<ShortcutManager.ShareShortcutInfo> result = new ArrayList<>(); for (int i = 0; i < shortcuts.size(); i++) { final ShortcutInfo si = shortcuts.get(i); final Set<String> categories = shortcuts.get(i).getCategories(); if (categories == null || categories.isEmpty()) { continue; } for (int j = 0; j < matchedTargets.size(); j++) { // Shortcut must have all of share target categories boolean hasAllCategories = true; final ShareTargetInfo target = matchedTargets.get(j); for (int q = 0; q < target.mCategories.length; q++) { if (!si.getCategories().contains(target.mCategories[q])) { if (!categories.contains(target.mCategories[q])) { hasAllCategories = false; break; } } if (hasAllCategories) { result.add(new ShortcutManager.ShareShortcutInfo(si, new ComponentName( getPackageName(), target.mTargetClass))); result.add(new ShortcutManager.ShareShortcutInfo(shortcuts.get(i), new ComponentName(getPackageName(), target.mTargetClass))); break; } } Loading @@ -705,6 +708,45 @@ class ShortcutPackage extends ShortcutPackageItem { return !mShareTargets.isEmpty(); } /** * Returns the number of shortcuts that can be used as a share target in the ShareSheet. Such * shortcuts must have a matching category with at least one of the defined ShareTargets from * the app's Xml resource. */ int getSharingShortcutCount() { if (mShortcuts.isEmpty() || mShareTargets.isEmpty()) { return 0; } // Get the list of all dynamic shortcuts in this package final ArrayList<ShortcutInfo> shortcuts = new ArrayList<>(); findAll(shortcuts, ShortcutInfo::isDynamicVisible, ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER); int sharingShortcutCount = 0; for (int i = 0; i < shortcuts.size(); i++) { final Set<String> categories = shortcuts.get(i).getCategories(); if (categories == null || categories.isEmpty()) { continue; } for (int j = 0; j < mShareTargets.size(); j++) { // A SharingShortcut must have all of share target categories boolean hasAllCategories = true; final ShareTargetInfo target = mShareTargets.get(j); for (int q = 0; q < target.mCategories.length; q++) { if (!categories.contains(target.mCategories[q])) { hasAllCategories = false; break; } } if (hasAllCategories) { sharingShortcutCount++; break; } } } return sharingShortcutCount; } /** * Return the filenames (excluding path names) of icon bitmap files from this package. */ Loading services/core/java/com/android/server/pm/ShortcutService.java +6 −0 Original line number Diff line number Diff line Loading @@ -95,6 +95,7 @@ import android.view.IWindowManager; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.logging.MetricsLogger; import com.android.internal.os.BackgroundThread; import com.android.internal.util.DumpUtils; import com.android.internal.util.FastXmlSerializer; Loading Loading @@ -413,6 +414,9 @@ public class ShortcutService extends IShortcutService.Stub { @GuardedBy("mLock") private Exception mLastWtfStacktrace; @GuardedBy("mLock") private final MetricsLogger mMetricsLogger = new MetricsLogger(); static class InvalidFileFormatException extends Exception { public InvalidFileFormatException(String message, Throwable cause) { super(message, cause); Loading Loading @@ -981,6 +985,8 @@ public class ShortcutService extends IShortcutService.Stub { Slog.e(TAG, "Failed to write to file " + file.getBaseFile(), e); file.failWrite(os); } getUserShortcutsLocked(userId).logSharingShortcutStats(mMetricsLogger); } @GuardedBy("mLock") Loading services/core/java/com/android/server/pm/ShortcutUser.java +22 −0 Original line number Diff line number Diff line Loading @@ -20,6 +20,7 @@ import android.annotation.Nullable; import android.annotation.UserIdInt; import android.content.ComponentName; import android.content.pm.ShortcutManager; import android.metrics.LogMaker; import android.text.TextUtils; import android.text.format.Formatter; import android.util.ArrayMap; Loading @@ -27,6 +28,8 @@ import android.util.Log; import android.util.Slog; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.logging.MetricsLogger; import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.internal.util.Preconditions; import com.android.server.pm.ShortcutService.DumpFilter; import com.android.server.pm.ShortcutService.InvalidFileFormatException; Loading Loading @@ -647,4 +650,23 @@ class ShortcutUser { return result; } void logSharingShortcutStats(MetricsLogger logger) { int packageWithShareTargetsCount = 0; int totalSharingShortcutCount = 0; for (int i = 0; i < mPackages.size(); i++) { if (mPackages.valueAt(i).hasShareTargets()) { packageWithShareTargetsCount++; totalSharingShortcutCount += mPackages.valueAt(i).getSharingShortcutCount(); } } final LogMaker logMaker = new LogMaker(MetricsEvent.ACTION_SHORTCUTS_CHANGED); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_USER_ID) .setSubtype(mUserId)); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_PACKAGE_COUNT) .setSubtype(packageWithShareTargetsCount)); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_SHORTCUT_COUNT) .setSubtype(totalSharingShortcutCount)); } } Loading
core/java/com/android/internal/app/ChooserActivity.java +20 −0 Original line number Diff line number Diff line Loading @@ -202,6 +202,9 @@ public class ChooserActivity extends ResolverActivity { private long mChooserShownTime; protected boolean mIsSuccessfullySelected; private long mQueriedTargetServicesTimeMs; private long mQueriedSharingShortcutsTimeMs; private ChooserListAdapter mChooserListAdapter; private ChooserRowAdapter mChooserRowAdapter; private int mChooserRowServiceSpacing; Loading Loading @@ -273,6 +276,8 @@ public class ChooserActivity extends ResolverActivity { sri.connection.destroy(); mServiceConnections.remove(sri.connection); if (mServiceConnections.isEmpty()) { logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE); sendVoiceChoicesIfNeeded(); } break; Loading @@ -283,6 +288,8 @@ public class ChooserActivity extends ResolverActivity { } unbindRemainingServices(); logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE); sendVoiceChoicesIfNeeded(); mChooserListAdapter.completeServiceTargetLoading(); break; Loading @@ -305,6 +312,8 @@ public class ChooserActivity extends ResolverActivity { break; case SHORTCUT_MANAGER_SHARE_TARGET_RESULT_COMPLETED: logDirectShareTargetReceived( MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER); sendVoiceChoicesIfNeeded(); break; Loading Loading @@ -1155,6 +1164,8 @@ public class ChooserActivity extends ResolverActivity { } void queryTargetServices(ChooserListAdapter adapter) { mQueriedTargetServicesTimeMs = System.currentTimeMillis(); final PackageManager pm = getPackageManager(); ShortcutManager sm = (ShortcutManager) getSystemService(ShortcutManager.class); int targetsToQuery = 0; Loading Loading @@ -1281,6 +1292,7 @@ public class ChooserActivity extends ResolverActivity { private void queryDirectShareTargets( ChooserListAdapter adapter, boolean skipAppPredictionService) { mQueriedSharingShortcutsTimeMs = System.currentTimeMillis(); if (!skipAppPredictionService) { AppPredictor appPredictor = getAppPredictorForDirectShareIfEnabled(); if (appPredictor != null) { Loading Loading @@ -1391,6 +1403,14 @@ public class ChooserActivity extends ResolverActivity { // Do nothing. We'll send the voice stuff ourselves. } private void logDirectShareTargetReceived(int logCategory) { final long queryTime = logCategory == MetricsEvent.ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER ? mQueriedSharingShortcutsTimeMs : mQueriedTargetServicesTimeMs; final int apiLatency = (int) (System.currentTimeMillis() - queryTime); getMetricsLogger().write(new LogMaker(logCategory).setSubtype(apiLatency)); } void updateModelAndChooserCounts(TargetInfo info) { if (info != null) { sendClickToAppPredictor(info); Loading
proto/src/metrics_constants/metrics_constants.proto +21 −0 Original line number Diff line number Diff line Loading @@ -263,6 +263,14 @@ message MetricsEvent { PREVIOUSLY_VISIBLE = 2; } // Types for ACTION_SHORTCUTS_CHANGED enum ShortcutsChangesInfo { SHORTCUTS_CHANGED_UNKNOWN = 0; SHORTCUTS_CHANGED_USER_ID = 1; SHORTCUTS_CHANGED_PACKAGE_COUNT = 2; SHORTCUTS_CHANGED_SHORTCUT_COUNT = 3; } // Explanations for notification importance, derived from // NotificationRecord.mImportanceExplanation. enum NotificationImportanceExplanation { Loading Loading @@ -7222,6 +7230,19 @@ message MetricsEvent { // OS: Q ASSISTANT = 1716; // ACTION: Published shortcuts in ShortcutManager changed // TYPE: All the SHORTCUTS_CHANGED_* values in ShortcutsChangesInfo // OS: Q ACTION_SHORTCUTS_CHANGED = 1717; // ACTION: Direct share targets loaded via ShortcutManager // OS: Q ACTION_DIRECT_SHARE_TARGETS_LOADED_SHORTCUT_MANAGER = 1718; // ACTION: Direct share targets loaded via ChooserService // OS: Q ACTION_DIRECT_SHARE_TARGETS_LOADED_CHOOSER_SERVICE = 1719; // ---- End Q Constants, all Q constants go above this line ---- // Add new aosp constants above this line. // END OF AOSP CONSTANTS Loading
services/core/java/com/android/server/pm/ShortcutPackage.java +46 −4 Original line number Diff line number Diff line Loading @@ -680,20 +680,23 @@ class ShortcutPackage extends ShortcutPackageItem { final List<ShortcutManager.ShareShortcutInfo> result = new ArrayList<>(); for (int i = 0; i < shortcuts.size(); i++) { final ShortcutInfo si = shortcuts.get(i); final Set<String> categories = shortcuts.get(i).getCategories(); if (categories == null || categories.isEmpty()) { continue; } for (int j = 0; j < matchedTargets.size(); j++) { // Shortcut must have all of share target categories boolean hasAllCategories = true; final ShareTargetInfo target = matchedTargets.get(j); for (int q = 0; q < target.mCategories.length; q++) { if (!si.getCategories().contains(target.mCategories[q])) { if (!categories.contains(target.mCategories[q])) { hasAllCategories = false; break; } } if (hasAllCategories) { result.add(new ShortcutManager.ShareShortcutInfo(si, new ComponentName( getPackageName(), target.mTargetClass))); result.add(new ShortcutManager.ShareShortcutInfo(shortcuts.get(i), new ComponentName(getPackageName(), target.mTargetClass))); break; } } Loading @@ -705,6 +708,45 @@ class ShortcutPackage extends ShortcutPackageItem { return !mShareTargets.isEmpty(); } /** * Returns the number of shortcuts that can be used as a share target in the ShareSheet. Such * shortcuts must have a matching category with at least one of the defined ShareTargets from * the app's Xml resource. */ int getSharingShortcutCount() { if (mShortcuts.isEmpty() || mShareTargets.isEmpty()) { return 0; } // Get the list of all dynamic shortcuts in this package final ArrayList<ShortcutInfo> shortcuts = new ArrayList<>(); findAll(shortcuts, ShortcutInfo::isDynamicVisible, ShortcutInfo.CLONE_REMOVE_FOR_LAUNCHER); int sharingShortcutCount = 0; for (int i = 0; i < shortcuts.size(); i++) { final Set<String> categories = shortcuts.get(i).getCategories(); if (categories == null || categories.isEmpty()) { continue; } for (int j = 0; j < mShareTargets.size(); j++) { // A SharingShortcut must have all of share target categories boolean hasAllCategories = true; final ShareTargetInfo target = mShareTargets.get(j); for (int q = 0; q < target.mCategories.length; q++) { if (!categories.contains(target.mCategories[q])) { hasAllCategories = false; break; } } if (hasAllCategories) { sharingShortcutCount++; break; } } } return sharingShortcutCount; } /** * Return the filenames (excluding path names) of icon bitmap files from this package. */ Loading
services/core/java/com/android/server/pm/ShortcutService.java +6 −0 Original line number Diff line number Diff line Loading @@ -95,6 +95,7 @@ import android.view.IWindowManager; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.logging.MetricsLogger; import com.android.internal.os.BackgroundThread; import com.android.internal.util.DumpUtils; import com.android.internal.util.FastXmlSerializer; Loading Loading @@ -413,6 +414,9 @@ public class ShortcutService extends IShortcutService.Stub { @GuardedBy("mLock") private Exception mLastWtfStacktrace; @GuardedBy("mLock") private final MetricsLogger mMetricsLogger = new MetricsLogger(); static class InvalidFileFormatException extends Exception { public InvalidFileFormatException(String message, Throwable cause) { super(message, cause); Loading Loading @@ -981,6 +985,8 @@ public class ShortcutService extends IShortcutService.Stub { Slog.e(TAG, "Failed to write to file " + file.getBaseFile(), e); file.failWrite(os); } getUserShortcutsLocked(userId).logSharingShortcutStats(mMetricsLogger); } @GuardedBy("mLock") Loading
services/core/java/com/android/server/pm/ShortcutUser.java +22 −0 Original line number Diff line number Diff line Loading @@ -20,6 +20,7 @@ import android.annotation.Nullable; import android.annotation.UserIdInt; import android.content.ComponentName; import android.content.pm.ShortcutManager; import android.metrics.LogMaker; import android.text.TextUtils; import android.text.format.Formatter; import android.util.ArrayMap; Loading @@ -27,6 +28,8 @@ import android.util.Log; import android.util.Slog; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.logging.MetricsLogger; import com.android.internal.logging.nano.MetricsProto.MetricsEvent; import com.android.internal.util.Preconditions; import com.android.server.pm.ShortcutService.DumpFilter; import com.android.server.pm.ShortcutService.InvalidFileFormatException; Loading Loading @@ -647,4 +650,23 @@ class ShortcutUser { return result; } void logSharingShortcutStats(MetricsLogger logger) { int packageWithShareTargetsCount = 0; int totalSharingShortcutCount = 0; for (int i = 0; i < mPackages.size(); i++) { if (mPackages.valueAt(i).hasShareTargets()) { packageWithShareTargetsCount++; totalSharingShortcutCount += mPackages.valueAt(i).getSharingShortcutCount(); } } final LogMaker logMaker = new LogMaker(MetricsEvent.ACTION_SHORTCUTS_CHANGED); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_USER_ID) .setSubtype(mUserId)); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_PACKAGE_COUNT) .setSubtype(packageWithShareTargetsCount)); logger.write(logMaker.setType(MetricsEvent.SHORTCUTS_CHANGED_SHORTCUT_COUNT) .setSubtype(totalSharingShortcutCount)); } }