LauncherModel.java revision 2fcbd686d1c2a9a9e520116a541c9caae0c2dc60
131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project/*
231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * Copyright (C) 2008 The Android Open Source Project
331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project *
431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * you may not use this file except in compliance with the License.
631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * You may obtain a copy of the License at
731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project *
831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project *
1031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
1131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
1231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * See the License for the specific language governing permissions and
1431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * limitations under the License.
1531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project */
1631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
1731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectpackage com.android.launcher;
1831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
1931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.ComponentName;
2031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.ContentResolver;
2131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.ContentValues;
2231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.Intent;
2331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.Context;
2431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.pm.ActivityInfo;
2531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.pm.PackageManager;
2631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.pm.ResolveInfo;
2731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.content.res.Resources;
2831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.database.Cursor;
2931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.graphics.Bitmap;
3031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.graphics.BitmapFactory;
31f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Projectimport android.graphics.drawable.Drawable;
3231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.net.Uri;
33f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Projectimport static android.util.Log.*;
3431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport android.os.Process;
3531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
3631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.util.ArrayList;
3731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.util.HashMap;
3831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.util.List;
3931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.util.Comparator;
4031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.lang.ref.WeakReference;
4131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.text.Collator;
4231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectimport java.net.URISyntaxException;
4331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
4431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project/**
4531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * Maintains in-memory state of the Launcher. It is expected that there should be only one
4631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project * LauncherModel object held in a static. Also provide APIs for updating the database state
47bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project * for the Launcher.
4831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project */
4931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Projectpublic class LauncherModel {
50829f56a020a3e2ca851d7e532036b14004bf0234Romain Guy    static final boolean DEBUG_LOADERS = true;
51f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    static final String LOG_TAG = "HomeLoaders";
52f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
5331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static final int UI_NOTIFICATION_RATE = 4;
5431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static final int DEFAULT_APPLICATIONS_NUMBER = 42;
5531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static final long APPLICATION_NOT_RESPONDING_TIMEOUT = 5000;
56bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    private static final int INITIAL_ICON_CACHE_CAPACITY = 50;
5731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
587376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project    private static final Collator sCollator = Collator.getInstance();
5931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
6031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private boolean mApplicationsLoaded;
6131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private boolean mDesktopItemsLoaded;
6231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
6331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private ArrayList<ItemInfo> mDesktopItems;
647376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project    private ArrayList<LauncherAppWidgetInfo> mDesktopAppWidgets;
6531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private HashMap<Long, FolderInfo> mFolders;
6631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
6731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private ArrayList<ApplicationInfo> mApplications;
6831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private ApplicationsAdapter mApplicationsAdapter;
6931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private ApplicationsLoader mApplicationsLoader;
7031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private DesktopItemsLoader mDesktopItemsLoader;
71ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    private Thread mApplicationsLoaderThread;
72ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    private Thread mDesktopLoaderThread;
7331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
74bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    private final HashMap<ComponentName, ApplicationInfo> mAppInfoCache =
75bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project            new HashMap<ComponentName, ApplicationInfo>(INITIAL_ICON_CACHE_CAPACITY);
76bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
77ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    synchronized void abortLoaders() {
7831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
7931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mApplicationsLoader.stop();
8031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mApplicationsLoaded = false;
8131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
82ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
8331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (mDesktopItemsLoader != null && mDesktopItemsLoader.isRunning()) {
8431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mDesktopItemsLoader.stop();
8531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mDesktopItemsLoaded = false;
8631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
8731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
8831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
8931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
90bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     * Drop our cache of components to their lables & icons.  We do
91bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     * this from Launcher when applications are added/removed.  It's a
92bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     * bit overkill, but it's a rare operation anyway.
93bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     */
94bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    synchronized void dropApplicationCache() {
95bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project        mAppInfoCache.clear();
96bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    }
97bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
98bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    /**
9931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Loads the list of installed applications in mApplications.
100ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project     *
101ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project     * @return true if the applications loader must be started
102ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project     *         (see startApplicationsLoader()), false otherwise.
10331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
104ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    synchronized boolean loadApplications(boolean isLaunching, Launcher launcher,
105bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project            boolean localeChanged) {
106f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
107f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (DEBUG_LOADERS) d(LOG_TAG, "load applications");
108f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
10931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (isLaunching && mApplicationsLoaded && !localeChanged) {
11031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mApplicationsAdapter = new ApplicationsAdapter(launcher, mApplications);
111f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (DEBUG_LOADERS) d(LOG_TAG, "  --> applications loaded, return");
112ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            return false;
11331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
11431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
115f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        stopAndWaitForApplicationsLoader();
116ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
117ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        if (localeChanged) {
118ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            dropApplicationCache();
1192fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        }
120ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
12131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (mApplicationsAdapter == null || isLaunching || localeChanged) {
122bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project            mApplications = new ArrayList<ApplicationInfo>(DEFAULT_APPLICATIONS_NUMBER);
123bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project            mApplicationsAdapter = new ApplicationsAdapter(launcher, mApplications);
12431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
12531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
126ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        mApplicationsLoaded = false;
127ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
128ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        if (!isLaunching) {
1292fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            startApplicationsLoader(launcher, false);
130ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            return false;
131ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        }
132ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
133ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        return true;
134ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    }
135ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
136f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private synchronized void stopAndWaitForApplicationsLoader() {
13731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
138f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (DEBUG_LOADERS) d(LOG_TAG, "  --> wait for applications loader");
139ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
14031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mApplicationsLoader.stop();
14131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // Wait for the currently running thread to finish, this can take a little
14231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // time but it should be well below the timeout limit
14331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            try {
144ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                mApplicationsLoaderThread.join(APPLICATION_NOT_RESPONDING_TIMEOUT);
14531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            } catch (InterruptedException e) {
146ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                // EMpty
14731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
14831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
14931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
15031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
1512fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy    private synchronized void startApplicationsLoader(Launcher launcher, boolean isLaunching) {
152f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (DEBUG_LOADERS) d(LOG_TAG, "  --> starting applications loader");
153f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
154f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        stopAndWaitForApplicationsLoader();
155ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
1562fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        mApplicationsLoader = new ApplicationsLoader(launcher, isLaunching);
157ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        mApplicationsLoaderThread = new Thread(mApplicationsLoader, "Applications Loader");
158ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        mApplicationsLoaderThread.start();
15931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
16031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
161f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    synchronized void addPackage(Launcher launcher, String packageName) {
162f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
1632fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            startApplicationsLoader(launcher, false);
164f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return;
165f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
166f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
167f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (packageName != null && packageName.length() > 0) {
168f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final PackageManager packageManager = launcher.getPackageManager();
169f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final List<ResolveInfo> matches = findActivitiesForPackage(packageManager, packageName);
170f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
171f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (matches.size() > 0) {
172f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ApplicationsAdapter adapter = mApplicationsAdapter;
173f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final HashMap<ComponentName, ApplicationInfo> cache = mAppInfoCache;
174f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
175f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                for (ResolveInfo info : matches) {
176f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    adapter.setNotifyOnChange(false);
177583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                    adapter.add(makeAndCacheApplicationInfo(packageManager, cache, info, launcher));
178f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
179f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
180f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.sort(new ApplicationInfoComparator());
181f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.notifyDataSetChanged();
182f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
183f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
184f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
185f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
186f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    synchronized void removePackage(Launcher launcher, String packageName) {
187f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
188f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            dropApplicationCache(); // TODO: this could be optimized
1892fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            startApplicationsLoader(launcher, false);
190f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return;
191f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
192f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
193f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (packageName != null && packageName.length() > 0) {
194f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ApplicationsAdapter adapter = mApplicationsAdapter;
195f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
196f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final List<ApplicationInfo> toRemove = new ArrayList<ApplicationInfo>();
197f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final int count = adapter.getCount();
198f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
199f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            for (int i = 0; i < count; i++) {
200f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ApplicationInfo applicationInfo = adapter.getItem(i);
201f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final Intent intent = applicationInfo.intent;
202f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ComponentName component = intent.getComponent();
203f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                if (packageName.equals(component.getPackageName())) {
204f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    toRemove.add(applicationInfo);
205f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
206f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
207f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
208f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final HashMap<ComponentName, ApplicationInfo> cache = mAppInfoCache;
209f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            for (ApplicationInfo info : toRemove) {
210f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.setNotifyOnChange(false);
211f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.remove(info);
212f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                cache.remove(info.intent.getComponent());
213f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
214f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
215f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (toRemove.size() > 0) {
216f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.sort(new ApplicationInfoComparator());
217f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.notifyDataSetChanged();
218f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
219f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
220f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
221f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
222f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    synchronized void updatePackage(Launcher launcher, String packageName) {
223f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
2242fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            startApplicationsLoader(launcher, false);
225f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return;
226f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
227f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
228f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (packageName != null && packageName.length() > 0) {
229f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final PackageManager packageManager = launcher.getPackageManager();
230f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ApplicationsAdapter adapter = mApplicationsAdapter;
231f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
232f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final List<ResolveInfo> matches = findActivitiesForPackage(packageManager, packageName);
233f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final int count = matches.size();
234f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
235f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            boolean changed = false;
236f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
237f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            for (int i = 0; i < count; i++) {
238f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ResolveInfo info = matches.get(i);
239f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ApplicationInfo applicationInfo = findIntent(adapter,
240f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                        info.activityInfo.applicationInfo.packageName, info.activityInfo.name);
241f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                if (applicationInfo != null) {
242583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                    updateAndCacheApplicationInfo(packageManager, info, applicationInfo, launcher);
243f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    changed = true;
244f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
245f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
246f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
247f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (changed) {
248f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.sort(new ApplicationInfoComparator());
249f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                adapter.notifyDataSetChanged();
250f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
251f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
252f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
253f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
254f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private void updateAndCacheApplicationInfo(PackageManager packageManager, ResolveInfo info,
255583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima            ApplicationInfo applicationInfo, Context context) {
256f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
257583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima        updateApplicationInfoTitleAndIcon(packageManager, info, applicationInfo, context);
258f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
259f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        ComponentName componentName = new ComponentName(
260f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                info.activityInfo.applicationInfo.packageName, info.activityInfo.name);
261f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        mAppInfoCache.put(componentName, applicationInfo);
262f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
263f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
264f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    synchronized void syncPackage(Launcher launcher, String packageName) {
265f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (mApplicationsLoader != null && mApplicationsLoader.isRunning()) {
2662fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            startApplicationsLoader(launcher, false);
267f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return;
268f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
269f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
270f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (packageName != null && packageName.length() > 0) {
271f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final PackageManager packageManager = launcher.getPackageManager();
272f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final List<ResolveInfo> matches = findActivitiesForPackage(packageManager, packageName);
273f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
274f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (matches.size() > 0) {
275f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ApplicationsAdapter adapter = mApplicationsAdapter;
276f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
277f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                // Find disabled activities and remove them from the adapter
278f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                boolean removed = removeDisabledActivities(packageName, matches, adapter);
279f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                // Find enable activities and add them to the adapter
280f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                // Also updates existing activities with new labels/icons
281f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                boolean added = addEnabledAndUpdateActivities(matches, adapter, launcher);
282f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
283f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                if (added || removed) {
284f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    adapter.sort(new ApplicationInfoComparator());
285f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    adapter.notifyDataSetChanged();
286f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
287f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
288f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
289f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
290f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
291f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static List<ResolveInfo> findActivitiesForPackage(PackageManager packageManager,
292f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            String packageName) {
293f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
294f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final Intent mainIntent = new Intent(Intent.ACTION_MAIN, null);
295f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        mainIntent.addCategory(Intent.CATEGORY_LAUNCHER);
296f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
297f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final List<ResolveInfo> apps = packageManager.queryIntentActivities(mainIntent, 0);
298f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final List<ResolveInfo> matches = new ArrayList<ResolveInfo>();
299f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
300f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (apps != null) {
301f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            // Find all activities that match the packageName
302f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            int count = apps.size();
303f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            for (int i = 0; i < count; i++) {
304f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ResolveInfo info = apps.get(i);
305f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                final ActivityInfo activityInfo = info.activityInfo;
306f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                if (packageName.equals(activityInfo.packageName)) {
307f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    matches.add(info);
308f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
309f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
310f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
311f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
312f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return matches;
313f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
314f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
315f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private boolean addEnabledAndUpdateActivities(List<ResolveInfo> matches,
316f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            ApplicationsAdapter adapter, Launcher launcher) {
317f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
318f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final List<ApplicationInfo> toAdd = new ArrayList<ApplicationInfo>();
319f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final int count = matches.size();
320f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
321f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        boolean changed = false;
322f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
323f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (int i = 0; i < count; i++) {
324f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ResolveInfo info = matches.get(i);
325f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ApplicationInfo applicationInfo = findIntent(adapter,
326f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    info.activityInfo.applicationInfo.packageName, info.activityInfo.name);
327f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (applicationInfo == null) {
328f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                toAdd.add(makeAndCacheApplicationInfo(launcher.getPackageManager(),
329583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                        mAppInfoCache, info, launcher));
330f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                changed = true;
331f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            } else {
332583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                updateAndCacheApplicationInfo(
333583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                        launcher.getPackageManager(), info, applicationInfo, launcher);
334f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                changed = true;
335f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
336f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
337f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
338f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (ApplicationInfo info : toAdd) {
339f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            adapter.setNotifyOnChange(false);
340f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            adapter.add(info);
341f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
342f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
343f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return changed;
344f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
345f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
346f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private boolean removeDisabledActivities(String packageName, List<ResolveInfo> matches,
347f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            ApplicationsAdapter adapter) {
348f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
349f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final List<ApplicationInfo> toRemove = new ArrayList<ApplicationInfo>();
350f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final int count = adapter.getCount();
351f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
352f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        boolean changed = false;
353f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
354f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (int i = 0; i < count; i++) {
355f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ApplicationInfo applicationInfo = adapter.getItem(i);
356f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final Intent intent = applicationInfo.intent;
357f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ComponentName component = intent.getComponent();
358f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (packageName.equals(component.getPackageName())) {
359f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                if (!findIntent(matches, component)) {
360f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    toRemove.add(applicationInfo);
361f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    changed = true;
362f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                }
363f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
364f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
365f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
366f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final HashMap<ComponentName, ApplicationInfo> cache = mAppInfoCache;
367f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (ApplicationInfo info : toRemove) {
368f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            adapter.setNotifyOnChange(false);
369f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            adapter.remove(info);
370f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            cache.remove(info.intent.getComponent());
371f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
372f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
373f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return changed;
374f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
375f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
376f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static ApplicationInfo findIntent(ApplicationsAdapter adapter, String packageName,
377f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            String name) {
378f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
379f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final int count = adapter.getCount();
380f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (int i = 0; i < count; i++) {
381f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ApplicationInfo applicationInfo = adapter.getItem(i);
382f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final Intent intent = applicationInfo.intent;
383f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ComponentName component = intent.getComponent();
384f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (packageName.equals(component.getPackageName()) &&
385f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    name.equals(component.getClassName())) {
386f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                return applicationInfo;
387f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
388f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
389f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
390f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return null;
391f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
392f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
393f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static boolean findIntent(List<ResolveInfo> apps, ComponentName component) {
394f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final String className = component.getClassName();
395f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        for (ResolveInfo info : apps) {
396f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final ActivityInfo activityInfo = info.activityInfo;
397f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (activityInfo.name.equals(className)) {
398f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                return true;
399f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            }
400f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
401f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return false;
402f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
403f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
404f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    Drawable getApplicationInfoIcon(PackageManager manager, ApplicationInfo info) {
405f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        final ResolveInfo resolveInfo = manager.resolveActivity(info.intent, 0);
406f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (resolveInfo == null) {
407f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return null;
408f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
409f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
410f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        ComponentName componentName = new ComponentName(
411f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                resolveInfo.activityInfo.applicationInfo.packageName,
412f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                resolveInfo.activityInfo.name);
413f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        ApplicationInfo application = mAppInfoCache.get(componentName);
414f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
415f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (application == null) {
416f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            return resolveInfo.activityInfo.loadIcon(manager);
417f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
418f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
419f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return application.icon;
420f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
421f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
422f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static ApplicationInfo makeAndCacheApplicationInfo(PackageManager manager,
423583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima            HashMap<ComponentName, ApplicationInfo> appInfoCache, ResolveInfo info,
424583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima            Context context) {
425f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
426f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        ComponentName componentName = new ComponentName(
427f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                info.activityInfo.applicationInfo.packageName,
428f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                info.activityInfo.name);
429f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        ApplicationInfo application = appInfoCache.get(componentName);
430f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
431f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (application == null) {
432f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            application = new ApplicationInfo();
433f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            application.container = ItemInfo.NO_ID;
434f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
435583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima            updateApplicationInfoTitleAndIcon(manager, info, application, context);
436f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
437f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            application.setActivity(componentName,
438f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
439f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
440f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            appInfoCache.put(componentName, application);
441f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
442f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
443f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        return application;
444f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
445f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
446f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static void updateApplicationInfoTitleAndIcon(PackageManager manager, ResolveInfo info,
447583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima            ApplicationInfo application, Context context) {
448f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
449f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        application.title = info.loadLabel(manager);
450f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (application.title == null) {
451f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            application.title = info.activityInfo.name;
452f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        }
453f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
454583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima        application.icon =
455583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                Utilities.createIconThumbnail(info.activityInfo.loadIcon(manager), context);
456f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        application.filtered = false;
457f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
458f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project
45931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private class ApplicationsLoader implements Runnable {
46031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private final WeakReference<Launcher> mLauncher;
46131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
46231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private volatile boolean mStopped;
46331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private volatile boolean mRunning;
4642fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        private final boolean mIsLaunching;
46531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
4662fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        ApplicationsLoader(Launcher launcher, boolean isLaunching) {
4672fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            mIsLaunching = isLaunching;
46831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mLauncher = new WeakReference<Launcher>(launcher);
46931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
47031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
47131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        void stop() {
47231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mStopped = true;
47331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
47431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
47531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        boolean isRunning() {
47631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            return mRunning;
47731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
47831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
47931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        public void run() {
48031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mRunning = true;
48131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
4822fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            // Elevate priority when Home launches for the first time to avoid
4832fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            // starving at boot time. Staring at a blank home is not cool.
4842fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            android.os.Process.setThreadPriority(mIsLaunching ? Process.THREAD_PRIORITY_DEFAULT :
4852fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy                    Process.THREAD_PRIORITY_BACKGROUND);
48631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
487f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            final Intent mainIntent = new Intent(Intent.ACTION_MAIN, null);
48831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mainIntent.addCategory(Intent.CATEGORY_LAUNCHER);
48931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
49031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final Launcher launcher = mLauncher.get();
49131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final PackageManager manager = launcher.getPackageManager();
49231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final List<ResolveInfo> apps = manager.queryIntentActivities(mainIntent, 0);
49331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
49431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (apps != null && !mStopped) {
49531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int count = apps.size();
496f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                // Can be set to null on the UI thread by the unbind() method
497f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                // Do not access without checking for null first
49831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final ApplicationsAdapter applicationList = mApplicationsAdapter;
49931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
500ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                ChangeNotifier action = new ChangeNotifier(applicationList, true);
5017376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                final HashMap<ComponentName, ApplicationInfo> appInfoCache = mAppInfoCache;
50231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
50331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                for (int i = 0; i < count && !mStopped; i++) {
50431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    ResolveInfo info = apps.get(i);
505f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    ApplicationInfo application =
506583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                        makeAndCacheApplicationInfo(manager, appInfoCache, info, launcher);
50731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
508f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                    if (action.add(application) && !mStopped) {
509ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                        launcher.runOnUiThread(action);
510ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                        action = new ChangeNotifier(applicationList, false);
511ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                    }
51231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
513ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
514ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                launcher.runOnUiThread(action);
51531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
51631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
51731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (!mStopped) {
51831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                mApplicationsLoaded = true;
51931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
52031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mRunning = false;
52131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
52231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
52331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
524f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    private static class ChangeNotifier implements Runnable {
52531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private final ApplicationsAdapter mApplicationList;
526bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project        private final ArrayList<ApplicationInfo> mBuffer;
5277376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project
5287376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        private boolean mFirst = true;
52931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
530ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        ChangeNotifier(ApplicationsAdapter applicationList, boolean first) {
53131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mApplicationList = applicationList;
532ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            mFirst = first;
53331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mBuffer = new ArrayList<ApplicationInfo>(UI_NOTIFICATION_RATE);
53431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
53531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
53631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        public void run() {
53731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final ApplicationsAdapter applicationList = mApplicationList;
538f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            // Can be set to null on the UI thread by the unbind() method
539f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (applicationList == null) return;
54031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
5417376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            if (mFirst) {
54231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                applicationList.setNotifyOnChange(false);
5437376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                applicationList.clear();
5447376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                mFirst = false;
54531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
54631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
547ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            final ArrayList<ApplicationInfo> buffer = mBuffer;
548ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            final int count = buffer.size();
5497376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project
550ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            for (int i = 0; i < count; i++) {
551ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                applicationList.setNotifyOnChange(false);
552ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                applicationList.add(buffer.get(i));
5537376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            }
5547376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project
555ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            buffer.clear();
556ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project
557f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            applicationList.sort(new ApplicationInfoComparator());
55831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            applicationList.notifyDataSetChanged();
55931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
56031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
561ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        boolean add(ApplicationInfo application) {
562ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            final ArrayList<ApplicationInfo> buffer = mBuffer;
563ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            buffer.add(application);
564ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project            return buffer.size() >= UI_NOTIFICATION_RATE;
56531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
566f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project    }
56731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
56873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    static class ApplicationInfoComparator implements Comparator<ApplicationInfo> {
5697376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        public final int compare(ApplicationInfo a, ApplicationInfo b) {
5707376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            return sCollator.compare(a.title.toString(), b.title.toString());
57131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
57231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
57331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
57431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    boolean isDesktopLoaded() {
5757376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        return mDesktopItems != null && mDesktopAppWidgets != null && mDesktopItemsLoaded;
57631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
577bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
57831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
57931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Loads all of the items on the desktop, in folders, or in the dock.
58031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * These can be apps, shortcuts or widgets
58131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
58231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    void loadUserItems(boolean isLaunching, Launcher launcher, boolean localeChanged,
58331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            boolean loadApplications) {
584f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (DEBUG_LOADERS) d(LOG_TAG, "loading user items");
58531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
58631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (isLaunching && isDesktopLoaded()) {
587f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project            if (DEBUG_LOADERS) d(LOG_TAG, "  --> items loaded, return");
5882fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            if (loadApplications) startApplicationsLoader(launcher, true);
58931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // We have already loaded our data from the DB
59031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            launcher.onDesktopItemsLoaded();
59131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            return;
59231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
59331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
59431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (mDesktopItemsLoader != null && mDesktopItemsLoader.isRunning()) {
595fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            if (DEBUG_LOADERS) d(LOG_TAG, "  --> stopping workspace loader");
59631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mDesktopItemsLoader.stop();
59731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // Wait for the currently running thread to finish, this can take a little
59831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // time but it should be well below the timeout limit
59931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            try {
600ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project                mDesktopLoaderThread.join(APPLICATION_NOT_RESPONDING_TIMEOUT);
60131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            } catch (InterruptedException e) {
60231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                // Empty
60331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
604fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy
605fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            // If the thread we are interrupting was tasked to load the list of
606fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            // applications make sure we keep that information in the new loader
607fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            // spawned below
608fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            // note: we don't apply this to localeChanged because the thread can
609fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            // only be stopped *after* the localeChanged handling has occured
610fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy            loadApplications = mDesktopItemsLoader.mLoadApplications;
61131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
61231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
613f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        if (DEBUG_LOADERS) d(LOG_TAG, "  --> starting workspace loader");
61431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mDesktopItemsLoaded = false;
6152fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        mDesktopItemsLoader = new DesktopItemsLoader(launcher, localeChanged, loadApplications,
6162fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy                isLaunching);
617ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        mDesktopLoaderThread = new Thread(mDesktopItemsLoader, "Desktop Items Loader");
618ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project        mDesktopLoaderThread.start();
61931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
62031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
62131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static void updateShortcutLabels(ContentResolver resolver, PackageManager manager) {
62231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final Cursor c = resolver.query(LauncherSettings.Favorites.CONTENT_URI,
62373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                new String[] { LauncherSettings.Favorites._ID, LauncherSettings.Favorites.TITLE,
62431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        LauncherSettings.Favorites.INTENT, LauncherSettings.Favorites.ITEM_TYPE },
62531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                null, null, null);
62631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
62773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final int idIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites._ID);
62831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final int intentIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.INTENT);
62931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final int itemTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ITEM_TYPE);
63031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final int titleIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.TITLE);
63131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
63231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // boolean changed = false;
63331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
63431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        try {
63531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            while (c.moveToNext()) {
63631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                try {
63731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    if (c.getInt(itemTypeIndex) !=
63831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            LauncherSettings.Favorites.ITEM_TYPE_APPLICATION) {
63931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        continue;
64031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    }
64131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
64231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    final String intentUri = c.getString(intentIndex);
64331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    if (intentUri != null) {
64431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        final Intent shortcut = Intent.getIntent(intentUri);
64531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        if (Intent.ACTION_MAIN.equals(shortcut.getAction())) {
64631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            final ComponentName name = shortcut.getComponent();
64731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (name != null) {
64831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                final ActivityInfo activityInfo = manager.getActivityInfo(name, 0);
64931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                final String title = c.getString(titleIndex);
65031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                String label = getLabel(manager, activityInfo);
65131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
65231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                if (title == null || !title.equals(label)) {
65331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    final ContentValues values = new ContentValues();
65431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    values.put(LauncherSettings.Favorites.TITLE, label);
65531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
656fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy                                    resolver.update(
657fedc4fcebc28feb5553bbfb4f0856676cb8f320dRomain Guy                                            LauncherSettings.Favorites.CONTENT_URI_NO_NOTIFICATION,
65831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                            values, "_id=?",
65931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                            new String[] { String.valueOf(c.getLong(idIndex)) });
66031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
66131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    // changed = true;
66231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                }
66331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
66431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        }
66531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    }
66631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                } catch (URISyntaxException e) {
66731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    // Ignore
66831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                } catch (PackageManager.NameNotFoundException e) {
66931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    // Ignore
67031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
67131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
67231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        } finally {
67331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            c.close();
67431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
67531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
67631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // if (changed) resolver.notifyChange(Settings.Favorites.CONTENT_URI, null);
67731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
67831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
67931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static String getLabel(PackageManager manager, ActivityInfo activityInfo) {
68031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        String label = activityInfo.loadLabel(manager).toString();
68131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (label == null) {
68231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            label = manager.getApplicationLabel(activityInfo.applicationInfo).toString();
68331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (label == null) {
68431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                label = activityInfo.name;
68531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
68631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
68731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return label;
68831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
68931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
69031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private class DesktopItemsLoader implements Runnable {
69131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private volatile boolean mStopped;
69231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private volatile boolean mRunning;
69331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
69431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private final WeakReference<Launcher> mLauncher;
69531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private final boolean mLocaleChanged;
69631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        private final boolean mLoadApplications;
6972fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        private final boolean mIsLaunching;
69831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
6992fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy        DesktopItemsLoader(Launcher launcher, boolean localeChanged, boolean loadApplications,
7002fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy                boolean isLaunching) {
70131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mLoadApplications = loadApplications;
7022fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            mIsLaunching = isLaunching;
70331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mLauncher = new WeakReference<Launcher>(launcher);
70431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mLocaleChanged = localeChanged;
70531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
70631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
70731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        void stop() {
70831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mStopped = true;
70931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
71031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
71131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        boolean isRunning() {
71231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            return mRunning;
71331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
71431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
71531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        public void run() {
71631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mRunning = true;
71731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
7182fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy            android.os.Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT);
7192fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
72031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final Launcher launcher = mLauncher.get();
72131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final ContentResolver contentResolver = launcher.getContentResolver();
72231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final PackageManager manager = launcher.getPackageManager();
72331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
72431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (mLocaleChanged) {
72531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                updateShortcutLabels(contentResolver, manager);
72631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
72731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
72831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mDesktopItems = new ArrayList<ItemInfo>();
7297376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            mDesktopAppWidgets = new ArrayList<LauncherAppWidgetInfo>();
73031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mFolders = new HashMap<Long, FolderInfo>();
73131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
73231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final ArrayList<ItemInfo> desktopItems = mDesktopItems;
7337376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            final ArrayList<LauncherAppWidgetInfo> desktopAppWidgets = mDesktopAppWidgets;
73431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
73531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final Cursor c = contentResolver.query(
73631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    LauncherSettings.Favorites.CONTENT_URI, null, null, null, null);
73731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
73831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            try {
73973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                final int idIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites._ID);
74031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int intentIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.INTENT);
74131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int titleIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.TITLE);
74231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int iconTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ICON_TYPE);
74331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int iconIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ICON);
74431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int iconPackageIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ICON_PACKAGE);
74531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int iconResourceIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ICON_RESOURCE);
74631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int containerIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CONTAINER);
74731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int itemTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ITEM_TYPE);
7487376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                final int appWidgetIdIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.APPWIDGET_ID);
74931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int screenIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.SCREEN);
75031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int cellXIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CELLX);
75131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int cellYIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CELLY);
75231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int spanXIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.SPANX);
75331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int spanYIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.SPANY);
75431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int uriIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.URI);
75531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int displayModeIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.DISPLAY_MODE);
75631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
75731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                ApplicationInfo info;
75831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                String intentDescription;
75931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                Widget widgetInfo;
7607376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                LauncherAppWidgetInfo appWidgetInfo;
76131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                int container;
76231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                long id;
76331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                Intent intent;
76431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
76531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final HashMap<Long, FolderInfo> folders = mFolders;
76631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
76731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                while (!mStopped && c.moveToNext()) {
76831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    try {
76931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        int itemType = c.getInt(itemTypeIndex);
77031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
77131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        switch (itemType) {
77231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION:
77331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT:
77431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            intentDescription = c.getString(intentIndex);
77531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            try {
77631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                intent = Intent.getIntent(intentDescription);
77731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            } catch (java.net.URISyntaxException e) {
77831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                continue;
77931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
78031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
78131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (itemType == LauncherSettings.Favorites.ITEM_TYPE_APPLICATION) {
782583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                                info = getApplicationInfo(manager, intent, launcher);
78331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            } else {
78431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info = getApplicationInfoShortcut(c, launcher, iconTypeIndex,
78531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                        iconPackageIndex, iconResourceIndex, iconIndex);
78631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
78731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
78831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (info == null) {
78931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info = new ApplicationInfo();
79031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.icon = manager.getDefaultActivityIcon();
79131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
79231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
79331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (info != null) {
79431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.title = c.getString(titleIndex);
79531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.intent = intent;
79631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
79731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.id = c.getLong(idIndex);
79831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                container = c.getInt(containerIndex);
79931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.container = container;
80031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.screen = c.getInt(screenIndex);
80131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.cellX = c.getInt(cellXIndex);
80231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                info.cellY = c.getInt(cellYIndex);
80331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
80431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                switch (container) {
80531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                case LauncherSettings.Favorites.CONTAINER_DESKTOP:
80631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    desktopItems.add(info);
80731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    break;
80831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                default:
80931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    // Item is in a user folder
81031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    UserFolderInfo folderInfo =
81131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                            findOrMakeUserFolder(folders, container);
81231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    folderInfo.add(info);
81331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    break;
81431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                }
81531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
81631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            break;
81731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER:
81831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
81931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            id = c.getLong(idIndex);
82031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            UserFolderInfo folderInfo = findOrMakeUserFolder(folders, id);
82131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
82231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.title = c.getString(titleIndex);
82331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
82431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.id = id;
82531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            container = c.getInt(containerIndex);
82631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.container = container;
82731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.screen = c.getInt(screenIndex);
82831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.cellX = c.getInt(cellXIndex);
82931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            folderInfo.cellY = c.getInt(cellYIndex);
83031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
83131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            switch (container) {
83231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                case LauncherSettings.Favorites.CONTAINER_DESKTOP:
83331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    desktopItems.add(folderInfo);
83431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    break;
83531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
83631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            break;
83731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER:
83831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
83931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            id = c.getLong(idIndex);
84031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            LiveFolderInfo liveFolderInfo = findOrMakeLiveFolder(folders, id);
84131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
84231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            intentDescription = c.getString(intentIndex);
84331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            intent = null;
84431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (intentDescription != null) {
84531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                try {
84631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    intent = Intent.getIntent(intentDescription);
84731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                } catch (java.net.URISyntaxException e) {
84831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    // Ignore, a live folder might not have a base intent
84931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                }
85031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
85131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
85231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.title = c.getString(titleIndex);
85331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.id = id;
85431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            container = c.getInt(containerIndex);
85531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.container = container;
85631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.screen = c.getInt(screenIndex);
85731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.cellX = c.getInt(cellXIndex);
85831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.cellY = c.getInt(cellYIndex);
85931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.uri = Uri.parse(c.getString(uriIndex));
86031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.baseIntent = intent;
86131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            liveFolderInfo.displayMode = c.getInt(displayModeIndex);
86231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
86331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            loadLiveFolderIcon(launcher, c, iconTypeIndex, iconPackageIndex,
86431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    iconResourceIndex, liveFolderInfo);
86531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
86631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            switch (container) {
86731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                case LauncherSettings.Favorites.CONTAINER_DESKTOP:
86831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    desktopItems.add(liveFolderInfo);
86931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                    break;
87031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
87131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            break;
87231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_WIDGET_SEARCH:
87331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo = Widget.makeSearch();
87431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
87531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            container = c.getInt(containerIndex);
87631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (container != LauncherSettings.Favorites.CONTAINER_DESKTOP) {
877f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                                e(Launcher.LOG_TAG, "Widget found where container "
87831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                        + "!= CONTAINER_DESKTOP  ignoring!");
87931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                continue;
88031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
881bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
88231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo.id = c.getLong(idIndex);
88331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo.screen = c.getInt(screenIndex);
88431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo.container = container;
88531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo.cellX = c.getInt(cellXIndex);
88631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            widgetInfo.cellY = c.getInt(cellYIndex);
88731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
88831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            desktopItems.add(widgetInfo);
88931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            break;
8907376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                        case LauncherSettings.Favorites.ITEM_TYPE_APPWIDGET:
8917376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            // Read all Launcher-specific widget details
8927376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            int appWidgetId = c.getInt(appWidgetIdIndex);
8937376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo = new LauncherAppWidgetInfo(appWidgetId);
8947376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.id = c.getLong(idIndex);
8957376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.screen = c.getInt(screenIndex);
8967376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.cellX = c.getInt(cellXIndex);
8977376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.cellY = c.getInt(cellYIndex);
8987376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.spanX = c.getInt(spanXIndex);
8997376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.spanY = c.getInt(spanYIndex);
90031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
90131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            container = c.getInt(containerIndex);
90231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            if (container != LauncherSettings.Favorites.CONTAINER_DESKTOP) {
903f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                                e(Launcher.LOG_TAG, "Widget found where container "
90431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                        + "!= CONTAINER_DESKTOP -- ignoring!");
90531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                                continue;
90631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            }
9077376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            appWidgetInfo.container = c.getInt(containerIndex);
908bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
9097376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                            desktopAppWidgets.add(appWidgetInfo);
91031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            break;
91131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        }
91231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    } catch (Exception e) {
913f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project                        w(Launcher.LOG_TAG, "Desktop items loading interrupted:", e);
91431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    }
91531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
91631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            } finally {
91731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                c.close();
91831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
91931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
92031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (!mStopped) {
92131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                launcher.runOnUiThread(new Runnable() {
92231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    public void run() {
92331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        launcher.onDesktopItemsLoaded();
92431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    }
92531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                });
9262fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy                if (mLoadApplications) startApplicationsLoader(launcher, mIsLaunching);
92731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
92831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
92931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (!mStopped) {
93031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                mDesktopItemsLoaded = true;
93131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
93231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            mRunning = false;
93331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
93431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
93531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
93631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private static void loadLiveFolderIcon(Launcher launcher, Cursor c, int iconTypeIndex,
93731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            int iconPackageIndex, int iconResourceIndex, LiveFolderInfo liveFolderInfo) {
93831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
93931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        int iconType = c.getInt(iconTypeIndex);
94031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        switch (iconType) {
94131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            case LauncherSettings.Favorites.ICON_TYPE_RESOURCE:
94231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                String packageName = c.getString(iconPackageIndex);
94331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                String resourceName = c.getString(iconResourceIndex);
94431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                PackageManager packageManager = launcher.getPackageManager();
94531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                try {
94631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    Resources resources = packageManager.getResourcesForApplication(packageName);
94731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    final int id = resources.getIdentifier(resourceName, null, null);
94831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    liveFolderInfo.icon = resources.getDrawable(id);
94931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                } catch (Exception e) {
95031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    liveFolderInfo.icon =
95131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                            launcher.getResources().getDrawable(R.drawable.ic_launcher_folder);
95231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
95331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                liveFolderInfo.iconResource = new Intent.ShortcutIconResource();
95431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                liveFolderInfo.iconResource.packageName = packageName;
95531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                liveFolderInfo.iconResource.resourceName = resourceName;
95631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                break;
95731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            default:
95831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                liveFolderInfo.icon =
959bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project                        launcher.getResources().getDrawable(R.drawable.ic_launcher_folder);
96031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
96131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
96231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
96331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
96431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Finds the user folder defined by the specified id.
96531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     *
96631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param id The id of the folder to look for.
967bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     *
96831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @return A UserFolderInfo if the folder exists or null otherwise.
96931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
97031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    FolderInfo findFolderById(long id) {
97131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return mFolders.get(id);
97231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
97331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
97431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    void addFolder(FolderInfo info) {
97531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mFolders.put(info.id, info);
97631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
97731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
97831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
97931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Return an existing UserFolderInfo object if we have encountered this ID previously, or make a
98031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * new one.
98131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
98231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private UserFolderInfo findOrMakeUserFolder(HashMap<Long, FolderInfo> folders, long id) {
98331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // See if a placeholder was created for us already
98431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        FolderInfo folderInfo = folders.get(id);
98531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (folderInfo == null || !(folderInfo instanceof UserFolderInfo)) {
98631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // No placeholder -- create a new instance
98731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            folderInfo = new UserFolderInfo();
98831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            folders.put(id, folderInfo);
98931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
99031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return (UserFolderInfo) folderInfo;
99131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
99231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
99331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
99431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Return an existing UserFolderInfo object if we have encountered this ID previously, or make a
99531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * new one.
99631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
99731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private LiveFolderInfo findOrMakeLiveFolder(HashMap<Long, FolderInfo> folders, long id) {
99831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // See if a placeholder was created for us already
99931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        FolderInfo folderInfo = folders.get(id);
100031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (folderInfo == null || !(folderInfo instanceof LiveFolderInfo)) {
100131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // No placeholder -- create a new instance
100231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            folderInfo = new LiveFolderInfo();
100331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            folders.put(id, folderInfo);
100431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
100531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return (LiveFolderInfo) folderInfo;
100631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
100731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
100831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
100931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove the callback for the cached drawables or we leak the previous
101031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Home screen on orientation change.
101131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
101231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    void unbind() {
1013f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        // Interrupt the applications loader before setting the adapter to null
1014f96811cdf564469a7a654a0c876288c9fd14f35eThe Android Open Source Project        stopAndWaitForApplicationsLoader();
101531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mApplicationsAdapter = null;
101631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        unbindAppDrawables(mApplications);
101731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        unbindDrawables(mDesktopItems);
10187376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        unbindAppWidgetHostViews(mDesktopAppWidgets);
1019bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project        unbindCachedIconDrawables();
102031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
1021bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
102231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
102331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove the callback for the cached drawables or we leak the previous
102431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Home screen on orientation change.
102531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
102631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private void unbindDrawables(ArrayList<ItemInfo> desktopItems) {
102731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (desktopItems != null) {
102831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final int count = desktopItems.size();
102931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            for (int i = 0; i < count; i++) {
103031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                ItemInfo item = desktopItems.get(i);
103131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                switch (item.itemType) {
103231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION:
103331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT:
103431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    ((ApplicationInfo)item).icon.setCallback(null);
103531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    break;
103631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
103731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
103831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
103931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
1040bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
104131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
104231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove the callback for the cached drawables or we leak the previous
104331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Home screen on orientation change.
104431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
104531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    private void unbindAppDrawables(ArrayList<ApplicationInfo> applications) {
104631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (applications != null) {
104731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            final int count = applications.size();
104831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            for (int i = 0; i < count; i++) {
104931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                applications.get(i).icon.setCallback(null);
105031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
105131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
105231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
105331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
105431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
10557376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project     * Remove any {@link LauncherAppWidgetHostView} references in our widgets.
105631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
10577376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project    private void unbindAppWidgetHostViews(ArrayList<LauncherAppWidgetInfo> appWidgets) {
10587376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        if (appWidgets != null) {
10597376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project            final int count = appWidgets.size();
106031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            for (int i = 0; i < count; i++) {
10617376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project                LauncherAppWidgetInfo launcherInfo = appWidgets.get(i);
106231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                launcherInfo.hostView = null;
106331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
106431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
106531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
106631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
106731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
1068bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     * Remove the callback for the cached drawables or we leak the previous
1069bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     * Home screen on orientation change.
1070bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project     */
1071bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    private void unbindCachedIconDrawables() {
1072bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project        for (ApplicationInfo appInfo : mAppInfoCache.values()) {
1073bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project            appInfo.icon.setCallback(null);
1074bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project        }
1075bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    }
1076bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project
1077bc219c3c127cb74cf4fe578f05022b745da921b8The Android Open Source Project    /**
107831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @return The current list of applications
107931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1080ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    ApplicationsAdapter getApplicationsAdapter() {
108131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return mApplicationsAdapter;
108231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
108331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
108431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
108531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @return The current list of desktop items
108631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1087ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    ArrayList<ItemInfo> getDesktopItems() {
108831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return mDesktopItems;
108931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
10902fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
109131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
109231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @return The current list of desktop items
109331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1094ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    ArrayList<LauncherAppWidgetInfo> getDesktopAppWidgets() {
10957376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        return mDesktopAppWidgets;
109631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
109731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
109831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
109931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Add an item to the desktop
110031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param info
110131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1102ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    void addDesktopItem(ItemInfo info) {
110331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // TODO: write to DB; also check that folder has been added to folders list
110431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mDesktopItems.add(info);
110531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
11062fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
110731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
110831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove an item from the desktop
110931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param info
111031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1111ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    void removeDesktopItem(ItemInfo info) {
111231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        // TODO: write to DB; figure out if we should remove folder from folders list
111331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mDesktopItems.remove(info);
111431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
111531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
111631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
11177376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project     * Add a widget to the desktop
111831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1119ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    void addDesktopAppWidget(LauncherAppWidgetInfo info) {
11207376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        mDesktopAppWidgets.add(info);
112131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
11222fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
112331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
11247376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project     * Remove a widget from the desktop
112531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1126ca9475f0403d9c0e843d5c189575068a386b2eb6The Android Open Source Project    void removeDesktopAppWidget(LauncherAppWidgetInfo info) {
11277376faefbbcbe30cc4e3f706ab95c254a4707d98The Android Open Source Project        mDesktopAppWidgets.remove(info);
112831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
112931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
113031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
113131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Make an ApplicationInfo object for an application
113231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
1133583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima    private static ApplicationInfo getApplicationInfo(PackageManager manager, Intent intent,
1134583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima                                                      Context context) {
113531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ResolveInfo resolveInfo = manager.resolveActivity(intent, 0);
113631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
113731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (resolveInfo == null) {
113831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            return null;
113931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
11402fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
114131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ApplicationInfo info = new ApplicationInfo();
114231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ActivityInfo activityInfo = resolveInfo.activityInfo;
1143583ed3ba08644912ec0f3ec8ceb939f9eb0b8e86Mitsuru Oshima        info.icon = Utilities.createIconThumbnail(activityInfo.loadIcon(manager), context);
114431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (info.title == null || info.title.length() == 0) {
114531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            info.title = activityInfo.loadLabel(manager);
114631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
114731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (info.title == null) {
114831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            info.title = "";
114931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
115031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        info.itemType = LauncherSettings.Favorites.ITEM_TYPE_APPLICATION;
115131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return info;
115231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
11532fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
115431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
115531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Make an ApplicationInfo object for a sortcut
115631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
115773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    private ApplicationInfo getApplicationInfoShortcut(Cursor c, Context context,
115831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            int iconTypeIndex, int iconPackageIndex, int iconResourceIndex, int iconIndex) {
115931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
116031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ApplicationInfo info = new ApplicationInfo();
116131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        info.itemType = LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT;
116231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
116331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        int iconType = c.getInt(iconTypeIndex);
116431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        switch (iconType) {
116531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            case LauncherSettings.Favorites.ICON_TYPE_RESOURCE:
116631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                String packageName = c.getString(iconPackageIndex);
116731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                String resourceName = c.getString(iconResourceIndex);
116873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                PackageManager packageManager = context.getPackageManager();
116931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                try {
117031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    Resources resources = packageManager.getResourcesForApplication(packageName);
117131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    final int id = resources.getIdentifier(resourceName, null, null);
117273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                    info.icon = Utilities.createIconThumbnail(resources.getDrawable(id), context);
117331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                } catch (Exception e) {
117431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    info.icon = packageManager.getDefaultActivityIcon();
117531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
117631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.iconResource = new Intent.ShortcutIconResource();
117731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.iconResource.packageName = packageName;
117831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.iconResource.resourceName = resourceName;
117931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.customIcon = false;
118031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                break;
118131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            case LauncherSettings.Favorites.ICON_TYPE_BITMAP:
118231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                byte[] data = c.getBlob(iconIndex);
1183c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                try {
1184c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                    Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
1185c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                    info.icon = new FastBitmapDrawable(
118673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            Utilities.createBitmapThumbnail(bitmap, context));
1187c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                } catch (Exception e) {
118873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                    packageManager = context.getPackageManager();
1189c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                    info.icon = packageManager.getDefaultActivityIcon();
1190c2ad7a6e1571f933f4bc8ceaee5c745a96aaaf68Romain Guy                }
119131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.filtered = true;
119231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.customIcon = true;
119331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                break;
119431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            default:
119573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                info.icon = context.getPackageManager().getDefaultActivityIcon();
119631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                info.customIcon = false;
119731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                break;
119831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
119931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return info;
120031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
120131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
120231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
120331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove an item from the in-memory represention of a user folder. Does not change the DB.
120431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
120531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    void removeUserFolderItem(UserFolderInfo folder, ItemInfo info) {
120631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        //noinspection SuspiciousMethodCalls
120731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        folder.contents.remove(info);
120831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
12092fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
121031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
121131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Removes a UserFolder from the in-memory list of folders. Does not change the DB.
121231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param userFolderInfo
121331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
121431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    void removeUserFolder(UserFolderInfo userFolderInfo) {
121531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        mFolders.remove(userFolderInfo.id);
121631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
12172fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
121831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
121931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Adds an item to the DB if it was not created previously, or move it to a new
122031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * <container, screen, cellX, cellY>
122131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
122231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void addOrMoveItemInDatabase(Context context, ItemInfo item, long container,
122331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            int screen, int cellX, int cellY) {
122431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (item.container == ItemInfo.NO_ID) {
122531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // From all apps
122631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            addItemToDatabase(context, item, container, screen, cellX, cellY, false);
122731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        } else {
122831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            // From somewhere else
122931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            moveItemInDatabase(context, item, container, screen, cellX, cellY);
123031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
123131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
12322fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
123331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
123431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Move an item in the DB to a new <container, screen, cellX, cellY>
123531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
123631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void moveItemInDatabase(Context context, ItemInfo item, long container, int screen,
123731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            int cellX, int cellY) {
123831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.container = container;
123931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.screen = screen;
124031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.cellX = cellX;
124131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.cellY = cellY;
12422fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
124331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentValues values = new ContentValues();
124431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
124531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
124631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        values.put(LauncherSettings.Favorites.CONTAINER, item.container);
124731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        values.put(LauncherSettings.Favorites.CELLX, item.cellX);
124831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        values.put(LauncherSettings.Favorites.CELLY, item.cellY);
124931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        values.put(LauncherSettings.Favorites.SCREEN, item.screen);
125031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
125131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        cr.update(LauncherSettings.Favorites.getContentUri(item.id, false), values, null, null);
125231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
125331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
125431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
125531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Returns true if the shortcuts already exists in the database.
125631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * we identify a shortcut by its title and intent.
125731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
125831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static boolean shortcutExists(Context context, String title, Intent intent) {
125931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
126031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        Cursor c = cr.query(LauncherSettings.Favorites.CONTENT_URI,
126131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            new String[] { "title", "intent" }, "title=? and intent=?",
126231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            new String[] { title, intent.toURI() }, null);
126331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        boolean result = false;
126431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        try {
126531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            result = c.moveToFirst();
126631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        } finally {
126731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            c.close();
126831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
126931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return result;
127031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
127131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
127231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    FolderInfo getFolderById(Context context, long id) {
127331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
127431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        Cursor c = cr.query(LauncherSettings.Favorites.CONTENT_URI, null,
1275591d6d77ccc242fcd4678141102531f093cd2a4fJeffrey Sharkey                "_id=? and (itemType=? or itemType=?)",
127631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                new String[] { String.valueOf(id),
127731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        String.valueOf(LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER),
127831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        String.valueOf(LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER) }, null);
127931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
128031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        try {
128131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            if (c.moveToFirst()) {
128231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int itemTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.ITEM_TYPE);
128331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int titleIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.TITLE);
128431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int containerIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CONTAINER);
128531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int screenIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.SCREEN);
128631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int cellXIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CELLX);
128731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                final int cellYIndex = c.getColumnIndexOrThrow(LauncherSettings.Favorites.CELLY);
128831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
128931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                FolderInfo folderInfo = null;
129031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                switch (c.getInt(itemTypeIndex)) {
129131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    case LauncherSettings.Favorites.ITEM_TYPE_USER_FOLDER:
129231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        folderInfo = findOrMakeUserFolder(mFolders, id);
129331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        break;
129431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                    case LauncherSettings.Favorites.ITEM_TYPE_LIVE_FOLDER:
129531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        folderInfo = findOrMakeLiveFolder(mFolders, id);
129631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                        break;
129731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                }
129831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
129931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.title = c.getString(titleIndex);
130031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.id = id;
130131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.container = c.getInt(containerIndex);
130231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.screen = c.getInt(screenIndex);
130331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.cellX = c.getInt(cellXIndex);
130431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                folderInfo.cellY = c.getInt(cellYIndex);
130531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
130631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                return folderInfo;
130731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            }
130831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        } finally {
130931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            c.close();
131031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
131131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
131231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        return null;
131331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
131431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
131531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
131631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Add an item to the database in a specified container. Sets the container, screen, cellX and
131731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * cellY fields of the item. Also assigns an ID to the item.
131831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
131931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void addItemToDatabase(Context context, ItemInfo item, long container,
132031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            int screen, int cellX, int cellY, boolean notify) {
132131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.container = container;
132231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.screen = screen;
132331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.cellX = cellX;
132431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.cellY = cellY;
13252fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
132631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentValues values = new ContentValues();
132731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
13282fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
132931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.onAddToDatabase(values);
13302fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
133131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        Uri result = cr.insert(notify ? LauncherSettings.Favorites.CONTENT_URI :
133231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                LauncherSettings.Favorites.CONTENT_URI_NO_NOTIFICATION, values);
133331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
133431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        if (result != null) {
133531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project            item.id = Integer.parseInt(result.getPathSegments().get(1));
133631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        }
133731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
133831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
133931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
134073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy     * Add an item to the database in a specified container. Sets the container, screen, cellX and
134173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy     * cellY fields of the item. Also assigns an ID to the item.
134273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy     */
134373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    static boolean addGestureToDatabase(Context context, ItemInfo item, boolean notify) {
134473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentValues values = new ContentValues();
134573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentResolver cr = context.getContentResolver();
134673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
134773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        item.onAddToDatabase(values);
134873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
134973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        Uri result = cr.insert(notify ? LauncherSettings.Gestures.CONTENT_URI :
135073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                LauncherSettings.Gestures.CONTENT_URI_NO_NOTIFICATION, values);
135173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
135273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        if (result != null) {
135373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            item.id = Integer.parseInt(result.getPathSegments().get(1));
135473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        }
135573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
135673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        return result != null;
135773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    }
135873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
135973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    /**
136031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Update an item to the database in a specified container.
136131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
136231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void updateItemInDatabase(Context context, ItemInfo item) {
136331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentValues values = new ContentValues();
136431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
136531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
136631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        item.onAddToDatabase(values);
136731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
136831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        cr.update(LauncherSettings.Favorites.getContentUri(item.id, false), values, null, null);
136931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
13702fcbd686d1c2a9a9e520116a541c9caae0c2dc60Romain Guy
137131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
137231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Removes the specified item from the database
137331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param context
137431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * @param item
137531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
137631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void deleteItemFromDatabase(Context context, ItemInfo item) {
137731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
137831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
137931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        cr.delete(LauncherSettings.Favorites.getContentUri(item.id, false), null, null);
138031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
138131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
138231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
138331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    /**
138431dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     * Remove the contents of the specified folder from the database
138531dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project     */
138631dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    static void deleteUserFolderContentsFromDatabase(Context context, UserFolderInfo info) {
138731dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        final ContentResolver cr = context.getContentResolver();
138831dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project
138931dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        cr.delete(LauncherSettings.Favorites.getContentUri(info.id, false), null, null);
139031dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project        cr.delete(LauncherSettings.Favorites.CONTENT_URI,
139131dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project                LauncherSettings.Favorites.CONTAINER + "=" + info.id, null);
139231dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project    }
139373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
139473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    static void deleteGestureFromDatabase(Context context, ItemInfo item) {
139573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentResolver cr = context.getContentResolver();
139673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
139773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        cr.delete(LauncherSettings.Gestures.getContentUri(item.id, false), null, null);
139873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    }
139973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
140073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    static void updateGestureInDatabase(Context context, ItemInfo item) {
140173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentValues values = new ContentValues();
140273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentResolver cr = context.getContentResolver();
140373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
140473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        item.onAddToDatabase(values);
140573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
140673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        cr.update(LauncherSettings.Gestures.getContentUri(item.id, false), values, null, null);
140773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    }
140873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
140973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
141073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    ApplicationInfo queryGesture(Context context, String id) {
141173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final ContentResolver contentResolver = context.getContentResolver();
141273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final PackageManager manager = context.getPackageManager();
141373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        final Cursor c = contentResolver.query(
141473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                LauncherSettings.Gestures.CONTENT_URI, null, LauncherSettings.Gestures._ID + "=?",
141573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                new String[] { id }, null);
141673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
141773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        ApplicationInfo info = null;
141873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
141973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        try {
142073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int idIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures._ID);
142173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int intentIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.INTENT);
142273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int titleIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.TITLE);
142373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int iconTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.ICON_TYPE);
142473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int iconIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.ICON);
142573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int iconPackageIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.ICON_PACKAGE);
142673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int iconResourceIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.ICON_RESOURCE);
142773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            final int itemTypeIndex = c.getColumnIndexOrThrow(LauncherSettings.Gestures.ITEM_TYPE);
142873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
142973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            String intentDescription;
143073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            Intent intent;
143173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
143273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            if (c.moveToNext()) {
143373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                int itemType = c.getInt(itemTypeIndex);
143473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
143573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                switch (itemType) {
143673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                    case LauncherSettings.Favorites.ITEM_TYPE_APPLICATION:
143773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                    case LauncherSettings.Favorites.ITEM_TYPE_SHORTCUT:
143873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        intentDescription = c.getString(intentIndex);
143973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        try {
144073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            intent = Intent.getIntent(intentDescription);
144173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        } catch (java.net.URISyntaxException e) {
144273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            return null;
144373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        }
144473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
144573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        if (itemType == LauncherSettings.Favorites.ITEM_TYPE_APPLICATION) {
144673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            info = getApplicationInfo(manager, intent, context);
144773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        } else {
144873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            info = getApplicationInfoShortcut(c, context, iconTypeIndex,
144973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                                    iconPackageIndex, iconResourceIndex, iconIndex);
145073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        }
145173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
145273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        if (info == null) {
145373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            info = new ApplicationInfo();
145473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                            info.icon = manager.getDefaultActivityIcon();
145573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        }
145673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
145773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        info.isGesture = true;
145873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        info.title = c.getString(titleIndex);
145973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        info.intent = intent;
146073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        info.id = c.getLong(idIndex);
146173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
146273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                        break;
146373b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy                }
146473b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            }
146573b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        } catch (Exception e) {
146673b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            w(LOG_TAG, "Could not load gesture with name " + id);
146773b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        } finally {
146873b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy            c.close();
146973b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        }
147073b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy
147173b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy        return info;
147273b979d8c141c7ceac82dad7c5b271a6a42afa67Romain Guy    }
147331dd503c6aa69018e694d91724d46db49ea09327The Android Open Source Project}
1474