Android 使用SearchManager';s SUGGEST_COLUMN_ICON_1显示本地文件

Android 使用SearchManager';s SUGGEST_COLUMN_ICON_1显示本地文件,android,android-searchmanager,Android,Android Searchmanager,我正在实现我自己的SearchRecentSuggestionsProvider,除了一件事之外,一切都正常:我无法让设备搜索显示结果图标。我想显示应用程序数据文件夹中的图像(位于/{sdcard}/Android/data/package_name/files/) 根据,它可以通过使用SearchManager.SUGGEST\u COLUMN\u ICON\u 1来实现,而且它显然支持许多方案,包括ContentResolver.SCHEME\u FILE,即FILE。以下是官方文件的引述:

我正在实现我自己的
SearchRecentSuggestionsProvider
,除了一件事之外,一切都正常:我无法让设备搜索显示结果图标。我想显示应用程序数据文件夹中的图像(位于
/{sdcard}/Android/data/package_name/files/

根据,它可以通过使用
SearchManager.SUGGEST\u COLUMN\u ICON\u 1
来实现,而且它显然支持许多方案,包括
ContentResolver.SCHEME\u FILE
,即
FILE
。以下是官方文件的引述:

建议游标的列名。可选。如果光标包含此列,则所有建议都将以包含两个小图标的空间的格式提供,一个在每个建议的左侧,一个在右侧。列中的数据必须是可绘制的资源ID,或以下格式之一的URI:

内容(
方案\内容

android.resource(
SCHEME\u android\u resource

文件(
SCHEME\u文件

我尝试了许多明显的方法,包括手动创建文件URI和使用
URI.Builder()
自动创建文件URI。所有这些都不起作用

我还发现有人在谷歌群组上问同样的问题,但遗憾的是没有人回答:

是否有人有过让设备搜索显示设备本地图像的经验

更新(12月15日):
我刚刚尝试使用
ContentProvider
SearchView
作为可搜索的信息,它的效果完全符合预期,包括封面图片。不过,全局搜索并没有显示它…

一种方法是从android.content.SearchRecentSuggestionsProvider复制源代码,将其放在扩展ContentProvider的类中,并自定义
设置建议(String,int)
。具体而言,您将更改以下内容:

Uri uriFile = Uri.fromFile(new File("path/to/file"));

mSuggestionProjection = new String [] {
        "0 AS " + SearchManager.SUGGEST_COLUMN_FORMAT,

        // Here, you would return a file uri: 'uriFile'
        "'android.resource://system/"
                + com.android.internal.R.drawable.ic_menu_recent_history + "' AS "
                        + SearchManager.SUGGEST_COLUMN_ICON_1,
        "display1 AS " + SearchManager.SUGGEST_COLUMN_TEXT_1,
        "query AS " + SearchManager.SUGGEST_COLUMN_QUERY,
        "_id"
};
不过我还是喜欢下面的。扩展
SearchRecentSuggestionsProvider
并覆盖
查询(…)
方法。在这里,截取
SearchManager。建议\u URI\u PATH\u查询
并返回光标

public class SearchSuggestionProvider extends SearchRecentSuggestionsProvider {

    private UriMatcher matcher;

    private static final int URI_MATCH_SUGGEST = 1;

    public SearchSuggestionProvider() {
        super();

        matcher = new UriMatcher(UriMatcher.NO_MATCH);

        // Add uri to return URI_MATCH_SUGGEST
        matcher.addURI(SearchSuggestionProvider.class.getName(), 
                         SearchManager.SUGGEST_URI_PATH_QUERY, URI_MATCH_SUGGEST);

        setupSuggestions(SearchSuggestionProvider.class.getName(), 
                                                           DATABASE_MODE_QUERIES);
    }

    @Override
    public Cursor query(Uri uri, String[] projection, String selection, 
                                      String[] selectionArgs, String sortOrder) {

        // special case for actual suggestions (from search manager)
        if (matcher.match(uri) == URI_MATCH_SUGGEST) {

            // File to use
            File f = new File("/path/to/file");

            Uri uriFile = Uri.fromFile(f);

            final String[] PROJECTION = new String[] {
                "_id", 
                "display1 AS " + SearchManager.SUGGEST_COLUMN_TEXT_1,                
                "query AS " + SearchManager.SUGGEST_COLUMN_QUERY,
                "'" + uriFile + "'" + " AS " + SearchManager.SUGGEST_COLUMN_ICON_1,
            };

            final Uri URI = Uri.parse("content://" + 
                        SearchSuggestionProvider.class.getName() + "/suggestions");

            // return cursor
            return getContext().getContentResolver().query(
                URI, 
                PROJECTION, 
                "display1 LIKE ?", 
                new String[] {selectionArgs[0] + "%"}, 
                "date DESC");          
        }

        // Let super method handle the query if the check fails
        return super.query(uri, projection, selection, selectionArgs, sortOrder);
    }
}

一种方法是从android.content.SearchRecentSuggestionsProvider复制源代码,将其放入扩展ContentProvider的类中,然后自定义
设置建议(String,int)
。具体而言,您将更改以下内容:

Uri uriFile = Uri.fromFile(new File("path/to/file"));

mSuggestionProjection = new String [] {
        "0 AS " + SearchManager.SUGGEST_COLUMN_FORMAT,

        // Here, you would return a file uri: 'uriFile'
        "'android.resource://system/"
                + com.android.internal.R.drawable.ic_menu_recent_history + "' AS "
                        + SearchManager.SUGGEST_COLUMN_ICON_1,
        "display1 AS " + SearchManager.SUGGEST_COLUMN_TEXT_1,
        "query AS " + SearchManager.SUGGEST_COLUMN_QUERY,
        "_id"
};
不过我还是喜欢下面的。扩展
SearchRecentSuggestionsProvider
并覆盖
查询(…)
方法。在这里,截取
SearchManager。建议\u URI\u PATH\u查询
并返回光标

public class SearchSuggestionProvider extends SearchRecentSuggestionsProvider {

    private UriMatcher matcher;

    private static final int URI_MATCH_SUGGEST = 1;

    public SearchSuggestionProvider() {
        super();

        matcher = new UriMatcher(UriMatcher.NO_MATCH);

        // Add uri to return URI_MATCH_SUGGEST
        matcher.addURI(SearchSuggestionProvider.class.getName(), 
                         SearchManager.SUGGEST_URI_PATH_QUERY, URI_MATCH_SUGGEST);

        setupSuggestions(SearchSuggestionProvider.class.getName(), 
                                                           DATABASE_MODE_QUERIES);
    }

    @Override
    public Cursor query(Uri uri, String[] projection, String selection, 
                                      String[] selectionArgs, String sortOrder) {

        // special case for actual suggestions (from search manager)
        if (matcher.match(uri) == URI_MATCH_SUGGEST) {

            // File to use
            File f = new File("/path/to/file");

            Uri uriFile = Uri.fromFile(f);

            final String[] PROJECTION = new String[] {
                "_id", 
                "display1 AS " + SearchManager.SUGGEST_COLUMN_TEXT_1,                
                "query AS " + SearchManager.SUGGEST_COLUMN_QUERY,
                "'" + uriFile + "'" + " AS " + SearchManager.SUGGEST_COLUMN_ICON_1,
            };

            final Uri URI = Uri.parse("content://" + 
                        SearchSuggestionProvider.class.getName() + "/suggestions");

            // return cursor
            return getContext().getContentResolver().query(
                URI, 
                PROJECTION, 
                "display1 LIKE ?", 
                new String[] {selectionArgs[0] + "%"}, 
                "date DESC");          
        }

        // Let super method handle the query if the check fails
        return super.query(uri, projection, selection, selectionArgs, sortOrder);
    }
}

我有一个类似的问题,无法使其他解决方案工作。最后,我用一个包含查询()中所需数据的新游标替换了游标


我有一个类似的问题,无法使其他解决方案工作。最后,我用一个包含查询()中所需数据的新游标替换了游标



你尝试过什么文件URI结构?我尝试过“file://{file_path}”、“file://{file_path}”以及{file_path}。我想知道你是否需要实现自己的
ContentProvider
来公开应用程序
数据
文件夹中的图像。你试过了吗?值得一试,特别是因为它不太复杂。或者,您是否尝试过从更公共的位置通过
文件://
方案加载图像?例如,SD卡的根?我很想试试,但我刚刚将所有设备更新为Android 4.4,出于某种原因,这意味着我无法再搜索已安装应用程序的内容。以前有效的一切,包括谷歌游戏,不再出现在谷歌搜索的“平板搜索”/“手机搜索”部分。奇怪的是…刚刚就这个问题提出了一个问题:你尝试过什么文件URI结构?我尝试过“file://{file_path}”、“file://{file_path}”以及{file_path}。我想知道你是否需要实现你自己的
ContentProvider
来公开你应用程序
data
文件夹中的图像。你试过了吗?值得一试,特别是因为它不太复杂。或者,您是否尝试过从更公共的位置通过
文件://
方案加载图像?例如,SD卡的根?我很想试试,但我刚刚将所有设备更新为Android 4.4,出于某种原因,这意味着我无法再搜索已安装应用程序的内容。以前有效的一切,包括谷歌游戏,不再出现在谷歌搜索的“平板搜索”/“手机搜索”部分。奇怪的是,我刚才也提出了一个关于这个问题的问题:我原来的问题可能有点含糊不清。如果是这样的话,我很抱歉。下面是我目前所取得成果的屏幕截图:结果来自我在重写的
query(…)
方法中查询的SQLite数据库。我希望每个结果都有一个封面图片显示在旁边。如果我没有弄错的话,这个解决方案似乎对只显示一张图片很有用。@MichellBak首先,这个应用看起来很棒,做得不错!我(有点)明白你想做什么。老实说,我不知道这个问题的答案。工作方法:向表中添加另一列以存储图像
Uri
。向
投影
数组中添加另一项:
iconuri AS“+SearchManager。建议列图标1
。非常感谢!如果可能的话,我会试一试。除了创建一个内容提供商并看看是否有效之外,人们似乎没有任何其他建议,所以我将奖励你奖金,因为奖金即将到期,暂时不回答这个问题。@MichellBak不,谢谢你的奖金,尽管我帮不了什么忙。我将在下个周末再次尝试并发回