Android:将搜索查询返回到当前活动

时间:2011-02-23 17:05:26

标签: android search

我按照http://developer.android.com/guide/topics/search/search-dialog.html中描述的步骤在我的记事本应用程序中实现了搜索功能。

我的问题是,当我完成搜索时,新的活动会打开捕获我的搜索查询。但我真正想要的是,查询返回到当前活动而不是开始新的活动。

这可能吗?

更新:

的AndroidManifest.xml


<activity android:name="MyNotepad"
                  android:label="@string/app_name">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
                <action android:name="android.intent.action.SEARCH"></action>
            </intent-filter>
            <meta-data android:resource="@xml/searchable" android:name="android.app.searchable"></meta-data>
        </activity><activity android:name="Preferences" android:label="Preferences" >
</activity>

searchable.xml


<?xml version="1.0" encoding="utf-8"?>
<searchable
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:label="@string/app_name"
  android:hint="@string/search_hint">
</searchable>

JAVA代码


@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main_pad);
    Intent intent = getIntent();
    if (Intent.ACTION_SEARCH.equals(intent.getAction())) {
        String query = intent.getStringExtra(SearchManager.QUERY);
        Toast.makeText(getApplicationContext(), query, Toast.LENGTH_LONG).show();
    }
}


@Override
public boolean onOptionsItemSelected(MenuItem item)
{
    switch(item.getItemId())
    {
        case R.id.menuItemSearch:
            startSearch("", false, null, false);
    break;
    }
    return true;
}

即使我使用手机上的搜索按钮,它也不起作用。因此我认为问题出在AndroidManifest.xml

9 个答案:

答案 0 :(得分:60)

在您的Application Manifest中,您需要将当前活动定义为可搜索的活动。

<activity android:name="BrowseItems" android:label="@string/browseitems"
            android:launchMode="singleTop">
            <intent-filter>
                <action android:name="android.intent.action.SEARCH" />
            </intent-filter>
            <meta-data android:name="android.app.searchable"
                android:resource="@xml/itemsearchable" />
</activity>

然后使用以下代码,该代码来自http://developer.android.com/guide/topics/search/search-dialog.html#LifeCycle

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.search);
    handleIntent(getIntent());
}

@Override
protected void onNewIntent(Intent intent) {
    setIntent(intent);
    handleIntent(intent);
}

private void handleIntent(Intent intent) {
    if (Intent.ACTION_SEARCH.equals(intent.getAction())) {
      String query = intent.getStringExtra(SearchManager.QUERY);
      // Do work using string
    }
}

然后您可以使用该字符串重新加载您的活动,如果它是一个列表活动,您可以调用您用于加载数据的代码并使用该字符串。

答案 1 :(得分:18)

在您的可搜索活动中添加到AndroidManifest.xml:

android:launchMode="singleTop" 

所以,您的AndroidManifest.xml看起来像:

<activity android:name="MyNotepad"
              android:label="@string/app_name"
              android:launchMode="singleTop">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
            <action android:name="android.intent.action.SEARCH"></action>
        </intent-filter>
        <meta-data android:resource="@xml/searchable" android:name="android.app.searchable"></meta-data>
    </activity><activity android:name="Preferences" android:label="Preferences" >

原因:

来自this post

活动启动模式有四个有效值:

“标准” “singleTop” “singleTask” “singleInstance”

'标准'是默认值。这四个值分为两组:

'standard'和'singleTop'可以实例化多个活动实例,并且实例将保留在同一任务中。 对于“singleTask”或“singleInstance”,活动类使用单例模式,该实例将是新任务的根活动。让我们检查每个值: “标准”:

可以实例化活动类的多个实例,并且可以将多个实例添加到同一任务或不同任务。这是大多数活动的共同模式。

“singleTop”:

与'standard'的区别在于,如果活动实例已存在于当前任务的顶部且系统路由意图此活动,则不会创建新实例,因为它将触发onNewIntent()方法而不是创建新对象。

答案 2 :(得分:5)

我只是用它: -

searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
        @Override
        public boolean onQueryTextSubmit(String s) {
            //on submit
            return false;
        }

        @Override
        public boolean onQueryTextChange(String s) {
            //get all text changes
            return false;
        }
});

当您必须搜索列表视图并且必须过滤掉项目时,最好使用此选项。我从不使用清单文件来实现搜索功能。这两种方法完成所有工作。

答案 3 :(得分:4)

我也遇到了同样的问题,然后我编写了这段代码,它解决了我的问题。

在您的活动

中实施此功能
**implements SearchView.OnQueryTextListener, SearchView.OnCloseListener**

在课程中添加此功能:

private void setupSearchView()
        {

            searchView.setIconifiedByDefault(true);

            SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
            if (searchManager != null)
                {
                    List<SearchableInfo> searchables = searchManager.getSearchablesInGlobalSearch();

                    // Try to use the "applications" global search provider
                    SearchableInfo info = searchManager.getSearchableInfo(getComponentName());
                    for (SearchableInfo inf : searchables)
                        {
                            if (inf.getSuggestAuthority() != null && inf.getSuggestAuthority().startsWith("applications"))
                                {
                                    info = inf;
                                }
                        }
                    searchView.setSearchableInfo(info);
                }

            searchView.setOnQueryTextListener(this);
            searchView.setOnCloseListener(this);
        }

在onCreateOptionsMenu(菜单菜单)中调用该函数

@Override
    public boolean onCreateOptionsMenu(Menu menu)
        {
            MenuInflater inflater = getMenuInflater();
            inflater.inflate(R.menu.menu, menu);
            //restoreActionBar();
            // Associate searchable configuration with the SearchView
            //SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
            searchView = (SearchView) menu.findItem(R.id.action_search).getActionView();
            //searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
            setupSearchView();
            return super.onCreateOptionsMenu(menu);
        }

这将完全解决您的问题..

快乐编码!!

答案 4 :(得分:2)

简言之:

  1. android:launchMode="singleTop"添加到searchable activity
  2. 中的AndroidManifest.xml定义
  3. onNewIntent中实施searchable activity并在那里处理搜索。

答案 5 :(得分:1)

我跟着Lachlan's clue“您可以使用字符串重新加载您的活动”,最后解决了这个问题。所以请先阅读Lachlan的帖子,然后按照以下3个步骤“重新加载你的活动”:

  1. 在ApplicationContext中保存查询字符串。
  2. 完成新打开的搜索活动。
  3. 覆盖OnResume,获取刚保存的查询字符串,然后刷新列表。
  4. 列表活动中的代码:

    private void handleIntent(Intent intent) {
        if (Intent.ACTION_SEARCH.equals(intent.getAction())) {
            String searchText = intent.getStringExtra(SearchManager.QUERY);
            ((MyApp)this.getApplicationContext()).setSearchText(searchText);
            this.finish();
        }
    }
    
    protected void onResume() {
        super.onResume();
    
        String searchText = ((MyApp)this.getApplicationContext()).getSearchText();
        //refresh your list here...
    }
    

    MyApp课程:(最初的想法来自:Android: How to declare global variables?

    public class MyApp extends Application {
    
        private String mSearchText;
    
        public String getSearchText() {
            return mSearchText;
        }
    
        public void setSearchText(String searchText) {
            this.mSearchText = searchText;
        }
    }
    

    不要忘记在Manifest文件中将属性android:name=".MyApp"添加到您的应用程序中。祝你好运!

答案 6 :(得分:1)

清单文件中的

,添加:

android:launchMode="singleTop"

到您的搜索活动。然后,让您的搜索活动实现 SearchView.OnSuggestionListener 最后:

mSearchView.setOnSuggestListener(this)

通过这种方式,您可以处理建议点击事件,而无需创建搜索活动的新实例。

答案 7 :(得分:0)

如果设置了searchView上的SearchView.OnSuggestionListener,并且重写的方法返回true(overriding the default behavior),则不会显示新活动。您可以在onCreateOptionsMenu()实现中执行此操作,如下所示:

    searchView.setOnSuggestionListener(new SearchView.OnSuggestionListener() {
        @Override
        public boolean onSuggestionSelect(int position) {
            return true;
        }

        @Override
        public boolean onSuggestionClick(int position) {
            CursorAdapter selectedView = searchView.getSuggestionsAdapter();
            Cursor cursor = (Cursor) selectedView.getItem(position);
            int index = cursor.getColumnIndexOrThrow(SearchManager.SUGGEST_COLUMN_TEXT_1);
            searchView.setQuery(cursor.getString(index), true);
            return true;
        }
    });

无需将活动强制为singleTop或其他黑客。

答案 8 :(得分:-1)

添加

<application>

  <meta-data 
     android:name="android.app.default_searchable"
     android:value="#Activity_Name" />

   <!-- All your activities, service, etc. -->

</application>

在你的android_manifest.xml文件中,其中#Activity_Name是处理搜索的活动的名称。