Problem passing a Bundle with onSearchRequested
Asked Answered
W

4

2

I'm actually trying to use the built-in search interface of Android, but I have some issues when I try to pass data with the search query.

Here is a brief explanation : I have an object in a first Activity (FirstActivity) called "Category" which implements Serializable (I already pass it successfuly between Activities) and I want to perform a search related to that category, and display the results in a second Activity (SecondActivity).

So, in FirstActivity I override the onSearchRequest method :

@Override
public boolean onSearchRequested() {
    Bundle appData = new Bundle();
    appData.putSerializable("category", _currentCategory);
    Log.d(Utils.LOG_TAG, "Bundle : "+appData.keySet());
    startSearch(null, false, appData, false);
    return true;
}

And in SecondActivity, I try to get this Bundle :

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

private void handleIntent(Intent intent){
    Bundle appData = intent.getBundleExtra(SearchManager.APP_DATA);
    if(appData == null) Log.d(Utils.LOG_TAG, "appData == null");
    Log.d(Utils.LOG_TAG, "Extras : "+intent.getExtras().keySet());
}

Problem is that appData seems to be equals to null everytime. Here is the logcat output :

Bundle : [category]
appData == null
Extras : [query, user_query]

I tried to add some other objects into the Bundle (Booleans, etc...) but it doesn't change anything at all and I keep having a null appData.

Wiedmann answered 16/6, 2011 at 13:21 Comment(3)
Please add your startSearch() method. The problem may be in this method where you are constructing the Intent that you're using to launch your second activity.Gambill
startSearch() is an existing method from Activity : developer.android.com/reference/android/app/…. From what I read, it should handle that stuff.Wiedmann
I found the best way to do it is to override StartActivity. See: enjoysmile.com/blog/28/…Papilionaceous
H
1

If you're using SearchView, it will not send your appData. Instead, consider using OnQueryTextListener. For example:

...
@Override
public boolean onCreateOptionsMenu(Menu menu) {
    MenuInflater inflater = getMenuInflater();
    inflater.inflate(R.menu.your-menu-id, menu);

    /*
     * Get the SearchView and set the searchable configuration.
     */
    SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
    SearchView searchView = (SearchView) menu.findItem(R.id.your-search-menuitem-id)
            .getActionView();
    searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
    /*
     * Set query text listener here.
     */
    searchView.setOnQueryTextListener(mSearchViewOnQueryTextListener);

    return true;
}// onCreateOptionsMenu()

...
private final SearchView.OnQueryTextListener mSearchViewOnQueryTextListener = new SearchView.OnQueryTextListener() {

    @Override
    public boolean onQueryTextSubmit(String query) {
        /*
         * You don't need to deal with "appData", because you already
         * have the search query here.
         */

        // Tell the SearchView that we handled the query.
        return true;
    }// onQueryTextSubmit()

    @Override
    public boolean onQueryTextChange(String newText) {
        // TODO Auto-generated method stub
        return false;
    }// onQueryTextChange()
};// mSearchViewOnQueryTextListener

Note: You still need to keep the old way (using appData inside onSearchRequested()). In your onCreate(), if the extra for SearchManager.APP_DATA is null, that means you already handled the search query in the listener.

Conclusion:

  • If the SearchView is inactive, and you invoke it via onSearchRequested(), this will happen: onSearchRequested() >> onCreate() (ACTION_SEARCH contains SearchManager.APP_DATA).
  • If the SearchView is active, the user types and submits search, this will happen: SearchView.OnQueryTextListener.onQueryTextSubmit() >> onCreate() (ACTION_SEARCH without SearchManager.APP_DATA).
Huda answered 29/11, 2012 at 2:15 Comment(0)
T
3

I had problems figuring this out as well, and the examples I found didn't really help. A lot of them suggested overriding onSearchRequested(), but that actually doesn't work for SearchWidget. I ended up using the following (from danada) as a solution, since it seemed much simpler for me than setting up the OnQueryTextListener. I just overrode startActivity (in the first, search Activity) like so:

@Override
public void startActivity(Intent intent) {      
    //check if search intent
    if(Intent.ACTION_SEARCH.equals(intent.getAction())) {
        intent.putExtra("KEY", "VALUE");
    }

    super.startActivity(intent);
}

Then in the second, searchable Activity, I pulled out the info like so (called from onCreate() or from overriding onNewIntent() (if using singleTop)):

private void handleIntent(Intent intent){
    if(Intent.ACTION_SEARCH.equals(intent.getAction())){
    mSearchedQuery = intent.getStringExtra(SearchManager.QUERY);
    mExtraData = intent.getStringExtra("KEY");
}

Simple, and worked like a charm! Check the link to the article above if you would like a little more explanation about it.

Trinee answered 14/9, 2013 at 19:10 Comment(0)
H
1

If you're using SearchView, it will not send your appData. Instead, consider using OnQueryTextListener. For example:

...
@Override
public boolean onCreateOptionsMenu(Menu menu) {
    MenuInflater inflater = getMenuInflater();
    inflater.inflate(R.menu.your-menu-id, menu);

    /*
     * Get the SearchView and set the searchable configuration.
     */
    SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
    SearchView searchView = (SearchView) menu.findItem(R.id.your-search-menuitem-id)
            .getActionView();
    searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
    /*
     * Set query text listener here.
     */
    searchView.setOnQueryTextListener(mSearchViewOnQueryTextListener);

    return true;
}// onCreateOptionsMenu()

...
private final SearchView.OnQueryTextListener mSearchViewOnQueryTextListener = new SearchView.OnQueryTextListener() {

    @Override
    public boolean onQueryTextSubmit(String query) {
        /*
         * You don't need to deal with "appData", because you already
         * have the search query here.
         */

        // Tell the SearchView that we handled the query.
        return true;
    }// onQueryTextSubmit()

    @Override
    public boolean onQueryTextChange(String newText) {
        // TODO Auto-generated method stub
        return false;
    }// onQueryTextChange()
};// mSearchViewOnQueryTextListener

Note: You still need to keep the old way (using appData inside onSearchRequested()). In your onCreate(), if the extra for SearchManager.APP_DATA is null, that means you already handled the search query in the listener.

Conclusion:

  • If the SearchView is inactive, and you invoke it via onSearchRequested(), this will happen: onSearchRequested() >> onCreate() (ACTION_SEARCH contains SearchManager.APP_DATA).
  • If the SearchView is active, the user types and submits search, this will happen: SearchView.OnQueryTextListener.onQueryTextSubmit() >> onCreate() (ACTION_SEARCH without SearchManager.APP_DATA).
Huda answered 29/11, 2012 at 2:15 Comment(0)
T
0

While putting data and retrieving it you are using two different keys. while putting you are using "category" and while retrieving you are using SearchManager.APP_DATA instead of using "category"

Try with

Bundle appData = intent.getBundleExtra("category");

Thanks Deepak

Thence answered 16/6, 2011 at 13:26 Comment(1)
Thanks for your answer but unfortunately, it doesn't change anything. As I wrote earlier, intent.getExtras().keySet() returns [query, user_query] so, no trace of my Bundle.Wiedmann
C
0

In your example, you are asking for the keyset on the original intent object, and not the Bundle containing your appData. Here is an example that should work:

private void handleIntent(Intent intent){
    final Bundle appData = intent.getBundleExtra(SearchManager.APP_DATA);

    for (String key : appData.keySet()) {
        Log.d(TAG, "key="+appData.getString(key));
    }
}
Cullin answered 4/2, 2012 at 0:48 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.