我正在尝试在我的应用程序中提出自定义搜索建议。我从文档和可搜索字典示例开始。然而,这个例子对我来说不是很好,所以我已经开始进行一些测试以了解如何制作它,因为互联网上也没有太多的教程。
一般来说,我的应用程序现在有 2 个数据库——一个是正常的,第二个是列数较少的——FTS3。我想要实现的是将建议提供者连接到这个 FTS3 表。
我现在想做的是,使用简单的功能,在搜索框中输入任何字母后,在建议中返回整个数据库(大约 200 条记录)。我知道限制 50 条记录,但我认为这不是问题。这是 Provider 代码的片段。我发现,当您输入文本时,提供者会转到选项SEARCH_SUGGEST
:
// UriMatcher stuff
private static final int SEARCH_WORDS = 0;
private static final int GET_WORD = 1;
private static final int SEARCH_SUGGEST = 2;
private static final int REFRESH_SHORTCUT = 3;
private static final UriMatcher mUriMatcher = buildUriMatcher();
/**
* Builds up a UriMatcher for search suggestion and shortcut refresh queries.
*/
private static UriMatcher buildUriMatcher() {
Log.d(TAG,"urimatcher");
UriMatcher matcher = new UriMatcher(UriMatcher.NO_MATCH);
// to get definitions...
matcher.addURI(AUTHORITY, "mydb", SEARCH_WORDS);
matcher.addURI(AUTHORITY, "mydb/#", GET_WORD);
// to get suggestions...
matcher.addURI(AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY, SEARCH_SUGGEST);
matcher.addURI(AUTHORITY, SearchManager.SUGGEST_URI_PATH_QUERY + "/*", SEARCH_SUGGEST);
return matcher;
}
@Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
switch (mUriMatcher.match(uri)) {
case SEARCH_SUGGEST:
Log.d(TAG,"SEARCH_SUGGEST");
if (selectionArgs == null) {
throw new IllegalArgumentException(
"selectionArgs must be provided for the Uri: " + uri);
}
return getSuggestions(selectionArgs[0]);
case SEARCH_WORDS:
Log.d(TAG,"SEARCH_WORDS");
if (selectionArgs == null) {
throw new IllegalArgumentException(
"selectionArgs must be provided for the Uri: " + uri);
}
return search(selectionArgs[0]);
case GET_WORD:
Log.d(TAG,"GET_WORD");
return null;
default:
Log.d(TAG,"default");
throw new IllegalArgumentException("Unknown Uri: " + uri);
}
}
private Cursor getSuggestions(String query) {
String[] columns = { MyDBAdapter.KEY_TITLE,MyDBAdapter.KEY_ID};
Log.d(TAG,"query1: " + query);
try{
Cursor tmp = MyDB.getAllEntriesFTS(false, columns,
null, null, null, null, MyDBAdapter.KEY_TITLE, null, query);
Log.d(TAG,"cursor: " + Integer.toString(tmp.getCount()));
}
catch(Exception e)
{
Log.d(TAG,e.toString());
}
return tmp;
}
在getSuggestions
我输入的代码通常应该可以工作,但它没有。仅在此处使用时不起作用。当我在其他活动中使用它来获取列表视图的光标时,一切都很好。在这里它返回我的 NullPointerException。
所以越来越深入,我还在方法中添加了一些日志标签getAllEntriesFTS
,这个方法看起来像这样:
public Cursor getAllEntriesFTS(boolean distinct, String[] result_columns,
String selection, String[] selectionArgs, String groupBy,
String having, String orderBy, String limit, String query) {
Log.d(TAG,"query db: " + query);
String[] columns = { MyDBAdapter.KEY_TITLE, MyDBAdapter.KEY_ID};
Log.d(TAG,"columns: " + Integer.toString(result_columns.length));
Cursor allRows = null;
try{
allRows = db.query(distinct, DATABASE_TABLE_FTS, columns,
null, null, null, null, MyDBAdapter.KEY_TITLE, null);
Log.d(TAG,"OK");
}
catch(Exception e)
{
Log.d(TAG, e.toString());//it always goes there with NullPointerExceptionwhen used in provider
}
Log.d(TAG,Integer.toString(allRows.getCount()));
return allRows;
}
所以,一般来说,它应该将光标返回到整个数据库,而是在不应该出现 NullPointerException 的地方抛出。
有人可以告诉我我做错了什么以及应该怎么做?