I'm using SearchView to filter my ListView data. I managed to implement it, but I can't get this code to work.
searchView.setSubmitButtonEnabled(false);
This is my full code:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.add_group_menu, menu);
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
MenuItem searchMenuItem = menu.findItem(R.id.search);
SearchView searchView = (SearchView) searchMenuItem.getActionView();
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
searchView.setQueryHint(getResources().getString(R.string.hint_type_something));
searchView.setSubmitButtonEnabled(false);
int searchPlateId = searchView.getContext().getResources().getIdentifier("android:id/search_plate", null, null);
View searchPlate = searchView.findViewById(searchPlateId);
if (searchPlate != null) {
int searchTextId = searchPlate.getContext().getResources().getIdentifier("android:id/search_src_text", null, null);
TextView searchText = (TextView) searchPlate.findViewById(searchTextId);
if (searchText != null) {
searchText.setTextColor(Color.WHITE);
searchText.setHintTextColor(getResources().getColor(R.color.white));
}
}
searchView.setSubmitButtonEnabled(true);
searchView.setOnQueryTextListener(this);
return true;
}
Image:
If anyone have a clue in How to I hide the submit button beside searchview?
Remove this line of code from your code.
//remove this line
searchView.setSubmitButtonEnabled(true);
Related
Today I decide to translate my android app from Java to Kotlin ! :) But I was very surprise when I type this :
val searchItem = menu.findItem(R.id.action_search)
val searchView = MenuItemCompat.getActionView(searchItem) as SearchView
And Android Studio told me : " 'getActionView(MenuItem!):View!' is deprecated. Deprecated in Java "
So before to ask you the solution I ask to Google what is the solution and I believed I find the solution : "Use getActionView() directly."
So I modified my code like this :
val searchView = MenuItemCompat.getActionView() as SearchView
But getActionView() is still crossed so I don't understand at all...
I will be very happy if you can help me :) Thank you !
The Javadoc says:
Use getActionView() directly.
Hence, what you should do is:
val searchView = searchItem.getActionView() as SearchView
As suggested by egor, you can do like this
getMenuInflater().inflate(R.menu.menu_items, menu);
MenuItem menuItem = menu.findItem(R.id.action_search);
SearchView searchView = (SearchView) menuItem.getActionView();
search(searchView);
return true;
You can use the same as provided on android developer website
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the options menu from XML
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.options_menu, menu);
// Get the SearchView and set the searchable configuration
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
SearchView searchView = (SearchView) menu.findItem(R.id.menu_search).getActionView();
// Assumes current activity is the searchable activity
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
searchView.setIconifiedByDefault(false); // Do not iconify the widget; expand it by default
return true;
}
Use actionView directly in Kotlin, like this:
override fun onCreateOptionsMenu(menu: Menu?): Boolean {
menuInflater.inflate(R.menu.actions, menu)
val searchItem = menu?.findItem(R.id.action_search)
val searchView = searchItem?.actionView as SearchView
searchView.animate()
// TODO: Configure the search info and add any event listeners...
return super.onCreateOptionsMenu(menu)
}
Declaration of myAdapter:
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
myAdapter = new SimpleCursorAdapter(MainActivity.this, android.R.layout.simple_spinner_dropdown_item, null, from, to, CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);
}
Usage:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// adds item to action bar
getMenuInflater().inflate(R.menu.search_main, menu);
// Get Search item from action bar and Get Search service
MenuItem searchItem = menu.findItem(R.id.action_search);
SearchManager searchManager = (SearchManager) MainActivity.this.getSystemService(Context.SEARCH_SERVICE);
if (searchItem != null) {
searchView = (SearchView) searchItem.getActionView();
}
if (searchView != null) {
searchView.setSearchableInfo(searchManager.getSearchableInfo(MainActivity.this.getComponentName()));
searchView.setIconified(false);
searchView.setSuggestionsAdapter(myAdapter);
// Getting selected (clicked) item suggestion
searchView.setOnSuggestionListener(new SearchView.OnSuggestionListener() {
#Override
public boolean onSuggestionClick(int position) {
// Add clicked text to search box
CursorAdapter ca = searchView.getSuggestionsAdapter();
Cursor cursor = ca.getCursor();
cursor.moveToPosition(position);
searchView.setQuery(cursor.getString(cursor.getColumnIndex("fishName")),false);
return true;
}
The lines that gets me the error:
searchView.setSuggestionsAdapter(myAdapter);
And:
CursorAdapter ca = searchView.getSuggestionsAdapter();
Errors:
Error:(218, 46) error: incompatible types: SimpleCursorAdapter cannot be converted to CursorAdapter
Error:(225, 72) error: incompatible types: android.support.v4.widget.CursorAdapter cannot be converted to android.widget.CursorAdapter
I'm trying to follow this tutorial.
I don't quite get why I'm getting this error. Can anyone help me shed a light?
Check your imports, CursorAdapter exists both in the regular and support libraries, so make it consistent inside all of your classes.
import android.widget.CursorAdapter;
import android.support.v4.widget.CursorAdapter;
So this I the code I use in the Activity that should get a search function:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.options_menu, menu);
// Associate searchable configuration with the SearchView
SearchManager searchManager =
(SearchManager) getSystemService(Context.SEARCH_SERVICE);
SearchView searchView =
(SearchView) menu.findItem(R.id.search).getActionView();
***searchView.setSearchableInfo(
searchManager.getSearchableInfo(getComponentName()));***
return true;
}
I got this code from the androidDeveloper site. The two lines that I made highlighted are the ones that are making trouble.
What am I doing wrong?
I found the solution in the first answer of this post, just in case someone else has the same problem!
Android - NullPointerException on SearchView in Action Bar
I'm trying to use the SearchView Support v4 version with action bar sherlock.
So i have my search button in the action bar -> when i touch it the keyboard show up and the searchBar too.
My problem is that i need to use the listeners onQueryTextSubmit and onQueryTextChange but they are never fired. I need to use the searh query string and do custom stuff with it.
Here is the full activity.java
public class ActivityMain extends SherlockFragmentActivity implements OnQueryTextListener, DialogFragmentListener {
/**
* PRIVATE ATTRIBUTES
*/
private static final String TAG = "ActivityMain";
private ViewPager _viewPager;
private TabsAdapter _tabsAdapter;
private DialogFiltre _dialogFiltre;
private String _searchCurrentQuery;
// data
private boolean _doubleBackToExitPressedOnce = false;
#Override
public boolean onPrepareOptionsMenu(Menu menu) {
menu.clear();
switch ((int) _viewPager.getCurrentItem()) {
case 0:
getSupportMenuInflater().inflate(R.menu.empty_menu, menu);
break;
case 1:
getSupportMenuInflater().inflate(R.menu.action_bar_menu, menu);
break;
case 2:
getSupportMenuInflater().inflate(R.menu.empty_menu, menu);
break;
}
return super.onPrepareOptionsMenu(menu);
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getSupportMenuInflater().inflate(R.menu.action_bar_menu, menu);
MenuItem searchItem = menu.findItem(R.id.search);
SearchView searchView = (SearchView) searchItem.getActionView();
searchView.setSubmitButtonEnabled(true);
searchView.setOnQueryTextListener(queryTextListener);
return true;
}
#Override
public boolean onQueryTextSubmit(String query) {
Log.i(TAG, "onQueryTextSubmit--");
onSearchClicked(query);
// hide keyboard
InputMethodManager inputManager = (InputMethodManager) this.getSystemService(Context.INPUT_METHOD_SERVICE);
inputManager.hideSoftInputFromWindow(this.getCurrentFocus().getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
return false;
}
#Override
public boolean onQueryTextChange(String newText) {
Log.d(TAG, "onQueryTextChange--");
_searchCurrentQuery = newText.toString();
EtablissementApplication._adapter.getFilter().filter(_searchCurrentQuery);
return true;
}
private void onSearchClicked(String query) {
Log.d(TAG, "onSearchClicked--");
_searchCurrentQuery = query.toString();
EtablissementApplication._adapter.getFilter().filter(_searchCurrentQuery);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
getSupportActionBar().setDisplayHomeAsUpEnabled(false);
break;
case R.id.search:
break;
case R.id.menu_filtre:
_dialogFiltre = DialogFiltre.newInstance(R.string.menu_filtre, this);
_dialogFiltre.setValidDialogListener(this);
_dialogFiltre.show(getSupportFragmentManager(), null);
break;
}
return super.onOptionsItemSelected(item);
}
You are trying to use a new SearchView instead of using the one created by the SupportMenuInflater.
You setting the listener to different SearchView that you see on the screen.
Also, every time onPrepareOptionsMenu is called, new SearchView is created, and thus it has no listeners set.
Try to do onPrepareOptionsMenu like this:
#Override
public boolean onPrepareOptionsMenu(Menu menu) {
menu.clear();
switch ((int) _viewPager.getCurrentItem()) {
case 0:
getSupportMenuInflater().inflate(R.menu.empty_menu, menu);
break;
case 1:
getSupportMenuInflater().inflate(R.menu.action_bar_menu, menu);
MenuItem searchItem = menu.findItem(R.id.search);
SearchView searchView = (SearchView) searchItem.getActionView();
searchView.setSubmitButtonEnabled(true);
searchView.setOnQueryTextListener(queryTextListener);
break;
case 2:
getSupportMenuInflater().inflate(R.menu.empty_menu, menu);
break;
}
return super.onPrepareOptionsMenu(menu);
}
And remove the overridden method
#Override
public boolean onCreateOptionsMenu(Menu menu) { }
Top result in Google so adding a new possible cause that just gave me a headache. Be mindful of which SearchView implementation you reference.
This did not work for me (compiles, does not crash, but listener does not work):
<!--actionbar.xml-->
...
<item android:id="#+id/search"
android:title="#string/action_search"
android:icon="#drawable/ic_search"
app:showAsAction="collapseActionView|ifRoom"
app:actionViewClass="android.widget.SearchView"/>
...
// Activity#onCreateOptionsMenu(android.view.Menu)
val searchView: SearchView = menu.findItem(R.id.search).actionView as android.widget.SearchView
searchView.setOnQueryTextListener(...)
This does (compiles, does not crash, and listener works):
<!--actionbar.xml-->
...
<item android:id="#+id/search"
android:title="#string/action_search"
android:icon="#drawable/ic_search"
app:showAsAction="collapseActionView|ifRoom"
app:actionViewClass="androidx.appcompat.widget.SearchView"/>
...
// Activity#onCreateOptionsMenu(android.view.Menu)
val searchView: SearchView = menu.findItem(R.id.search).actionView as androidx.appcompat.widget.SearchView
searchView.setOnQueryTextListener(...)
You may have to set searchView.setOnQueryTextListener(this); on your SearchView reference.
I've got 2 activites : the first, HomepageActiviy, have a search widget that search data using another activity, SearchActivity.
What I want to do is when I go back from SearchActiviy to HomepageActivity, the search widget go collapsed and with a empty text.
I've tried to do this following thing :
public class HomepageActivity extends Activity {
#TargetApi(11)
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.projectslist, menu);
if(Build.VERSION.SDK_INT >= 11) {
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
SearchView searchView = (SearchView) menu.findItem(R.id.homepage_search).getActionView();
ComponentName component = new ComponentName(this, SearchActivity.class);
searchView.setSearchableInfo(searchManager.getSearchableInfo(component));
searchView.setIconifiedByDefault(true);
searchView.setQuery("", false);
}
return super.onCreateOptionsMenu(menu);
}
[…]
#TargetApi(11)
#Override
protected void onRestart() {
super.onRestart();
if(Build.VERSION.SDK_INT >= 11)
invalidateOptionsMenu();
launchAsynchronousImageDownload();
}
}
If the widget is well displayed as collapsed, the text in the widget still remember searched text (after I re-open the widget).
How can I reset the text of the widget?
Thanks for any help! ;)
You might also try the following:
searchView.setQuery("", false);
searchView.clearFocus();
this is the magic
searchView.setQuery("", false); // clear the text
searchView.setIconified(true); // close the search editor and make search icon again
in the HomepageActivity insert the onSaveInstanceState function after oncreate function
this function will trigger everytime you open a new activity ,
before opening new activity it will reset the value of Search Widget
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
searchView.setQuery("", false);
searchView.setIconified(true);
}
This worked for me:
First, I declared the menu item variable at the top of the activity:
private MenuItem mSearchMenuItem;
I defined the variable in OnCreateOptionsMenu():
mSearchMenuItem = menu.findItem(R.id.action_search);
I declared invalidateOptionsMenu() in onResume():
#Override
protected void onResume() {
invalidateOptionsMenu();
super.onResume();
}
Lastly, I called collapseActionView() on the menu item in onPrepareOptionsMenu().
#Override
public boolean onPrepareOptionsMenu(Menu menu) {
mSearchMenuItem.collapseActionView();
return super.onPrepareOptionsMenu(menu);
}
searchView.setQuery("", false);
searchView.setIconified(false);
I had this problem too and it worked if I put it in onPrepareOptionsMenu.
#Override
public boolean onPrepareOptionsMenu (Menu menu) {
SearchView searchView = (SearchView) menu.findItem(R.id.action_search).getActionView();
searchView.setQuery("", false);
// rest of code...
}
Kotlin
Here's a cleaner solution, it fixes the following:
Issue of showing filtered list after screen rotation.
Issue of showing filtered list when the user switches to other app and returns back.
Issue of search menu shifting to the left when the user returns back.
No need to iconify if you are invalidating, it's done automatically.
override fun onSaveInstanceState(outState: Bundle) {
super.onSaveInstanceState(outState)
searchView.setQuery("", false)
(activity as YourActivity).invalidateOptionsMenu()
}
Make sure to change YourActivity to the Activity name in which you have your Fragment.
Just found an ugly way to make it work (read comments to see differences):
public class HomepageActivity extends Activity {
// Declaring SearchView as an instance object
private SearchView searchView;
#TargetApi(11)
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.projectslist, menu);
if(Build.VERSION.SDK_INT >= 11) {
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
// Using instance var instead of local var
searchView = (SearchView) menu.findItem(R.id.homepage_search).getActionView();
ComponentName component = new ComponentName(this, SearchActivity.class);
searchView.setSearchableInfo(searchManager.getSearchableInfo(component));
searchView.setIconifiedByDefault(true);
// Setting query is not anymore required
//searchView.setQuery("", false);
}
return super.onCreateOptionsMenu(menu);
}
[…]
#TargetApi(11)
#Override
protected void onRestart() {
super.onRestart();
// Do not need to recreate menu
/*if(Build.VERSION.SDK_INT >= 11)
invalidateOptionsMenu();*/
if(Build.VERSION.SDK_INT >= 11) {
// Calling twice: first empty text field, second iconify the view
searchView.setIconified(true);
searchView.setIconified(true);
}
launchAsynchronousImageDownload();
}
}
It's pretty ugly, I think, so if anybody as a better idea, just tell me :)