Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to add a SearchWidget to the ActionBar?

I'm trying to add a Search-ActionView to my application (as explained here http://developer.android.com/guide/topics/search/search-dialog.html#UsingSearchWidget). Unfortunately I keep getting a NullPointerException and I'm having a hard time detecting what's actually going wrong.

I created a searchable config and a searchable activity as shown on the android page. My menu .xml file looks like this:

<menu xmlns:android="http://schemas.android.com/apk/res/android" >     ...     <item         android:id="@+id/menu_item_search"         android:actionViewClass="android.widget.SearchView"         android:icon="@drawable/icon_search"         android:showAsAction="always"         android:title="@string/action_bar_button_search">     </item>  </menu> 

This is the method where the Exception is thrown:

public boolean onCreateOptionsMenu( Menu menu ) {     MenuInflater menuInflater = getMenuInflater();     menuInflater.inflate( R.menu.action_bar, menu );      SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);     SearchView searchView = (SearchView) menu.findItem(R.id.menu_item_search).getActionView();      // NullPointerException thrown here; searchView is null.     searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));     searchView.setIconifiedByDefault(false);      return super.onCreateOptionsMenu( menu ); } 

Complete stack trace:

FATAL EXCEPTION: main java.lang.NullPointerException at com.example.activities.Test.onCreateOptionsMenu(Test.java:41) at android.app.Activity.onCreatePanelMenu(Activity.java:2444) at com.android.internal.policy.impl.PhoneWindow.preparePanel(PhoneWindow.java:408) at com.android.internal.policy.impl.PhoneWindow.invalidatePanelMenu(PhoneWindow.java:759) at com.android.internal.policy.impl.PhoneWindow$1.run(PhoneWindow.java:2997) at android.os.Handler.handleCallback(Handler.java:605) at android.os.Handler.dispatchMessage(Handler.java:92) at android.os.Looper.loop(Looper.java:137) at android.app.ActivityThread.main(ActivityThread.java:4507) at java.lang.reflect.Method.invokeNative(Native Method) at java.lang.reflect.Method.invoke(Method.java:511) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:790) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:557) at dalvik.system.NativeStart.main(Native Method) 
like image 978
Taig Avatar asked Jun 30 '12 17:06

Taig


People also ask

What is a search view in Android Studio?

↳ android.widget.SearchView. A widget that provides a user interface for the user to enter a search query and submit a request to a search provider. Shows a list of query suggestions or results, if available, and allows the user to pick a suggestion or result to launch into.


2 Answers

Since this question is looked up quite often and I stumbled across the very same problem again and again here is a little follow up that keeps track of all necessary steps to create a SearchWidget.

There is one tricky part about the SearchWidget though: If you use hardcoded Strings in the searchable.xml instead of resources the app will crash with a confusing error message. This took me way too many hours of my life...

  1. Create an Activity to handle the search results

    public class Search extends Activity {} 
  2. Add a file "searchable.xml" to your res/xml directory (use resources for hint & label!)

    <searchable xmlns:android="http://schemas.android.com/apk/res/android"     android:hint="@string/search_hint"     android:includeInGlobalSearch="false"     android:label="@string/search_label"     android:searchSettingsDescription="@string/search_global_description" /> 
  3. Create the proper menu item "main.xml" in you res/menu directory

    <?xml version="1.0" encoding="utf-8"?> <menu xmlns:android="http://schemas.android.com/apk/res/android" >      <item        android:id="@+id/options_menu_main_search"        android:actionViewClass="android.widget.SearchView"        android:icon="@drawable/icon_magnifier"        android:showAsAction="always"        android:title="Search"/>  </menu> 
  4. Update your Manifest.xml: Add the search activity and specify which activities may receive search intents. Adding <meta-data android:name="android.app.default_searchable" android:value=".app.Search" /> to an activity node makes it searchable. Adding it to the application node makes all activities searchable.

    <?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android">     <application>         <meta-data             android:name="android.app.default_searchable"             android:value=".app.Search" />          <activity android:name=".activities.Search" >             <intent-filter>             <action android:name="android.intent.action.SEARCH" />         </intent-filter>          <meta-data             android:name="android.app.searchable"             android:resource="@xml/searchable" />     </activity> </application> 

  5. Add the SearchManager to your ActionView in every activity that should provide the SearchWidget

    public class Activity extends android.app.Activity {     @Override     public boolean onCreateOptionsMenu( Menu menu )     {         getMenuInflater().inflate( R.menu.main, menu );          // Add SearchWidget.         SearchManager searchManager = (SearchManager) getSystemService( Context.SEARCH_SERVICE );         SearchView searchView = (SearchView) menu.findItem( R.id.options_menu_main_search ).getActionView();          searchView.setSearchableInfo( searchManager.getSearchableInfo( getComponentName() ) );          return super.onCreateOptionsMenu( menu );     } } 
like image 199
Taig Avatar answered Oct 30 '22 16:10

Taig


If you are using targeting Android 2.x and using android.support.v7.widget.SearchView check that your menu.xml looks like this (note the yourapp namespace)

<?xml version="1.0" encoding="utf-8"?> <menu xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:yourapp="http://schemas.android.com/apk/res-auto">     <item         android:id="@+id/search"         android:title="@string/search"         android:icon="@drawable/ic_search"         yourapp:showAsAction="always"         yourapp:actionViewClass="android.support.v7.widget.SearchView" /> </menu> 

And in the Activity where you inflate the menu use:

android.support.v7.widget.SearchView searchView = (android.support.v7.widget.SearchView)  MenuItemCompat.getActionView(menu.findItem(R.id.search)); 
like image 38
peceps Avatar answered Oct 30 '22 14:10

peceps