Loading src/com/android/launcher3/Launcher.java +3 −0 Original line number Diff line number Diff line Loading @@ -1090,6 +1090,9 @@ public class Launcher extends Activity if (!isWorkspaceLoading()) { // Process any items that were added while Launcher was away. InstallShortcutReceiver.disableAndFlushInstallQueue(this); // Refresh shortcuts if the permission changed. mModel.refreshShortcutsIfRequired(); } if (shouldShowDiscoveryBounce()) { Loading src/com/android/launcher3/LauncherModel.java +36 −5 Original line number Diff line number Diff line Loading @@ -146,6 +146,20 @@ public class LauncherModel extends BroadcastReceiver // Maps all launcher activities to the id's of their shortcuts (if they have any). private final MultiHashMap<ComponentKey, String> mBgDeepShortcutMap = new MultiHashMap<>(); private boolean mHasShortcutHostPermission; // Runnable to check if the shortcuts permission has changed. private final Runnable mShortcutPermissionCheckRunnable = new Runnable() { @Override public void run() { if (mDeepShortcutsLoaded) { boolean hasShortcutHostPermission = mDeepShortcutManager.hasHostPermission(); if (hasShortcutHostPermission != mHasShortcutHostPermission) { mApp.reloadWorkspace(); } } } }; // The lock that must be acquired before referencing any static bg data structures. Unlike // other locks, this one can generally be held long-term because we never expect any of these // static data structures to be referenced outside of the worker thread except on the first Loading Loading @@ -1244,6 +1258,7 @@ public class LauncherModel extends BroadcastReceiver if (resetAllAppsLoaded) mAllAppsLoaded = false; if (resetWorkspaceLoaded) mWorkspaceLoaded = false; // Always reset deep shortcuts loaded. // TODO: why? mDeepShortcutsLoaded = false; } } Loading Loading @@ -1299,6 +1314,7 @@ public class LauncherModel extends BroadcastReceiver // If there is already one running, tell it to stop. stopLoaderLocked(); mLoaderTask = new LoaderTask(mApp.getContext(), synchronousBindPage); // TODO: mDeepShortcutsLoaded does not need to be true for synchronous bind. if (synchronousBindPage != PagedView.INVALID_RESTORE_PAGE && mAllAppsLoaded && mWorkspaceLoaded && mDeepShortcutsLoaded && !mIsLoaderTaskRunning) { mLoaderTask.runBindSynchronousPage(synchronousBindPage); Loading Loading @@ -2793,6 +2809,8 @@ public class LauncherModel extends BroadcastReceiver } if (!mDeepShortcutsLoaded) { mBgDeepShortcutMap.clear(); mHasShortcutHostPermission = mDeepShortcutManager.hasHostPermission(); if (mHasShortcutHostPermission) { for (UserHandleCompat user : mUserManager.getUserProfiles()) { if (mUserManager.isUserUnlocked(user)) { List<ShortcutInfoCompat> shortcuts = mDeepShortcutManager Loading @@ -2800,6 +2818,7 @@ public class LauncherModel extends BroadcastReceiver updateDeepShortcutMap(null, user, shortcuts); } } } synchronized (LoaderTask.this) { if (mStopped) { return; Loading Loading @@ -2862,6 +2881,18 @@ public class LauncherModel extends BroadcastReceiver runOnMainThread(r); } /** * Refreshes the cached shortcuts if the shortcut permission has changed. * Current implementation simply reloads the workspace, but it can be optimized to * use partial updates similar to {@link UserManagerCompat} */ public void refreshShortcutsIfRequired() { if (Utilities.isNycMR1OrAbove()) { sWorker.removeCallbacks(mShortcutPermissionCheckRunnable); sWorker.post(mShortcutPermissionCheckRunnable); } } /** * Called when the icons for packages have been updated in the icon cache. */ Loading src/com/android/launcher3/shortcuts/DeepShortcutManager.java +12 −0 Original line number Diff line number Diff line Loading @@ -224,4 +224,16 @@ public class DeepShortcutManager { return Collections.EMPTY_LIST; } } @TargetApi(25) public boolean hasHostPermission() { if (Utilities.isNycMR1OrAbove()) { try { return mLauncherApps.hasShortcutHostPermission(); } catch (SecurityException|IllegalStateException e) { Log.e(TAG, "Failed to make shortcut manager call", e); } } return false; } } Loading
src/com/android/launcher3/Launcher.java +3 −0 Original line number Diff line number Diff line Loading @@ -1090,6 +1090,9 @@ public class Launcher extends Activity if (!isWorkspaceLoading()) { // Process any items that were added while Launcher was away. InstallShortcutReceiver.disableAndFlushInstallQueue(this); // Refresh shortcuts if the permission changed. mModel.refreshShortcutsIfRequired(); } if (shouldShowDiscoveryBounce()) { Loading
src/com/android/launcher3/LauncherModel.java +36 −5 Original line number Diff line number Diff line Loading @@ -146,6 +146,20 @@ public class LauncherModel extends BroadcastReceiver // Maps all launcher activities to the id's of their shortcuts (if they have any). private final MultiHashMap<ComponentKey, String> mBgDeepShortcutMap = new MultiHashMap<>(); private boolean mHasShortcutHostPermission; // Runnable to check if the shortcuts permission has changed. private final Runnable mShortcutPermissionCheckRunnable = new Runnable() { @Override public void run() { if (mDeepShortcutsLoaded) { boolean hasShortcutHostPermission = mDeepShortcutManager.hasHostPermission(); if (hasShortcutHostPermission != mHasShortcutHostPermission) { mApp.reloadWorkspace(); } } } }; // The lock that must be acquired before referencing any static bg data structures. Unlike // other locks, this one can generally be held long-term because we never expect any of these // static data structures to be referenced outside of the worker thread except on the first Loading Loading @@ -1244,6 +1258,7 @@ public class LauncherModel extends BroadcastReceiver if (resetAllAppsLoaded) mAllAppsLoaded = false; if (resetWorkspaceLoaded) mWorkspaceLoaded = false; // Always reset deep shortcuts loaded. // TODO: why? mDeepShortcutsLoaded = false; } } Loading Loading @@ -1299,6 +1314,7 @@ public class LauncherModel extends BroadcastReceiver // If there is already one running, tell it to stop. stopLoaderLocked(); mLoaderTask = new LoaderTask(mApp.getContext(), synchronousBindPage); // TODO: mDeepShortcutsLoaded does not need to be true for synchronous bind. if (synchronousBindPage != PagedView.INVALID_RESTORE_PAGE && mAllAppsLoaded && mWorkspaceLoaded && mDeepShortcutsLoaded && !mIsLoaderTaskRunning) { mLoaderTask.runBindSynchronousPage(synchronousBindPage); Loading Loading @@ -2793,6 +2809,8 @@ public class LauncherModel extends BroadcastReceiver } if (!mDeepShortcutsLoaded) { mBgDeepShortcutMap.clear(); mHasShortcutHostPermission = mDeepShortcutManager.hasHostPermission(); if (mHasShortcutHostPermission) { for (UserHandleCompat user : mUserManager.getUserProfiles()) { if (mUserManager.isUserUnlocked(user)) { List<ShortcutInfoCompat> shortcuts = mDeepShortcutManager Loading @@ -2800,6 +2818,7 @@ public class LauncherModel extends BroadcastReceiver updateDeepShortcutMap(null, user, shortcuts); } } } synchronized (LoaderTask.this) { if (mStopped) { return; Loading Loading @@ -2862,6 +2881,18 @@ public class LauncherModel extends BroadcastReceiver runOnMainThread(r); } /** * Refreshes the cached shortcuts if the shortcut permission has changed. * Current implementation simply reloads the workspace, but it can be optimized to * use partial updates similar to {@link UserManagerCompat} */ public void refreshShortcutsIfRequired() { if (Utilities.isNycMR1OrAbove()) { sWorker.removeCallbacks(mShortcutPermissionCheckRunnable); sWorker.post(mShortcutPermissionCheckRunnable); } } /** * Called when the icons for packages have been updated in the icon cache. */ Loading
src/com/android/launcher3/shortcuts/DeepShortcutManager.java +12 −0 Original line number Diff line number Diff line Loading @@ -224,4 +224,16 @@ public class DeepShortcutManager { return Collections.EMPTY_LIST; } } @TargetApi(25) public boolean hasHostPermission() { if (Utilities.isNycMR1OrAbove()) { try { return mLauncherApps.hasShortcutHostPermission(); } catch (SecurityException|IllegalStateException e) { Log.e(TAG, "Failed to make shortcut manager call", e); } } return false; } }