2012-04-18 21 views
18

Tengo problemas para configurar la vista de búsqueda en la barra de acciones.SearchInfo siempre saliendo nulo

Seguí el sitio del desarrollador, pero no funciona. Me da la sensación de que me estoy perdiendo algo.

Cuando ejecuto mi código, siempre muestra "no se pudo obtener información de búsqueda" (MainActivity.setupSearchView()).

MainActivity.java

// package... 
// imports... 
public class MainActivity extends Activity { 
    private static String tag = "Main Activity"; 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 
    } 
    @Override 
    public boolean onCreateOptionsMenu(Menu menu) { 
     MenuInflater mi = getMenuInflater(); 
     mi.inflate(R.menu.search_view, menu); 
     setupSearchView(menu); 
     return true; 
    } 
    private void setupSearchView(Menu menu) { 
     SearchManager sm = (SearchManager) getSystemService(Context.SEARCH_SERVICE); 
     SearchableInfo si = sm.getSearchableInfo(getComponentName()); 
     if (si == null) { 
      Log.wtf(tag, "failed to get searchable info"); 
      return; 
     } 
     SearchView sv = (SearchView) menu.findItem(R.id.menu_search).getActionView(); 
     sv.setSearchableInfo(si); 
     // Do not iconify the widget; expand it by default 
     sv.setIconifiedByDefault(false); 
    } 
} 

SearchResultsActivity.java

// package... 
// imports... 
public class SearchResultsActivity extends ListActivity { 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     final Intent queryIntent = getIntent(); 
     doSearchQuery(queryIntent); 
    } 
    @Override 
    public void onNewIntent(final Intent newIntent) { 
     super.onNewIntent(newIntent); 
     final Intent queryIntent = getIntent(); 
     doSearchQuery(queryIntent); 
    } 
} 

searchable.xml

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

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?> 
<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
    package="kpaek.examples" 
    android:versionCode="1" 
    android:versionName="1.0" > 
    <uses-sdk android:minSdkVersion="15" /> 
    <application 
     android:icon="@drawable/ic_launcher" 
     android:label="@string/app_name" > 
     <activity 
      android:name=".search.MainActivity" 
      android:label="@string/app_name" > 
      <intent-filter> 
       <action android:name="android.intent.action.MAIN" /> 

       <category android:name="android.intent.category.LAUNCHER" /> 
      </intent-filter> 
     </activity> 
     <activity 
      android:name=".SearchResultsActivity"> 
      <intent-filter> 
       <action android:name="android.intent.action.SEARCH" /> 
      </intent-filter> 
      <meta-data 
       android:name="android.app.searchable" 
       android:resource="@xml/searchable" /> 
     </activity> 
    </application> 
</manifest> 

Respuesta

38

La clave que encontré es que searchable.xml debe no contener cadenas literales, solo recursos. Perdí cerca de medio día en eso, ya que causa que getSearchableInfo falle silenciosamente.

+0

¡Gracias! Ahorras medio día para mí :) – HighFlyer

+0

¡Guau! Ese es un error muy malvado. Informé aquí: https://code.google.com/p/android/issues/detail?id=37517 – Rodja

+0

hombre - ¡gracias por esa información! – mAx

3

Desde el developersite:

Una configuración de búsqueda define cómo la SearchView comporta y es definido en un archivo res/xml/searchable.xml. Como mínimo, una configuración de búsqueda debe contener un atributo android: label que tenga el mismo valor que el atributo android: label del elemento en su manifiesto de Android.

Como un ejemplo, que muestran:

<searchable xmlns:android="http://schemas.android.com/apk/res/android" 
     android:label="@string/app_name" 
     android:hint="@string/search_hint" /> 

nombre_apl es, como en el manifiesto, la etiqueta de la actividad. Sin embargo, en su búsqueda, la etiqueta se refiere a search_label. Funciona quizás si app_name y search_label son iguales, pero eso me parece frágil.

11

Esto me mató por un día - Pensé que era relacionado con ActionBarSherlock, pero no funciona bien con eso.

El problema era que estaba intentando cortocircuitar la muestra. Al menos una de sus actividades - la persona que está haciendo la búsqueda de es suficiente - debe tener esta intención filtro en ella en el manifiesto:

<intent-filter> 
    <action android:name="android.intent.action.SEARCH" /> 
</intent-filter> 

Si no, entonces searchManager.getSearchableInfo(getComponentName()) siempre devuelve un valor nulo, y la configuración de su es ignorado

19

En mi caso el uso de etiquetas personalizadas en res/menu/mymenu.xml trabajó para mí:

app:showAsAction="ifRoom|collapseActionView" 
app:actionViewClass="android.support.v7.widget.SearchView" 

No utilice:

android:showAsAction="ifRoom|collapseActionView" 
android:actionViewClass="android.support.v7.widget.SearchView" 
+1

Me funcionó. ¡Muchas gracias! –

+0

@mahesh ¡Esto también funcionó para mí! – Tony

17

he encontrado que la intención-filtro y los elementos de metadatos deben estar incluido en el elemento de actividad de manifiesto a partir del cual se inicia la búsqueda (MainActivity tiene un SearchView) para el método getSearchableInfo (getComponentName()) para devolver la configuración correcta y no nula.

<activity 
    android:name=".MainActivity" 
    android:label="@string/app_name"> 
    <intent-filter> 
     <action android:name="android.intent.action.MAIN" /> 
     <category android:name="android.intent.category.LAUNCHER" /> 
    </intent-filter> 

    <intent-filter> 
     <action android:name="android.intent.action.SEARCH" /> 
    </intent-filter> 

    <meta-data 
     android:name="android.app.searchable" 
     android:resource="@xml/searchable" /> 
</activity> 

Me pregunto si en vez (y la solución que voy por ahora) uno debe dejar la intención y meta-datos en la declaración de la actividad de los resultados y cambiar el argumento para getSearchableInfo() de la siguiente manera:

<activity android:name=".SearchResultsActivity"> 
    <intent-filter> 
     <action android:name="android.intent.action.SEARCH" /> 
    </intent-filter> 

    <meta-data 
     android:name="android.app.searchable" 
     android:resource="@xml/searchable" /> 
</activity> 

Y los cambios en MainActivity (tenga en cuenta la instrucción de asignación para searchableInfo):

@Override 
public boolean onCreateOptionsMenu(Menu menu) { 
    getMenuInflater().inflate(R.menu.menu_search, menu); 
    SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE); 
    SearchView mySearchView = (SearchView) menu.findItem(R.id.action_search).getActionView(); 
    SearchableInfo searchableInfo = searchManager.getSearchableInfo(new ComponentName(getApplicationContext(), SearchResultsActivity.class)); 
    mySearchView.setSearchableInfo(searchableInfo); 

    return true; 
} 
+1

Gracias, hombre ... la única solución que me ha funcionado es el nuevo componentName uno ..... no sé por qué, pero todos los demás no funcionaron – Gaurav

+0

¡Oh, guau! ¡La única solución que funcionó! ¡Se merece más votos a favor! – camelCaseCoder

2

me encontré con este tema, pero el consejo anterior no se ha solucionado el problema. En su lugar, resultó ser la configuración predeterminada de la categoría en SearchResultActivity. Por ejemplo los siguientes descansos:

<activity android:name=".SearchResultActivity" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme"> 
    <intent-filter> 
      <action android:name="android.intent.action.SEARCH" /> 
      <category android:name="android.intent.category.DEFAULT" /> 
    </intent-filter> 
    <meta-data 
      android:name="android.app.searchable" 
      android:resource="@xml/searchable" /> 
</activity> 

Extracción android.intent.category.DEFAULT resuelve este problema .:

<activity android:name=".SearchResultActivity" 
     android:label="@string/app_name" 
     android:theme="@style/AppTheme"> 
    <intent-filter> 
      <action android:name="android.intent.action.SEARCH" /> 
    </intent-filter> 
    <meta-data 
      android:name="android.app.searchable" 
      android:resource="@xml/searchable" /> 
</activity> 

también las respuestas anteriores a esta pregunta tiene un error. MainActivity se debe definir con android.app.default_searchable. android.app.searchable es solo para su SearchResultsActivity.

<activity 
    android:name=".MainActivity" 
    android:label="@string/app_name"> 
    <!-- other stuff--> 
    <meta-data android:name="android.app.default_searchable" 
      android:value=".SearchResultsActivity" /> 
</activity> 

En conclusión, el SearchManager es un componente frágil propenso a fallos silenciosos cuando el AndroidManifest.xml no es perfecto.

1

Perdí 8 horas completas en este caso porque revisé todas las soluciones anteriores, pero me faltaba una cosa.

En mi manifiesto de Android:

<meta-data 
       android:name="android.app.searchable" 
       android:value="@xml/searchable" /> 

En caso de ha sido:

<meta-data 
       android:name="android.app.searchable" 
       android:resource="@xml/searchable" /> 

Para mí estaba fallando en silencio. Lo mejor que puedes hacer al principio es copiar y pegar los ejemplos. Solo asegúrate de que todos tus atributos sean exactamente iguales.

Cuestiones relacionadas