Loading core/api/current.txt +9 −9 Original line number Diff line number Diff line Loading @@ -12881,18 +12881,18 @@ package android.content.pm { } public class ShortcutManager { method public boolean addDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method public android.content.Intent createShortcutResultIntent(@NonNull android.content.pm.ShortcutInfo); method @WorkerThread public boolean addDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public android.content.Intent createShortcutResultIntent(@NonNull android.content.pm.ShortcutInfo); method public void disableShortcuts(@NonNull java.util.List<java.lang.String>); method public void disableShortcuts(@NonNull java.util.List<java.lang.String>, CharSequence); method public void enableShortcuts(@NonNull java.util.List<java.lang.String>); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts(); method public int getIconMaxHeight(); method public int getIconMaxWidth(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getManifestShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getManifestShortcuts(); method public int getMaxShortcutCountPerActivity(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(int); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(int); method public boolean isRateLimitingActive(); method public boolean isRequestPinShortcutSupported(); method public void pushDynamicShortcut(@NonNull android.content.pm.ShortcutInfo); Loading @@ -12900,10 +12900,10 @@ package android.content.pm { method public void removeDynamicShortcuts(@NonNull java.util.List<java.lang.String>); method public void removeLongLivedShortcuts(@NonNull java.util.List<java.lang.String>); method public void reportShortcutUsed(String); method public boolean requestPinShortcut(@NonNull android.content.pm.ShortcutInfo, @Nullable android.content.IntentSender); method public boolean setDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public boolean requestPinShortcut(@NonNull android.content.pm.ShortcutInfo, @Nullable android.content.IntentSender); method @WorkerThread public boolean setDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method public void updateShortcutVisibility(@NonNull String, @Nullable byte[], boolean); method public boolean updateShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public boolean updateShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); field public static final int FLAG_MATCH_CACHED = 8; // 0x8 field public static final int FLAG_MATCH_DYNAMIC = 2; // 0x2 field public static final int FLAG_MATCH_MANIFEST = 1; // 0x1 core/api/system-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -2703,7 +2703,7 @@ package android.content.pm { } public class ShortcutManager { method @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_APP_PREDICTIONS) public java.util.List<android.content.pm.ShortcutManager.ShareShortcutInfo> getShareTargets(@NonNull android.content.IntentFilter); method @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_APP_PREDICTIONS) @WorkerThread public java.util.List<android.content.pm.ShortcutManager.ShareShortcutInfo> getShareTargets(@NonNull android.content.IntentFilter); method public boolean hasShareTargets(@NonNull String); } Loading core/java/android/content/pm/IShortcutService.aidl +31 −27 Original line number Diff line number Diff line Loading @@ -21,32 +21,34 @@ import android.content.IntentSender; import android.content.pm.ParceledListSlice; import android.content.pm.ShortcutInfo; /** * {@hide} */ import com.android.internal.infra.AndroidFuture; /** {@hide} */ interface IShortcutService { boolean setDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId); oneway void setDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId, in AndroidFuture callback); boolean addDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId); oneway void addDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId, in AndroidFuture callback); void removeDynamicShortcuts(String packageName, in List shortcutIds, int userId); oneway void removeDynamicShortcuts(String packageName, in List shortcutIds, int userId); void removeAllDynamicShortcuts(String packageName, int userId); oneway void removeAllDynamicShortcuts(String packageName, int userId); boolean updateShortcuts(String packageName, in ParceledListSlice shortcuts, int userId); oneway void updateShortcuts(String packageName, in ParceledListSlice shortcuts, int userId, in AndroidFuture callback); boolean requestPinShortcut(String packageName, in ShortcutInfo shortcut, in IntentSender resultIntent, int userId); oneway void requestPinShortcut(String packageName, in ShortcutInfo shortcut, in IntentSender resultIntent, int userId, in AndroidFuture callback); Intent createShortcutResultIntent(String packageName, in ShortcutInfo shortcut, int userId); oneway void createShortcutResultIntent(String packageName, in ShortcutInfo shortcut, int userId, in AndroidFuture callback); void disableShortcuts(String packageName, in List shortcutIds, CharSequence disabledMessage, int disabledMessageResId, int userId); oneway void disableShortcuts(String packageName, in List shortcutIds, CharSequence disabledMessage, int disabledMessageResId, int userId); void enableShortcuts(String packageName, in List shortcutIds, int userId); oneway void enableShortcuts(String packageName, in List shortcutIds, int userId); int getMaxShortcutCountPerActivity(String packageName, int userId); Loading @@ -56,29 +58,31 @@ interface IShortcutService { int getIconMaxDimensions(String packageName, int userId); void reportShortcutUsed(String packageName, String shortcutId, int userId); oneway void reportShortcutUsed(String packageName, String shortcutId, int userId); void resetThrottling(); // system only API for developer opsions oneway void resetThrottling(); // system only API for developer opsions void onApplicationActive(String packageName, int userId); // system only API for sysUI oneway void onApplicationActive(String packageName, int userId); // system only API for sysUI byte[] getBackupPayload(int user); void applyRestore(in byte[] payload, int user); oneway void applyRestore(in byte[] payload, int user); boolean isRequestPinItemSupported(int user, int requestType); // System API used by framework's ShareSheet (ChooserActivity) ParceledListSlice getShareTargets(String packageName, in IntentFilter filter, int userId); oneway void getShareTargets(String packageName, in IntentFilter filter, int userId, in AndroidFuture<ParceledListSlice> callback); boolean hasShareTargets(String packageName, String packageToCheck, int userId); void removeLongLivedShortcuts(String packageName, in List shortcutIds, int userId); oneway void removeLongLivedShortcuts(String packageName, in List shortcutIds, int userId); ParceledListSlice getShortcuts(String packageName, int matchFlags, int userId); oneway void getShortcuts(String packageName, int matchFlags, int userId, in AndroidFuture<ParceledListSlice<ShortcutInfo>> callback); void pushDynamicShortcut(String packageName, in ShortcutInfo shortcut, int userId); oneway void pushDynamicShortcut(String packageName, in ShortcutInfo shortcut, int userId); void updateShortcutVisibility(String callingPkg, String packageName, in byte[] certificate, in boolean visible, int userId); oneway void updateShortcutVisibility(String callingPkg, String packageName, in byte[] certificate, in boolean visible, int userId); } core/java/android/content/pm/ShortcutManager.java +78 −30 Original line number Diff line number Diff line Loading @@ -24,6 +24,7 @@ import android.annotation.SystemApi; import android.annotation.SystemService; import android.annotation.TestApi; import android.annotation.UserIdInt; import android.annotation.WorkerThread; import android.app.Notification; import android.app.usage.UsageStatsManager; import android.compat.annotation.UnsupportedAppUsage; Loading @@ -42,10 +43,12 @@ import android.os.ServiceManager; import android.os.UserHandle; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.infra.AndroidFuture; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.util.List; import java.util.concurrent.ExecutionException; /** * <p><code>ShortcutManager</code> executes operations on an app's set of <i>shortcuts</i>, which Loading Loading @@ -140,13 +143,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean setDynamicShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.setDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.setDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading @@ -158,14 +164,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getDynamicShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_DYNAMIC, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_DYNAMIC, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -177,14 +186,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getManifestShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_MANIFEST, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_MANIFEST, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -205,14 +217,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getShortcuts(@ShortcutMatchFlags int matchFlags) { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), matchFlags, injectMyUserId()) .getList(); mService.getShortcuts(mContext.getPackageName(), matchFlags, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -228,13 +242,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean addDynamicShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.addDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.addDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -287,14 +304,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getPinnedShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_PINNED, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_PINNED, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -309,13 +329,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean updateShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.updateShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.updateShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -584,14 +607,17 @@ public class ShortcutManager { * @throws IllegalStateException The caller doesn't have a foreground activity or a foreground * service, or the device is locked. */ @WorkerThread public boolean requestPinShortcut(@NonNull ShortcutInfo shortcut, @Nullable IntentSender resultIntent) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.requestPinShortcut(mContext.getPackageName(), shortcut, resultIntent, injectMyUserId()); mService.requestPinShortcut(mContext.getPackageName(), shortcut, resultIntent, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading @@ -611,13 +637,16 @@ public class ShortcutManager { * * @throws IllegalArgumentException if a shortcut with the same ID exists and is disabled. */ @WorkerThread public Intent createShortcutResultIntent(@NonNull ShortcutInfo shortcut) { final AndroidFuture<Intent> future = new AndroidFuture<>(); try { return mService.createShortcutResultIntent(mContext.getPackageName(), shortcut, injectMyUserId()); mService.createShortcutResultIntent(mContext.getPackageName(), shortcut, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -650,16 +679,18 @@ public class ShortcutManager { * @return List of {@link ShareShortcutInfo}s that match the given IntentFilter. * @hide */ @WorkerThread @NonNull @SystemApi @RequiresPermission(Manifest.permission.MANAGE_APP_PREDICTIONS) public List<ShareShortcutInfo> getShareTargets(@NonNull IntentFilter filter) { final AndroidFuture<ParceledListSlice> future = new AndroidFuture<>(); try { return mService.getShareTargets(mContext.getPackageName(), filter, injectMyUserId()).getList(); mService.getShareTargets(mContext.getPackageName(), filter, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading Loading @@ -788,4 +819,21 @@ public class ShortcutManager { throw e.rethrowFromSystemServer(); } } private static <T> T getFutureOrThrow(@NonNull AndroidFuture<T> future) { try { return future.get(); } catch (Throwable e) { if (e instanceof ExecutionException) { e = e.getCause(); } if (e instanceof RuntimeException) { throw (RuntimeException) e; } if (e instanceof Error) { throw (Error) e; } throw new RuntimeException(e); } } } services/core/java/com/android/server/pm/ShortcutService.java +39 −26 Original line number Diff line number Diff line Loading @@ -103,6 +103,7 @@ import android.view.IWindowManager; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.infra.AndroidFuture; import com.android.internal.logging.MetricsLogger; import com.android.internal.os.BackgroundThread; import com.android.internal.util.CollectionUtils; Loading Loading @@ -142,6 +143,7 @@ import java.util.Arrays; import java.util.Collections; import java.util.List; import java.util.Objects; import java.util.concurrent.ExecutionException; import java.util.concurrent.atomic.AtomicBoolean; import java.util.function.Consumer; import java.util.function.Predicate; Loading Loading @@ -1885,8 +1887,8 @@ public class ShortcutService extends IShortcutService.Stub { // === APIs === @Override public boolean setDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void setDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, @NonNull AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading @@ -1913,7 +1915,7 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); } // Initialize the implicit ranks for ShortcutPackage.adjustRanks(). Loading Loading @@ -1949,12 +1951,12 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override public boolean updateShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void updateShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading @@ -1981,7 +1983,8 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); return; } // Initialize the implicit ranks for ShortcutPackage.adjustRanks(). Loading Loading @@ -2046,12 +2049,12 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override public boolean addDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void addDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading Loading @@ -2081,7 +2084,8 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); return; } for (int i = 0; i < size; i++) { final ShortcutInfo newShortcut = newShortcuts.get(i); Loading Loading @@ -2109,7 +2113,7 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override Loading Loading @@ -2174,15 +2178,17 @@ public class ShortcutService extends IShortcutService.Stub { } @Override public boolean requestPinShortcut(String packageName, ShortcutInfo shortcut, IntentSender resultIntent, int userId) { public void requestPinShortcut(String packageName, ShortcutInfo shortcut, IntentSender resultIntent, int userId, AndroidFuture callback) { Objects.requireNonNull(shortcut); Objects.requireNonNull(callback); Preconditions.checkArgument(shortcut.isEnabled(), "Shortcut must be enabled"); return requestPinItem(packageName, userId, shortcut, null, null, resultIntent); callback.complete(requestPinItem(packageName, userId, shortcut, null, null, resultIntent)); } @Override public Intent createShortcutResultIntent(String packageName, ShortcutInfo shortcut, int userId) public void createShortcutResultIntent(String packageName, ShortcutInfo shortcut, int userId, AndroidFuture callback) throws RemoteException { Objects.requireNonNull(shortcut); Preconditions.checkArgument(shortcut.isEnabled(), "Shortcut must be enabled"); Loading @@ -2198,7 +2204,7 @@ public class ShortcutService extends IShortcutService.Stub { } verifyStates(); return ret; callback.complete(ret); } /** Loading Loading @@ -2455,8 +2461,9 @@ public class ShortcutService extends IShortcutService.Stub { } @Override public ParceledListSlice<ShortcutInfo> getShortcuts(String packageName, @ShortcutManager.ShortcutMatchFlags int matchFlags, @UserIdInt int userId) { public void getShortcuts(String packageName, @ShortcutManager.ShortcutMatchFlags int matchFlags, @UserIdInt int userId, AndroidFuture<ParceledListSlice<ShortcutInfo>> callback) { verifyCaller(packageName, userId); synchronized (mLock) { Loading @@ -2472,16 +2479,16 @@ public class ShortcutService extends IShortcutService.Stub { | (matchManifest ? ShortcutInfo.FLAG_MANIFEST : 0) | (matchCached ? ShortcutInfo.FLAG_CACHED_ALL : 0); return getShortcutsWithQueryLocked( callback.complete(getShortcutsWithQueryLocked( packageName, userId, ShortcutInfo.CLONE_REMOVE_FOR_CREATOR, (ShortcutInfo si) -> si.isVisibleToPublisher() && (si.getFlags() & shortcutFlags) != 0); si.isVisibleToPublisher() && (si.getFlags() & shortcutFlags) != 0)); } } @Override public ParceledListSlice<ShortcutManager.ShareShortcutInfo> getShareTargets(String packageName, IntentFilter filter, @UserIdInt int userId) { public void getShareTargets(String packageName, IntentFilter filter, @UserIdInt int userId, AndroidFuture<ParceledListSlice> callback) { Preconditions.checkStringNotEmpty(packageName, "packageName"); Objects.requireNonNull(filter, "intentFilter"); Loading @@ -2497,7 +2504,7 @@ public class ShortcutService extends IShortcutService.Stub { final ShortcutUser user = getUserShortcutsLocked(userId); user.forAllPackages(p -> shortcutInfoList.addAll(p.getMatchingShareTargets(filter))); return new ParceledListSlice<>(shortcutInfoList); callback.complete(new ParceledListSlice<>(shortcutInfoList)); } } Loading Loading @@ -3081,8 +3088,14 @@ public class ShortcutService extends IShortcutService.Stub { @Override public List<ShortcutManager.ShareShortcutInfo> getShareTargets( @NonNull String callingPackage, @NonNull IntentFilter intentFilter, int userId) { return ShortcutService.this.getShareTargets( callingPackage, intentFilter, userId).getList(); final AndroidFuture<ParceledListSlice> future = new AndroidFuture<>(); ShortcutService.this.getShareTargets( callingPackage, intentFilter, userId, future); try { return future.get().getList(); } catch (InterruptedException | ExecutionException e) { throw new RuntimeException(e); } } @Override Loading Loading
core/api/current.txt +9 −9 Original line number Diff line number Diff line Loading @@ -12881,18 +12881,18 @@ package android.content.pm { } public class ShortcutManager { method public boolean addDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method public android.content.Intent createShortcutResultIntent(@NonNull android.content.pm.ShortcutInfo); method @WorkerThread public boolean addDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public android.content.Intent createShortcutResultIntent(@NonNull android.content.pm.ShortcutInfo); method public void disableShortcuts(@NonNull java.util.List<java.lang.String>); method public void disableShortcuts(@NonNull java.util.List<java.lang.String>, CharSequence); method public void enableShortcuts(@NonNull java.util.List<java.lang.String>); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getDynamicShortcuts(); method public int getIconMaxHeight(); method public int getIconMaxWidth(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getManifestShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getManifestShortcuts(); method public int getMaxShortcutCountPerActivity(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts(); method @NonNull public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(int); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getPinnedShortcuts(); method @NonNull @WorkerThread public java.util.List<android.content.pm.ShortcutInfo> getShortcuts(int); method public boolean isRateLimitingActive(); method public boolean isRequestPinShortcutSupported(); method public void pushDynamicShortcut(@NonNull android.content.pm.ShortcutInfo); Loading @@ -12900,10 +12900,10 @@ package android.content.pm { method public void removeDynamicShortcuts(@NonNull java.util.List<java.lang.String>); method public void removeLongLivedShortcuts(@NonNull java.util.List<java.lang.String>); method public void reportShortcutUsed(String); method public boolean requestPinShortcut(@NonNull android.content.pm.ShortcutInfo, @Nullable android.content.IntentSender); method public boolean setDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public boolean requestPinShortcut(@NonNull android.content.pm.ShortcutInfo, @Nullable android.content.IntentSender); method @WorkerThread public boolean setDynamicShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method public void updateShortcutVisibility(@NonNull String, @Nullable byte[], boolean); method public boolean updateShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); method @WorkerThread public boolean updateShortcuts(@NonNull java.util.List<android.content.pm.ShortcutInfo>); field public static final int FLAG_MATCH_CACHED = 8; // 0x8 field public static final int FLAG_MATCH_DYNAMIC = 2; // 0x2 field public static final int FLAG_MATCH_MANIFEST = 1; // 0x1
core/api/system-current.txt +1 −1 Original line number Diff line number Diff line Loading @@ -2703,7 +2703,7 @@ package android.content.pm { } public class ShortcutManager { method @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_APP_PREDICTIONS) public java.util.List<android.content.pm.ShortcutManager.ShareShortcutInfo> getShareTargets(@NonNull android.content.IntentFilter); method @NonNull @RequiresPermission(android.Manifest.permission.MANAGE_APP_PREDICTIONS) @WorkerThread public java.util.List<android.content.pm.ShortcutManager.ShareShortcutInfo> getShareTargets(@NonNull android.content.IntentFilter); method public boolean hasShareTargets(@NonNull String); } Loading
core/java/android/content/pm/IShortcutService.aidl +31 −27 Original line number Diff line number Diff line Loading @@ -21,32 +21,34 @@ import android.content.IntentSender; import android.content.pm.ParceledListSlice; import android.content.pm.ShortcutInfo; /** * {@hide} */ import com.android.internal.infra.AndroidFuture; /** {@hide} */ interface IShortcutService { boolean setDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId); oneway void setDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId, in AndroidFuture callback); boolean addDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId); oneway void addDynamicShortcuts(String packageName, in ParceledListSlice shortcutInfoList, int userId, in AndroidFuture callback); void removeDynamicShortcuts(String packageName, in List shortcutIds, int userId); oneway void removeDynamicShortcuts(String packageName, in List shortcutIds, int userId); void removeAllDynamicShortcuts(String packageName, int userId); oneway void removeAllDynamicShortcuts(String packageName, int userId); boolean updateShortcuts(String packageName, in ParceledListSlice shortcuts, int userId); oneway void updateShortcuts(String packageName, in ParceledListSlice shortcuts, int userId, in AndroidFuture callback); boolean requestPinShortcut(String packageName, in ShortcutInfo shortcut, in IntentSender resultIntent, int userId); oneway void requestPinShortcut(String packageName, in ShortcutInfo shortcut, in IntentSender resultIntent, int userId, in AndroidFuture callback); Intent createShortcutResultIntent(String packageName, in ShortcutInfo shortcut, int userId); oneway void createShortcutResultIntent(String packageName, in ShortcutInfo shortcut, int userId, in AndroidFuture callback); void disableShortcuts(String packageName, in List shortcutIds, CharSequence disabledMessage, int disabledMessageResId, int userId); oneway void disableShortcuts(String packageName, in List shortcutIds, CharSequence disabledMessage, int disabledMessageResId, int userId); void enableShortcuts(String packageName, in List shortcutIds, int userId); oneway void enableShortcuts(String packageName, in List shortcutIds, int userId); int getMaxShortcutCountPerActivity(String packageName, int userId); Loading @@ -56,29 +58,31 @@ interface IShortcutService { int getIconMaxDimensions(String packageName, int userId); void reportShortcutUsed(String packageName, String shortcutId, int userId); oneway void reportShortcutUsed(String packageName, String shortcutId, int userId); void resetThrottling(); // system only API for developer opsions oneway void resetThrottling(); // system only API for developer opsions void onApplicationActive(String packageName, int userId); // system only API for sysUI oneway void onApplicationActive(String packageName, int userId); // system only API for sysUI byte[] getBackupPayload(int user); void applyRestore(in byte[] payload, int user); oneway void applyRestore(in byte[] payload, int user); boolean isRequestPinItemSupported(int user, int requestType); // System API used by framework's ShareSheet (ChooserActivity) ParceledListSlice getShareTargets(String packageName, in IntentFilter filter, int userId); oneway void getShareTargets(String packageName, in IntentFilter filter, int userId, in AndroidFuture<ParceledListSlice> callback); boolean hasShareTargets(String packageName, String packageToCheck, int userId); void removeLongLivedShortcuts(String packageName, in List shortcutIds, int userId); oneway void removeLongLivedShortcuts(String packageName, in List shortcutIds, int userId); ParceledListSlice getShortcuts(String packageName, int matchFlags, int userId); oneway void getShortcuts(String packageName, int matchFlags, int userId, in AndroidFuture<ParceledListSlice<ShortcutInfo>> callback); void pushDynamicShortcut(String packageName, in ShortcutInfo shortcut, int userId); oneway void pushDynamicShortcut(String packageName, in ShortcutInfo shortcut, int userId); void updateShortcutVisibility(String callingPkg, String packageName, in byte[] certificate, in boolean visible, int userId); oneway void updateShortcutVisibility(String callingPkg, String packageName, in byte[] certificate, in boolean visible, int userId); }
core/java/android/content/pm/ShortcutManager.java +78 −30 Original line number Diff line number Diff line Loading @@ -24,6 +24,7 @@ import android.annotation.SystemApi; import android.annotation.SystemService; import android.annotation.TestApi; import android.annotation.UserIdInt; import android.annotation.WorkerThread; import android.app.Notification; import android.app.usage.UsageStatsManager; import android.compat.annotation.UnsupportedAppUsage; Loading @@ -42,10 +43,12 @@ import android.os.ServiceManager; import android.os.UserHandle; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.infra.AndroidFuture; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.util.List; import java.util.concurrent.ExecutionException; /** * <p><code>ShortcutManager</code> executes operations on an app's set of <i>shortcuts</i>, which Loading Loading @@ -140,13 +143,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean setDynamicShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.setDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.setDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading @@ -158,14 +164,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getDynamicShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_DYNAMIC, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_DYNAMIC, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -177,14 +186,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getManifestShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_MANIFEST, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_MANIFEST, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -205,14 +217,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getShortcuts(@ShortcutMatchFlags int matchFlags) { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), matchFlags, injectMyUserId()) .getList(); mService.getShortcuts(mContext.getPackageName(), matchFlags, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -228,13 +242,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean addDynamicShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.addDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.addDynamicShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -287,14 +304,17 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread @NonNull public List<ShortcutInfo> getPinnedShortcuts() { final AndroidFuture<ParceledListSlice<ShortcutInfo>> future = new AndroidFuture<>(); try { return mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_PINNED, injectMyUserId()).getList(); mService.getShortcuts(mContext.getPackageName(), FLAG_MATCH_PINNED, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading @@ -309,13 +329,16 @@ public class ShortcutManager { * * @throws IllegalStateException when the user is locked. */ @WorkerThread public boolean updateShortcuts(@NonNull List<ShortcutInfo> shortcutInfoList) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.updateShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId()); mService.updateShortcuts(mContext.getPackageName(), new ParceledListSlice(shortcutInfoList), injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -584,14 +607,17 @@ public class ShortcutManager { * @throws IllegalStateException The caller doesn't have a foreground activity or a foreground * service, or the device is locked. */ @WorkerThread public boolean requestPinShortcut(@NonNull ShortcutInfo shortcut, @Nullable IntentSender resultIntent) { final AndroidFuture<Boolean> future = new AndroidFuture<>(); try { return mService.requestPinShortcut(mContext.getPackageName(), shortcut, resultIntent, injectMyUserId()); mService.requestPinShortcut(mContext.getPackageName(), shortcut, resultIntent, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading @@ -611,13 +637,16 @@ public class ShortcutManager { * * @throws IllegalArgumentException if a shortcut with the same ID exists and is disabled. */ @WorkerThread public Intent createShortcutResultIntent(@NonNull ShortcutInfo shortcut) { final AndroidFuture<Intent> future = new AndroidFuture<>(); try { return mService.createShortcutResultIntent(mContext.getPackageName(), shortcut, injectMyUserId()); mService.createShortcutResultIntent(mContext.getPackageName(), shortcut, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future); } /** Loading Loading @@ -650,16 +679,18 @@ public class ShortcutManager { * @return List of {@link ShareShortcutInfo}s that match the given IntentFilter. * @hide */ @WorkerThread @NonNull @SystemApi @RequiresPermission(Manifest.permission.MANAGE_APP_PREDICTIONS) public List<ShareShortcutInfo> getShareTargets(@NonNull IntentFilter filter) { final AndroidFuture<ParceledListSlice> future = new AndroidFuture<>(); try { return mService.getShareTargets(mContext.getPackageName(), filter, injectMyUserId()).getList(); mService.getShareTargets(mContext.getPackageName(), filter, injectMyUserId(), future); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); future.completeExceptionally(e); } return getFutureOrThrow(future).getList(); } /** Loading Loading @@ -788,4 +819,21 @@ public class ShortcutManager { throw e.rethrowFromSystemServer(); } } private static <T> T getFutureOrThrow(@NonNull AndroidFuture<T> future) { try { return future.get(); } catch (Throwable e) { if (e instanceof ExecutionException) { e = e.getCause(); } if (e instanceof RuntimeException) { throw (RuntimeException) e; } if (e instanceof Error) { throw (Error) e; } throw new RuntimeException(e); } } }
services/core/java/com/android/server/pm/ShortcutService.java +39 −26 Original line number Diff line number Diff line Loading @@ -103,6 +103,7 @@ import android.view.IWindowManager; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.infra.AndroidFuture; import com.android.internal.logging.MetricsLogger; import com.android.internal.os.BackgroundThread; import com.android.internal.util.CollectionUtils; Loading Loading @@ -142,6 +143,7 @@ import java.util.Arrays; import java.util.Collections; import java.util.List; import java.util.Objects; import java.util.concurrent.ExecutionException; import java.util.concurrent.atomic.AtomicBoolean; import java.util.function.Consumer; import java.util.function.Predicate; Loading Loading @@ -1885,8 +1887,8 @@ public class ShortcutService extends IShortcutService.Stub { // === APIs === @Override public boolean setDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void setDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, @NonNull AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading @@ -1913,7 +1915,7 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); } // Initialize the implicit ranks for ShortcutPackage.adjustRanks(). Loading Loading @@ -1949,12 +1951,12 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override public boolean updateShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void updateShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading @@ -1981,7 +1983,8 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); return; } // Initialize the implicit ranks for ShortcutPackage.adjustRanks(). Loading Loading @@ -2046,12 +2049,12 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override public boolean addDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId) { public void addDynamicShortcuts(String packageName, ParceledListSlice shortcutInfoList, @UserIdInt int userId, AndroidFuture callback) { verifyCaller(packageName, userId); final List<ShortcutInfo> newShortcuts = (List<ShortcutInfo>) shortcutInfoList.getList(); Loading Loading @@ -2081,7 +2084,8 @@ public class ShortcutService extends IShortcutService.Stub { // Throttling. if (!ps.tryApiCall(unlimited)) { return false; callback.complete(false); return; } for (int i = 0; i < size; i++) { final ShortcutInfo newShortcut = newShortcuts.get(i); Loading Loading @@ -2109,7 +2113,7 @@ public class ShortcutService extends IShortcutService.Stub { verifyStates(); return true; callback.complete(true); } @Override Loading Loading @@ -2174,15 +2178,17 @@ public class ShortcutService extends IShortcutService.Stub { } @Override public boolean requestPinShortcut(String packageName, ShortcutInfo shortcut, IntentSender resultIntent, int userId) { public void requestPinShortcut(String packageName, ShortcutInfo shortcut, IntentSender resultIntent, int userId, AndroidFuture callback) { Objects.requireNonNull(shortcut); Objects.requireNonNull(callback); Preconditions.checkArgument(shortcut.isEnabled(), "Shortcut must be enabled"); return requestPinItem(packageName, userId, shortcut, null, null, resultIntent); callback.complete(requestPinItem(packageName, userId, shortcut, null, null, resultIntent)); } @Override public Intent createShortcutResultIntent(String packageName, ShortcutInfo shortcut, int userId) public void createShortcutResultIntent(String packageName, ShortcutInfo shortcut, int userId, AndroidFuture callback) throws RemoteException { Objects.requireNonNull(shortcut); Preconditions.checkArgument(shortcut.isEnabled(), "Shortcut must be enabled"); Loading @@ -2198,7 +2204,7 @@ public class ShortcutService extends IShortcutService.Stub { } verifyStates(); return ret; callback.complete(ret); } /** Loading Loading @@ -2455,8 +2461,9 @@ public class ShortcutService extends IShortcutService.Stub { } @Override public ParceledListSlice<ShortcutInfo> getShortcuts(String packageName, @ShortcutManager.ShortcutMatchFlags int matchFlags, @UserIdInt int userId) { public void getShortcuts(String packageName, @ShortcutManager.ShortcutMatchFlags int matchFlags, @UserIdInt int userId, AndroidFuture<ParceledListSlice<ShortcutInfo>> callback) { verifyCaller(packageName, userId); synchronized (mLock) { Loading @@ -2472,16 +2479,16 @@ public class ShortcutService extends IShortcutService.Stub { | (matchManifest ? ShortcutInfo.FLAG_MANIFEST : 0) | (matchCached ? ShortcutInfo.FLAG_CACHED_ALL : 0); return getShortcutsWithQueryLocked( callback.complete(getShortcutsWithQueryLocked( packageName, userId, ShortcutInfo.CLONE_REMOVE_FOR_CREATOR, (ShortcutInfo si) -> si.isVisibleToPublisher() && (si.getFlags() & shortcutFlags) != 0); si.isVisibleToPublisher() && (si.getFlags() & shortcutFlags) != 0)); } } @Override public ParceledListSlice<ShortcutManager.ShareShortcutInfo> getShareTargets(String packageName, IntentFilter filter, @UserIdInt int userId) { public void getShareTargets(String packageName, IntentFilter filter, @UserIdInt int userId, AndroidFuture<ParceledListSlice> callback) { Preconditions.checkStringNotEmpty(packageName, "packageName"); Objects.requireNonNull(filter, "intentFilter"); Loading @@ -2497,7 +2504,7 @@ public class ShortcutService extends IShortcutService.Stub { final ShortcutUser user = getUserShortcutsLocked(userId); user.forAllPackages(p -> shortcutInfoList.addAll(p.getMatchingShareTargets(filter))); return new ParceledListSlice<>(shortcutInfoList); callback.complete(new ParceledListSlice<>(shortcutInfoList)); } } Loading Loading @@ -3081,8 +3088,14 @@ public class ShortcutService extends IShortcutService.Stub { @Override public List<ShortcutManager.ShareShortcutInfo> getShareTargets( @NonNull String callingPackage, @NonNull IntentFilter intentFilter, int userId) { return ShortcutService.this.getShareTargets( callingPackage, intentFilter, userId).getList(); final AndroidFuture<ParceledListSlice> future = new AndroidFuture<>(); ShortcutService.this.getShareTargets( callingPackage, intentFilter, userId, future); try { return future.get().getList(); } catch (InterruptedException | ExecutionException e) { throw new RuntimeException(e); } } @Override Loading