Add support for saving and using the Preference's key value
- modify the SQlite data model
- update Index code for managing the key value
- pass the key when launching a Fragment or and Activity
- implement a small animation for highlighting the Preference
from a Search result
Change-Id: I617643a4e5e3b752ece8f45ce7d5429037e479da
diff --git a/src/com/android/settings/SettingsActivity.java b/src/com/android/settings/SettingsActivity.java
index 7cdf781..6128690 100644
--- a/src/com/android/settings/SettingsActivity.java
+++ b/src/com/android/settings/SettingsActivity.java
@@ -146,6 +146,11 @@
public static final String EXTRA_SHOW_FRAGMENT_ARGUMENTS = ":settings:show_fragment_args";
/**
+ * Fragment "key" argument passed thru {@link #EXTRA_SHOW_FRAGMENT_ARGUMENTS}
+ */
+ public static final String EXTRA_FRAGMENT_ARG_KEY = ":settings:fragment_args_key";
+
+ /**
* When starting this activity, the invoking Intent can contain this extra
* boolean that the header list should not be displayed. This is most often
* used in conjunction with {@link #EXTRA_SHOW_FRAGMENT} to launch
@@ -461,6 +466,7 @@
final String initialTitle = getIntent().getStringExtra(EXTRA_SHOW_FRAGMENT_TITLE);
mInitialTitle = (initialTitle != null) ? initialTitle : getTitle();
setTitle(mInitialTitle);
+
switchToFragment( initialFragmentName, initialArguments, true, false,
mInitialTitle, false);
} else {
diff --git a/src/com/android/settings/SettingsPreferenceFragment.java b/src/com/android/settings/SettingsPreferenceFragment.java
index 35893ff..d575153 100644
--- a/src/com/android/settings/SettingsPreferenceFragment.java
+++ b/src/com/android/settings/SettingsPreferenceFragment.java
@@ -26,12 +26,15 @@
import android.os.Bundle;
import android.preference.Preference;
import android.preference.PreferenceFragment;
+import android.preference.PreferenceGroup;
+import android.preference.PreferenceGroupAdapter;
import android.text.TextUtils;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.widget.Button;
+import android.widget.ListAdapter;
/**
* Base class for Settings fragments, with some helper functions and dialog management.
@@ -41,6 +44,7 @@
private static final String TAG = "SettingsPreferenceFragment";
private static final int MENU_HELP = Menu.FIRST + 100;
+ private static final int HIGHLIGHT_DURATION_MILLIS = 750;
private SettingsDialogFragment mDialogFragment;
@@ -66,6 +70,47 @@
if (!TextUtils.isEmpty(mHelpUrl)) {
setHasOptionsMenu(true);
}
+
+ final Bundle args = getArguments();
+ if (args != null) {
+ final String key = args.getString(SettingsActivity.EXTRA_FRAGMENT_ARG_KEY);
+ final int position = findPositionFromKey(getPreferenceScreen(), key);
+ if (position >= 0) {
+ final ListAdapter adapter = getListView().getAdapter();
+ if (adapter instanceof PreferenceGroupAdapter) {
+ ((PreferenceGroupAdapter) adapter).setActivated(position);
+
+ getListView().postDelayed(new Runnable() {
+ @Override
+ public void run() {
+ ((PreferenceGroupAdapter) adapter).setActivated(-1);
+ ((PreferenceGroupAdapter) adapter).notifyDataSetChanged();
+ }
+ }, HIGHLIGHT_DURATION_MILLIS);
+ }
+ }
+ }
+ }
+
+ private int findPositionFromKey(PreferenceGroup group, String key) {
+ if (group != null) {
+ int count = group.getPreferenceCount();
+ for (int n = 0; n < count; n++) {
+ final Preference preference = group.getPreference(n);
+ final String preferenceKey = preference.getKey();
+ if (preferenceKey != null && preferenceKey.equals(key)) {
+ return n;
+ }
+ if (preference instanceof PreferenceGroup) {
+ PreferenceGroup nestedGroup = (PreferenceGroup) preference;
+ final int nestedPosition = findPositionFromKey(nestedGroup, key);
+ if (nestedPosition >= 0) {
+ return n + 1 + nestedPosition;
+ }
+ }
+ }
+ }
+ return -1;
}
protected void removePreference(String key) {
diff --git a/src/com/android/settings/dashboard/SearchResultsSummary.java b/src/com/android/settings/dashboard/SearchResultsSummary.java
index 706ae0f..22326a6 100644
--- a/src/com/android/settings/dashboard/SearchResultsSummary.java
+++ b/src/com/android/settings/dashboard/SearchResultsSummary.java
@@ -109,15 +109,18 @@
final String className = cursor.getString(Index.COLUMN_INDEX_CLASS_NAME);
final String screenTitle = cursor.getString(Index.COLUMN_INDEX_SCREEN_TITLE);
-
final String action = cursor.getString(Index.COLUMN_INDEX_INTENT_ACTION);
+ final String key = cursor.getString(Index.COLUMN_INDEX_KEY);
final SettingsActivity sa = (SettingsActivity) getActivity();
sa.needToRevertToInitialFragment();
if (TextUtils.isEmpty(action)) {
- sa.startWithFragment(className, null, null, 0, screenTitle);
+ Bundle args = new Bundle();
+ args.putString(SettingsActivity.EXTRA_FRAGMENT_ARG_KEY, key);
+
+ sa.startWithFragment(className, args, null, 0, screenTitle);
} else {
final Intent intent = new Intent(action);
@@ -130,6 +133,7 @@
new ComponentName(targetPackage, targetClass);
intent.setComponent(component);
}
+ intent.putExtra(SettingsActivity.EXTRA_FRAGMENT_ARG_KEY, key);
sa.startActivity(intent);
}
@@ -194,21 +198,23 @@
}
private static class SearchResult {
+ public Context context;
public String title;
public String summaryOn;
public String summaryOff;
public String entries;
public int iconResId;
- public Context context;
+ public String key;
public SearchResult(Context context, String title, String summaryOn, String summaryOff,
- String entries, int iconResId) {
+ String entries, int iconResId, String key) {
this.context = context;
this.title = title;
this.summaryOn = summaryOn;
this.summaryOff = summaryOff;
this.entries = entries;
this.iconResId = iconResId;
+ this.key = key;
}
}
@@ -263,6 +269,8 @@
Index.COLUMN_INDEX_CLASS_NAME);
final String packageName = mCursor.getString(
Index.COLUMN_INDEX_INTENT_ACTION_TARGET_PACKAGE);
+ final String key = mCursor.getString(
+ Index.COLUMN_INDEX_KEY);
Context packageContext;
if (TextUtils.isEmpty(className) && !TextUtils.isEmpty(packageName)) {
@@ -284,7 +292,7 @@
R.drawable.empty_icon : Integer.parseInt(iconResStr);
return new SearchResult(packageContext, title, summaryOn, summaryOff,
- entries, iconResId);
+ entries, iconResId, key);
}
return null;
}
diff --git a/src/com/android/settings/search/Index.java b/src/com/android/settings/search/Index.java
index 987539b..138c896 100644
--- a/src/com/android/settings/search/Index.java
+++ b/src/com/android/settings/search/Index.java
@@ -71,6 +71,7 @@
public static final int COLUMN_INDEX_INTENT_ACTION_TARGET_PACKAGE = 12;
public static final int COLUMN_INDEX_INTENT_ACTION_TARGET_CLASS = 13;
public static final int COLUMN_INDEX_ENABLED = 14;
+ public static final int COLUMN_INDEX_KEY = 15;
// If you change the order of columns here, you SHOULD change the COLUMN_INDEX_XXX values
private static final String[] SELECT_COLUMNS = new String[] {
@@ -87,7 +88,9 @@
IndexColumns.ICON, // 10
IndexColumns.INTENT_ACTION, // 11
IndexColumns.INTENT_TARGET_PACKAGE, // 12
- IndexColumns.INTENT_TARGET_CLASS // 13
+ IndexColumns.INTENT_TARGET_CLASS, // 13
+ IndexColumns.ENABLED, // 14
+ IndexColumns.DATA_KEY_REF // 15
};
private static final String[] MATCH_COLUMNS = {
@@ -375,6 +378,8 @@
final String targetPackage = cursor.getString(12);
final String targetClass = cursor.getString(13);
+ final String key = cursor.getString(15);
+
SearchIndexableRaw data = new SearchIndexableRaw(packageContext);
data.rank = rank;
data.title = title;
@@ -391,6 +396,7 @@
data.intentAction = action;
data.intentTargetPackage = targetPackage;
data.intentTargetClass = targetClass;
+ data.key = key;
addIndexableData(data);
}
@@ -503,12 +509,13 @@
String title = getDataTitle(context, attrs);
String summary = getDataSummary(context, attrs);
String keywords = getDataKeywords(context, attrs);
+ String key = getDataKey(context, attrs);
// Insert rows for the main PreferenceScreen node. Rewrite the data for removing
// hyphens.
updateOneRowWithFilteredData(database, localeStr, title, summary, null, null,
- null, null, fragmentName, screenTitle, iconResId, rank, keywords,
- intentAction, intentTargetPackage, intentTargetClass, true);
+ null, null, fragmentName, screenTitle, iconResId, rank,
+ keywords, intentAction, intentTargetPackage, intentTargetClass, true, key);
while ((type = parser.next()) != XmlPullParser.END_DOCUMENT
&& (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
@@ -520,6 +527,7 @@
title = getDataTitle(context, attrs);
keywords = getDataKeywords(context, attrs);
+ key = getDataKey(context, attrs);
if (!nodeName.equals(NODE_NAME_CHECK_BOX_PREFERENCE)) {
summary = getDataSummary(context, attrs);
@@ -537,15 +545,17 @@
// Insert rows for the child nodes of PreferenceScreen
updateOneRowWithFilteredData(database, localeStr, title, summary, null, entries,
- switchOn, switchOff, fragmentName, screenTitle, iconResId, rank, keywords,
- intentAction, intentTargetPackage, intentTargetClass, true);
- } else if (nodeName.equals(NODE_NAME_CHECK_BOX_PREFERENCE)) {
+ switchOn, switchOff, fragmentName, screenTitle, iconResId, rank,
+ keywords, intentAction, intentTargetPackage, intentTargetClass,
+ true, key);
+ } else {
final String summaryOn = getDataSummaryOn(context, attrs);
final String summaryOff = getDataSummaryOff(context, attrs);
updateOneRowWithFilteredData(database, localeStr, title, summaryOn, summaryOff,
- null, null, null, fragmentName, screenTitle, iconResId, rank, keywords,
- intentAction, intentTargetPackage, intentTargetClass, true);
+ null, null, null, fragmentName, screenTitle, iconResId, rank,
+ keywords, intentAction, intentTargetPackage, intentTargetClass,
+ true, key);
}
}
@@ -580,7 +590,8 @@
raw.intentAction,
raw.intentTargetPackage,
raw.intentTargetClass,
- raw.enabled);
+ raw.enabled,
+ raw.key);
}
private void indexFromLocalProvider(SQLiteDatabase database, String localeStr,
@@ -619,7 +630,8 @@
raw.intentAction,
raw.intentTargetPackage,
raw.intentTargetClass,
- raw.enabled);
+ raw.enabled,
+ raw.key);
}
}
@@ -657,7 +669,7 @@
String switchOn, String switchOff, String className,
String screenTitle, int iconResId, int rank, String keywords,
String intentAction, String intentTargetPackage, String intentTargetClass,
- boolean enabled) {
+ boolean enabled, String key) {
String updatedTitle;
if (title != null) {
@@ -706,7 +718,7 @@
updatedSummaryOff, normalizedSummaryOff, entries,
updatedSwitchOn, normalizedSwitchOn, updatedSwitchOff, normalizedSwitchOff,
className, screenTitle, iconResId,
- rank, keywords, intentAction, intentTargetPackage, intentTargetClass, enabled);
+ rank, keywords, intentAction, intentTargetPackage, intentTargetClass, enabled, key);
}
private void updateOneRow(SQLiteDatabase database, String locale,
@@ -717,7 +729,7 @@
String updatedSwitchOff, String normalizedSwitchOff,
String className, String screenTitle, int iconResId, int rank, String keywords,
String intentAction, String intentTargetPackage, String intentTargetClass,
- boolean enabled) {
+ boolean enabled, String key) {
if (TextUtils.isEmpty(updatedTitle)) {
return;
@@ -746,10 +758,17 @@
values.put(IndexColumns.INTENT_TARGET_CLASS, intentTargetClass);
values.put(IndexColumns.ICON, iconResId);
values.put(IndexColumns.ENABLED, enabled);
+ values.put(IndexColumns.DATA_KEY_REF, key);
database.replaceOrThrow(Tables.TABLE_PREFS_INDEX, null, values);
}
+ private String getDataKey(Context context, AttributeSet attrs) {
+ return getData(context, attrs,
+ com.android.internal.R.styleable.Preference,
+ com.android.internal.R.styleable.Preference_key);
+ }
+
private String getDataTitle(Context context, AttributeSet attrs) {
return getData(context, attrs,
com.android.internal.R.styleable.Preference,
diff --git a/src/com/android/settings/search/IndexDatabaseHelper.java b/src/com/android/settings/search/IndexDatabaseHelper.java
index bd035c3..bc827f4 100644
--- a/src/com/android/settings/search/IndexDatabaseHelper.java
+++ b/src/com/android/settings/search/IndexDatabaseHelper.java
@@ -28,7 +28,7 @@
private static final String TAG = "IndexDatabaseHelper";
private static final String DATABASE_NAME = "search_index.db";
- private static final int DATABASE_VERSION = 106;
+ private static final int DATABASE_VERSION = 107;
public interface Tables {
public static final String TABLE_PREFS_INDEX = "prefs_index";
@@ -58,6 +58,7 @@
public static final String INTENT_TARGET_CLASS = "intent_target_class";
public static final String ICON = "icon";
public static final String ENABLED = "enabled";
+ public static final String DATA_KEY_REF = "data_key_reference";
}
public interface MetaColumns {
@@ -108,6 +109,8 @@
IndexColumns.INTENT_TARGET_CLASS +
", " +
IndexColumns.ENABLED +
+ ", " +
+ IndexColumns.DATA_KEY_REF +
");";
private static final String CREATE_META_TABLE =