QuickLaunchSettings.java revision 8762093e0094e09493fa6cbac8e8fbf265f18165
1afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project/*
2afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * Copyright (C) 2008 The Android Open Source Project
3afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project *
4afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
5afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * you may not use this file except in compliance with the License.
6afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * You may obtain a copy of the License at
7afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project *
8afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
9afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project *
10afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * Unless required by applicable law or agreed to in writing, software
11afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
12afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * See the License for the specific language governing permissions and
14afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * limitations under the License.
15afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project */
16afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
17afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectpackage com.android.settings.quicklaunch;
18afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
19afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.app.AlertDialog;
20afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.app.Dialog;
21afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.content.DialogInterface;
22afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.content.Intent;
23afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.database.ContentObserver;
24afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.database.Cursor;
25afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.os.Bundle;
26afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.os.Handler;
27afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.preference.Preference;
28afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.preference.PreferenceActivity;
29afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.preference.PreferenceGroup;
30afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.preference.PreferenceScreen;
31afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.provider.Settings.Bookmarks;
32afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.util.Log;
33afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.util.SparseArray;
34afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.util.SparseBooleanArray;
35afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.view.KeyCharacterMap;
36afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.view.KeyEvent;
37afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.view.View;
38afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport android.widget.AdapterView;
39afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
40afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectimport com.android.settings.R;
41afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
42afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project/**
43afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * Settings activity for quick launch.
44afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * <p>
45afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * Shows a list of possible shortcuts, the current application each is bound to,
46afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project * and allows choosing a new bookmark for a shortcut.
47afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project */
48afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Projectpublic class QuickLaunchSettings extends PreferenceActivity implements
49afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        AdapterView.OnItemLongClickListener, DialogInterface.OnClickListener {
50afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
51afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String TAG = "QuickLaunchSettings";
52afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
53afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String KEY_SHORTCUT_CATEGORY = "shortcut_category";
54afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
55afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final int DIALOG_CLEAR_SHORTCUT = 0;
56afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
57afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final int REQUEST_PICK_BOOKMARK = 1;
58afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
59afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final int COLUMN_SHORTCUT = 0;
60afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final int COLUMN_TITLE = 1;
61afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final int COLUMN_INTENT = 2;
62afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String[] sProjection = new String[] {
63afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            Bookmarks.SHORTCUT, Bookmarks.TITLE, Bookmarks.INTENT
64afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    };
65afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String sShortcutSelection = Bookmarks.SHORTCUT + "=?";
66afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
67afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private Handler mUiHandler = new Handler();
68afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
69afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String DEFAULT_BOOKMARK_FOLDER = "@quicklaunch";
70afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** Cursor for Bookmarks provider. */
71afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private Cursor mBookmarksCursor;
72afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** Listens for changes to Bookmarks provider. */
73afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private BookmarksObserver mBookmarksObserver;
74afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** Used to keep track of which shortcuts have bookmarks. */
75afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private SparseBooleanArray mBookmarkedShortcuts;
76afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
77afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** Preference category to hold the shortcut preferences. */
78afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private PreferenceGroup mShortcutGroup;
79afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** Mapping of a shortcut to its preference. */
80afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private SparseArray<ShortcutPreference> mShortcutToPreference;
81afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
82afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** The bookmark title of the shortcut that is being cleared. */
83afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private CharSequence mClearDialogBookmarkTitle;
84afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String CLEAR_DIALOG_BOOKMARK_TITLE = "CLEAR_DIALOG_BOOKMARK_TITLE";
85afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    /** The shortcut that is being cleared. */
86afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private char mClearDialogShortcut;
87afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private static final String CLEAR_DIALOG_SHORTCUT = "CLEAR_DIALOG_SHORTCUT";
88afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
89afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
90afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onCreate(Bundle savedInstanceState) {
91afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        super.onCreate(savedInstanceState);
92afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
93afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        addPreferencesFromResource(R.xml.quick_launch_settings);
94afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
95afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mShortcutGroup = (PreferenceGroup) findPreference(KEY_SHORTCUT_CATEGORY);
96afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mShortcutToPreference = new SparseArray<ShortcutPreference>();
97afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mBookmarksObserver = new BookmarksObserver(mUiHandler);
98afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        initShortcutPreferences();
99afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mBookmarksCursor = managedQuery(Bookmarks.CONTENT_URI, sProjection, null, null);
100afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        getListView().setOnItemLongClickListener(this);
101afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
102afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
103afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
104afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onResume() {
105afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        super.onResume();
106afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        getContentResolver().registerContentObserver(Bookmarks.CONTENT_URI, true,
107afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                mBookmarksObserver);
108afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        refreshShortcuts();
109afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
110afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
111afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
112afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onPause() {
113afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        super.onPause();
114afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        getContentResolver().unregisterContentObserver(mBookmarksObserver);
115afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
116afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
117afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
118afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onRestoreInstanceState(Bundle state) {
119afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        super.onRestoreInstanceState(state);
120afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
121afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Restore the clear dialog's info
122afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogBookmarkTitle = state.getString(CLEAR_DIALOG_BOOKMARK_TITLE);
123afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogShortcut = (char) state.getInt(CLEAR_DIALOG_SHORTCUT, 0);
124afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
125afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
126afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
127afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onSaveInstanceState(Bundle outState) {
128afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        super.onSaveInstanceState(outState);
129afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
130afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Save the clear dialog's info
131afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        outState.putCharSequence(CLEAR_DIALOG_BOOKMARK_TITLE, mClearDialogBookmarkTitle);
132afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        outState.putInt(CLEAR_DIALOG_SHORTCUT, mClearDialogShortcut);
133afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
134afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
135afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
136afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected Dialog onCreateDialog(int id) {
137afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        switch (id) {
138afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
139afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            case DIALOG_CLEAR_SHORTCUT: {
140afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                // Create the dialog for clearing a shortcut
141afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                return new AlertDialog.Builder(this)
142afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .setTitle(getString(R.string.quick_launch_clear_dialog_title))
143afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .setIcon(android.R.drawable.ic_dialog_alert)
144afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .setMessage(getString(R.string.quick_launch_clear_dialog_message,
145afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                                mClearDialogShortcut, mClearDialogBookmarkTitle))
146afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .setPositiveButton(R.string.quick_launch_clear_ok_button, this)
147afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .setNegativeButton(R.string.quick_launch_clear_cancel_button, this)
148afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        .create();
149afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            }
150afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
151afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
152afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        return super.onCreateDialog(id);
153afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
154afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
155afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
156afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onPrepareDialog(int id, Dialog dialog) {
157afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        switch (id) {
158afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
159afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            case DIALOG_CLEAR_SHORTCUT: {
160afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                AlertDialog alertDialog = (AlertDialog) dialog;
161afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                alertDialog.setMessage(getString(R.string.quick_launch_clear_dialog_message,
162afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        mClearDialogShortcut, mClearDialogBookmarkTitle));
163afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            }
164afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
165afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
166afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
167afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private void showClearDialog(ShortcutPreference pref) {
168afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
169afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (!pref.hasBookmark()) return;
170afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
171afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogBookmarkTitle = pref.getTitle();
172afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogShortcut = pref.getShortcut();
173afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        showDialog(DIALOG_CLEAR_SHORTCUT);
174afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
175afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
176afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    public void onClick(DialogInterface dialog, int which) {
177afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (mClearDialogShortcut > 0 && which == AlertDialog.BUTTON1) {
178afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // Clear the shortcut
179afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            clearShortcut(mClearDialogShortcut);
180afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
181afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogBookmarkTitle = null;
182afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mClearDialogShortcut = 0;
183afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
184afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
185afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private void clearShortcut(char shortcut) {
186afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        getContentResolver().delete(Bookmarks.CONTENT_URI, sShortcutSelection,
187afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                new String[] { String.valueOf((int) shortcut) });
188afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
189afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
190afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
191afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference) {
192afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (!(preference instanceof ShortcutPreference)) return false;
193afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
194afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Open the screen to pick a bookmark for this shortcut
195afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        ShortcutPreference pref = (ShortcutPreference) preference;
196afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        Intent intent = new Intent(this, BookmarkPicker.class);
197afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        intent.putExtra(BookmarkPicker.EXTRA_SHORTCUT, pref.getShortcut());
198afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        startActivityForResult(intent, REQUEST_PICK_BOOKMARK);
199afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
200afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        return true;
201afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
202afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
203afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    public boolean onItemLongClick(AdapterView parent, View view, int position, long id) {
204afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
205afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Open the clear shortcut dialog
206afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        Preference pref = (Preference) getPreferenceScreen().getRootAdapter().getItem(position);
207afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (!(pref instanceof ShortcutPreference)) return false;
208afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        showClearDialog((ShortcutPreference) pref);
209afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        return true;
210afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
211afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
212afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    @Override
213afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
214afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (resultCode != RESULT_OK) {
215afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            return;
216afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
217afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
218afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (requestCode == REQUEST_PICK_BOOKMARK) {
219afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
220afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // Returned from the 'pick bookmark for this shortcut' screen
221afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            if (data == null) {
222afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                Log.w(TAG, "Result from bookmark picker does not have an intent.");
223afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                return;
224afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            }
2258762093e0094e09493fa6cbac8e8fbf265f18165Michael Chan
226afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            char shortcut = data.getCharExtra(BookmarkPicker.EXTRA_SHORTCUT, (char) 0);
227afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            updateShortcut(shortcut, data);
228afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
229afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        } else {
230afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            super.onActivityResult(requestCode, resultCode, data);
231afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
232afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
233afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
234afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private void updateShortcut(char shortcut, Intent intent) {
235afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Update the bookmark for a shortcut
236afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Pass an empty title so it gets resolved each time this bookmark is
237afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // displayed (since the locale could change after we insert into the provider).
238afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        Bookmarks.add(getContentResolver(), intent, "", DEFAULT_BOOKMARK_FOLDER, shortcut, 0);
239afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
240afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
241afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private ShortcutPreference getOrCreatePreference(char shortcut) {
242afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        ShortcutPreference pref = mShortcutToPreference.get(shortcut);
243afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (pref != null) {
244afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            return pref;
245afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        } else {
246afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            Log.w(TAG, "Unknown shortcut '" + shortcut + "', creating preference anyway");
247afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            return createPreference(shortcut);
248afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
249afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
250afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
251afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private ShortcutPreference createPreference(char shortcut) {
252afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        ShortcutPreference pref = new ShortcutPreference(QuickLaunchSettings.this, shortcut);
253afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mShortcutGroup.addPreference(pref);
254afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mShortcutToPreference.put(shortcut, pref);
255afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        return pref;
256afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
257afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
258afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private void initShortcutPreferences() {
259afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
260afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        /** Whether the shortcut has been seen already.  The array index is the shortcut. */
261afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        SparseBooleanArray shortcutSeen = new SparseBooleanArray();
262afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        KeyCharacterMap keyMap = KeyCharacterMap.load(KeyCharacterMap.BUILT_IN_KEYBOARD);
263afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
264afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        // Go through all the key codes and create a preference for the appropriate keys
265afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        for (int keyCode = KeyEvent.getMaxKeyCode() - 1; keyCode >= 0; keyCode--) {
266afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // Get the label for the primary char on the key that produces this key code
267afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            char shortcut = (char) Character.toLowerCase(keyMap.getDisplayLabel(keyCode));
268afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            if (shortcut == 0 || shortcutSeen.get(shortcut, false)) continue;
269afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // TODO: need a to tell if the current keyboard can produce this key code, for now
270afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // only allow the letter or digits
271afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            if (!Character.isLetterOrDigit(shortcut)) continue;
272afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            shortcutSeen.put(shortcut, true);
273afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
274afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            createPreference(shortcut);
275afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
276afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
277afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
278afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private synchronized void refreshShortcuts() {
279afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        Cursor c = mBookmarksCursor;
280afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (c == null) {
281afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            // Haven't finished querying yet
282afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            return;
283afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
284afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
285afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (!c.requery()) {
286afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            Log.e(TAG, "Could not requery cursor when refreshing shortcuts.");
287afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            return;
288afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
289afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
290afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        /**
291afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project         * We use the previous bookmarked shortcuts array to filter out those
292afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project         * shortcuts that had bookmarks before this method call, and don't after
293afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project         * (so we can set the preferences to be without bookmarks).
294afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project         */
295afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        SparseBooleanArray noLongerBookmarkedShortcuts = mBookmarkedShortcuts;
296afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        SparseBooleanArray newBookmarkedShortcuts = new SparseBooleanArray();
297afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        while (c.moveToNext()) {
298afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            char shortcut = Character.toLowerCase((char) c.getInt(COLUMN_SHORTCUT));
299afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            if (shortcut == 0) continue;
300afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
301afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            ShortcutPreference pref = getOrCreatePreference(shortcut);
302afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            pref.setTitle(Bookmarks.getTitle(this, c));
303afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            pref.setSummary(getString(R.string.quick_launch_shortcut,
304afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    String.valueOf(shortcut)));
305afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            pref.setHasBookmark(true);
306afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
307afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            newBookmarkedShortcuts.put(shortcut, true);
308afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            if (noLongerBookmarkedShortcuts != null) {
309afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                // After this loop, the shortcuts with value true in this array
310afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                // will no longer have bookmarks
311afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                noLongerBookmarkedShortcuts.put(shortcut, false);
312afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            }
313afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
314afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
315afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        if (noLongerBookmarkedShortcuts != null) {
316afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            for (int i = noLongerBookmarkedShortcuts.size() - 1; i >= 0; i--) {
317afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                if (noLongerBookmarkedShortcuts.valueAt(i)) {
318afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    // True, so there is no longer a bookmark for this shortcut
319afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    char shortcut = (char) noLongerBookmarkedShortcuts.keyAt(i);
320afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    ShortcutPreference pref = mShortcutToPreference.get(shortcut);
321afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    if (pref != null) {
322afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                        pref.setHasBookmark(false);
323afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                    }
324afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project                }
325afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            }
326afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
327afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
328afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        mBookmarkedShortcuts = newBookmarkedShortcuts;
329afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
330afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        c.deactivate();
331afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
332afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
333afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    private class BookmarksObserver extends ContentObserver {
334afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
335afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        public BookmarksObserver(Handler handler) {
336afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            super(handler);
337afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
338afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
339afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        @Override
340afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        public void onChange(boolean selfChange) {
341afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            super.onChange(selfChange);
342afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project
343afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project            refreshShortcuts();
344afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project        }
345afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project    }
346afc4ab2ffbb8327ddce9907961295a32cbf49d0fThe Android Open Source Project}
347