From: Hyunyoung Song Date: Mon, 4 May 2015 23:28:20 +0000 (-0700) Subject: WidgetTray performance improvement (less sorting): Part 1 X-Git-Tag: android-x86-7.1-r1~166^2~547^2 X-Git-Url: http://git.osdn.net/view?a=commitdiff_plain;h=8821ca9a6a5bf34308f9b70c2cabf9da17330497;p=android-x86%2Fpackages-apps-Launcher3.git WidgetTray performance improvement (less sorting): Part 1 - No longer return sorted list from the package manager since, the only time the widget list requires to be sorted is when recycler view renders them. - Made getWidgetsAndShortcuts private to guarantee that widgets are being loaded in the worker thread. Change-Id: I2c35973c1226e831514380dd38fc2f88b1b91d02 --- diff --git a/src/com/android/launcher3/Launcher.java b/src/com/android/launcher3/Launcher.java index 2ef5d0ac4..efe27ad6c 100644 --- a/src/com/android/launcher3/Launcher.java +++ b/src/com/android/launcher3/Launcher.java @@ -3584,14 +3584,13 @@ public class Launcher extends Activity * in onResume. * * This needs to be called from incoming places where resources might have been loaded - * while we are paused. That is becaues the Configuration might be wrong - * when we're not running, and if it comes back to what it was when we - * were paused, we are not restarted. + * while the activity is paused. That is because the Configuration (e.g., rotation) might be + * wrong when we're not running, and if the activity comes back to what the configuration was + * when we were paused, activity is not restarted. * * Implementation of the method from LauncherModel.Callbacks. * - * @return true if we are currently paused. The caller might be able to - * skip some work in that case since we will come back again. + * @return {@code true} if we are currently paused. The caller might be able to skip some work */ private boolean waitUntilResume(Runnable run, boolean deletePreviousRunnables) { if (mPaused) { @@ -4135,10 +4134,6 @@ public class Launcher extends Activity if (mAppsView != null) { mAppsView.setApps(apps); } - if (mWidgetsView != null) { - mWidgetsView.addWidgets(LauncherModel.getSortedWidgetsAndShortcuts(this, false), - getPackageManager()); - } if (mLauncherCallbacks != null) { mLauncherCallbacks.bindAllApplications(apps); } @@ -4274,26 +4269,23 @@ public class Launcher extends Activity } } - /** - * A number of packages were updated. - */ @Thunk ArrayList mWidgetsAndShortcuts; private Runnable mBindPackagesUpdatedRunnable = new Runnable() { public void run() { - bindPackagesUpdated(mWidgetsAndShortcuts); - mWidgetsAndShortcuts = null; + bindAllPackages(mWidgetsAndShortcuts); } }; - public void bindPackagesUpdated(final ArrayList widgetsAndShortcuts) { + @Override + public void bindAllPackages(final ArrayList widgetsAndShortcuts) { if (waitUntilResume(mBindPackagesUpdatedRunnable, true)) { mWidgetsAndShortcuts = widgetsAndShortcuts; return; } - if (mWidgetsView != null) { - mWidgetsView.addWidgets(LauncherModel.getSortedWidgetsAndShortcuts(this, false), - getPackageManager()); + if (mWidgetsView != null && widgetsAndShortcuts != null) { + mWidgetsView.addWidgets(widgetsAndShortcuts, getPackageManager()); + mWidgetsAndShortcuts = null; } } diff --git a/src/com/android/launcher3/LauncherModel.java b/src/com/android/launcher3/LauncherModel.java index 97a283006..0624478ec 100644 --- a/src/com/android/launcher3/LauncherModel.java +++ b/src/com/android/launcher3/LauncherModel.java @@ -197,7 +197,7 @@ public class LauncherModel extends BroadcastReceiver public void bindRestoreItemsChange(HashSet updates); public void bindComponentsRemoved(ArrayList packageNames, ArrayList appInfos, UserHandleCompat user, int reason); - public void bindPackagesUpdated(ArrayList widgetsAndShortcuts); + public void bindAllPackages(ArrayList widgetsAndShortcuts); public void bindSearchablesChanged(); public boolean isAllAppsButtonRank(int rank); public void onPageBoundSynchronously(int page); @@ -1594,9 +1594,6 @@ public class LauncherModel extends BroadcastReceiver if (DEBUG_LOADERS) Log.d(TAG, "step 2: loading all apps"); loadAndBindAllApps(); - // Remove entries for packages which changed while the launcher was dead. - LauncherAppState.getInstance().getWidgetCache().removeObsoletePreviews(); - // Restore the default thread priority after we are done loading items synchronized (mLock) { android.os.Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); @@ -2865,6 +2862,7 @@ public class LauncherModel extends BroadcastReceiver final Callbacks callbacks = tryGetCallbacks(oldCallbacks); if (callbacks != null) { callbacks.bindAllApplications(added); + loadAndBindWidgetsAndShortcuts(mContext,callbacks); if (DEBUG_LOADERS) { Log.d(TAG, "bound " + added.size() + " apps in " + (SystemClock.uptimeMillis() - bindTime) + "ms"); @@ -3280,29 +3278,33 @@ public class LauncherModel extends BroadcastReceiver runOnWorkerThread(new Runnable(){ @Override public void run() { - final ArrayList list = - getSortedWidgetsAndShortcuts(context, true /* refresh */); + final ArrayList list = getWidgetsAndShortcuts(context, true /* refresh */); mHandler.post(new Runnable() { @Override public void run() { Callbacks cb = getCallback(); if (callbacks == cb && cb != null) { - callbacks.bindPackagesUpdated(list); + callbacks.bindAllPackages(list); } } }); + // update the Widget entries inside DB on the worker thread. + LauncherAppState.getInstance().getWidgetCache().removeObsoletePreviews(list); } }); } - // Returns a list of ResolveInfos/AppWidgetInfos in sorted order - public static ArrayList getSortedWidgetsAndShortcuts(Context context, boolean refresh) { + /** + * Returns a list of ResolveInfos/AppWidgetInfos. + * + * @see #loadAndBindWidgetsAndShortcuts + */ + private ArrayList getWidgetsAndShortcuts(Context context, boolean refresh) { PackageManager packageManager = context.getPackageManager(); final ArrayList widgetsAndShortcuts = new ArrayList(); widgetsAndShortcuts.addAll(getWidgetProviders(context, refresh)); Intent shortcutsIntent = new Intent(Intent.ACTION_CREATE_SHORTCUT); widgetsAndShortcuts.addAll(packageManager.queryIntentActivities(shortcutsIntent, 0)); - Collections.sort(widgetsAndShortcuts, new WidgetAndShortcutNameComparator(context)); return widgetsAndShortcuts; } diff --git a/src/com/android/launcher3/WidgetPreviewLoader.java b/src/com/android/launcher3/WidgetPreviewLoader.java index 412cbcd6d..93bfeaffd 100644 --- a/src/com/android/launcher3/WidgetPreviewLoader.java +++ b/src/com/android/launcher3/WidgetPreviewLoader.java @@ -24,6 +24,7 @@ import android.graphics.RectF; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import android.os.AsyncTask; +import android.os.Process; import android.util.Log; import android.util.LongSparseArray; @@ -34,6 +35,9 @@ import com.android.launcher3.util.ComponentKey; import com.android.launcher3.util.Thunk; import com.android.launcher3.widget.WidgetCell; +import junit.framework.Assert; + +import java.util.ArrayList; import java.util.Collections; import java.util.HashMap; import java.util.HashSet; @@ -202,11 +206,14 @@ public class WidgetPreviewLoader { * 2. Any preview for an absent package is removed * This ensures that we remove entries for packages which changed while the launcher was dead. */ - public void removeObsoletePreviews() { + public void removeObsoletePreviews(ArrayList list) { + // This method should always be called from the worker thread. + Assert.assertTrue(LauncherModel.sWorkerThread.getThreadId() == Process.myTid()); + LongSparseArray userIdCache = new LongSparseArray<>(); LongSparseArray> validPackages = new LongSparseArray<>(); - for (Object obj : LauncherModel.getSortedWidgetsAndShortcuts(mContext, false)) { + for (Object obj : list) { final UserHandleCompat user; final String pkg; if (obj instanceof ResolveInfo) {