Showing the soft keyboard for SearchView on ActionBar - android

We've got a SearchView on the ActionBar which is set to be non-iconified. As we don't have any content in the view until the user's entered something to search for, it would make sense to give the SearchView initial focus, and make sure the soft keyboard is showing ready for the user to enter text — otherwise they'll always have to first tap in the SearchView.
I can give the SearchView focus by just calling
searchView.requestFocus();
but I can't get the soft keyboard to appear. In another one of our Fragments I have an EditText which we want to be focused I can get the soft keyboard to appear there by calling
InputMethodManager mgr = (InputMethodManager)getActivity().getSystemService(
Context.INPUT_METHOD_SERVICE);
mgr.showSoftInput(editText, InputMethodManager.SHOW_IMPLICIT);
but this just doesn't work on the SearchView. It must surely be possible to get this to work.

Further rummaging around StackOverflow and I found this question:
Forcing the Soft Keyboard open
which contains a solution that worked for me:
((InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE)).
toggleSoftInput(InputMethodManager.SHOW_FORCED,
InputMethodManager.HIDE_IMPLICIT_ONLY);

I have a similar problem where none of the proposed solutions here worked. Some just didn't make the keyboard appear at all and some show a keyboard but the key presses there just do not work.
The only thing that worked was:
// hack for making the keyboard appear
searchView.setIconified(true);
searchView.setIconified(false);

I am using a SearchView with setIconifiedByDefault(false). Testing with Android 4.4.2, the only way I could get the keyboard to actually show was to look at the source code for SearchView and mimic how it requested the keyboard to be shown. I've tried literally every other method I could find/think of and this is the only way I could get the keyboard to show reliably. Unfortunately, my method requires some reflection.
In onCreateOptionsMenu(Menu):
searchView.requestFocus();
searchView.post(new Runnable() {
#Override
public void run() {
showSoftInputUnchecked();
}
});
And then create a method to call the hidden method "showSoftInputUnchecked" in InputMethodManager:
private void showSoftInputUnchecked() {
InputMethodManager imm = (InputMethodManager)
getSystemService(Context.INPUT_METHOD_SERVICE);
if (imm != null) {
Method showSoftInputUnchecked = null;
try {
showSoftInputUnchecked = imm.getClass()
.getMethod("showSoftInputUnchecked", int.class, ResultReceiver.class);
} catch (NoSuchMethodException e) {
// Log something
}
if (showSoftInputUnchecked != null) {
try {
showSoftInputUnchecked.invoke(imm, 0, null);
} catch (IllegalAccessException e) {
// Log something
} catch (InvocationTargetException e) {
// Log something
}
}
}
}
As with all solutions that access methods not in the public API, I can't promise that this won't break with new versions of Android.

It worked for me.
private SearchView mSearchView;
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
SearchManager searchManager =
(SearchManager) getSystemService(Context.SEARCH_SERVICE);
MenuItem searchItem = menu.findItem(R.id.action_search);
mSearchView =
(SearchView) searchItem.getActionView();
mSearchView.setSearchableInfo(
searchManager.getSearchableInfo(getComponentName()));
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.action_search) {
mSearchView.setIconifiedByDefault(true);
mSearchView.setFocusable(true);
mSearchView.setIconified(false);
mSearchView.requestFocusFromTouch();
}
return super.onOptionsItemSelected(item);
}

If you wanna show the soft keyboard and focus on the input box, you can try
final MenuItem menuItem = menu.findItem(R.id.action_search);
menuItem.expandActionView();//expand show soft keyboard
<item
android:id="#+id/action_search"
android:icon="#drawable/ic_actionbar_search"
liven:showAsAction="collapseActionView|always" //always
liven:actionViewClass="android.support.v7.widget.SearchView" />enter code here

This will not show keyboard every time you come on activity
searchview.clearFocus();

Use expandView method :
Your onCreateOptionsMenu could be something like this:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
//Used to put dark icons on light action bar
final SearchView searchView = new SearchView(getSupportActionBar().getThemedContext());
MenuItem mitem = menu.add("Search");
mitem.setIcon(ic_search_inverse)
.setActionView(searchView)
.setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM | MenuItem.SHOW_AS_ACTION_COLLAPSE_ACTION_VIEW);
mitem.expandActionView();
listsearch.setOnItemClickListener(this);
return true;
}

You can try what I did. This worked well for me.
//set query change listener
searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener(){
#Override
public boolean onQueryTextChange(String newText) {
// TODO Auto-generated method stub
return false;
}
#Override
public boolean onQueryTextSubmit(String query) {
/**
* hides and then unhides search tab to make sure keyboard disappears when query is submitted
* 4 = INVISIBLE
* 0 = VISIBLE
*/
searchView.setVisibility(4);
searchView.setVisibility(0);
return false;
}
});

Related

Searchview - Hide toast that appears by pressing key

I'm using a filtering SearchView. Everything works fine but, when you leave the keyboard to type and press a button, a kind of toast is shown. Anyone know how to remove it?
My code is:
searchView = (SearchView) view.findViewById(R.id.buscador_lineas_transporte);
searchView.setOnQueryTextListener(new OnQueryTextListener() {
#Override
public boolean onQueryTextSubmit(String query) {
return false;
}
#Override
public boolean onQueryTextChange(String newText) {
if(TextUtils.isEmpty(newText)){
lvLineasTransporte.clearTextFilter();
}
else{
lvLineasTransporte.setFilterText(newText);
}
return true;
}
});
Thanks.
Solved
This keyboard appears when you implement the interface Filterable in your adapater.
I recommendto use "AutoCompleteTextView" instead of "SearchView".
AutoCompleteTextView searchView = (AutoCompleteTextView) view.findViewById(R.id.searchView);

Android search widget How to hide the close button in search view by default?

I have implemented an android SearchView in ActionBar. When the SearchView gains focus, the close button [x] at the right shows up. I took a look at other android native apps, like Contacts and Gmail. The close button is not shown when the SearchView gains focus.
How to set my SearchView behave like that?
Setting searchView.setIconifiedByDefault(false) will disable collapsing the search view and also remove the close button.
I faced the same problem with android.support.v7.widget.SearchView and found a solution. First, in onCreateOptionsMenu, you can obtain a reference to the SearchView as well as its close button:
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
super.onCreateOptionsMenu(menu, inflater);
inflater.inflate(R.menu.search, menu);
MenuItem searchItem = menu.findItem(R.id.action_search);
mSearchView = (SearchView) MenuItemCompat.getActionView(searchItem);
try {
Field searchField = SearchView.class.getDeclaredField("mCloseButton");
searchField.setAccessible(true);
mSearchCloseButton = (ImageView) searchField.get(mSearchView);
} catch (Exception e) {
Log.e(TAG, "Error finding close button", e);
}
}
Now you can try to modify the button. First I tried to use setVisibility(View.GONE) to hide the close button, but that doesn't work, because the SearchView resets the visibility of its close button when the user interacts with the SearchView. So my solution was to use a transparent drawable and disable the click of the close button:
if (mSearchCloseButton != null) {
mSearchCloseButton.setEnabled(false);
mSearchCloseButton.setImageDrawable(getResources().getDrawable(R.drawable.transparent));
}
This article helped me as well:
http://novoda.com/blog/styling-actionbar-searchview
However, this is quite hacky to be honest. It would be cleaner to grab the SearchView source from https://android.googlesource.com/platform/frameworks/support.git/+/master/v7/appcompat/src/android/support/v7/widget/SearchView.java and create your own version of SearchView that does the hide/show of the close button.
Update:
Google just announced AppCompat v21, which has styling improvements for the SearchView widget:
http://android-developers.blogspot.com/2014/10/appcompat-v21-material-design-for-pre.html
You can also use this to hide the close the button
ImageView closeBtn = (ImageView) searchView.findViewById(R.id.search_close_btn);
closeBtn.setEnabled(false);
closeBtn.setImageDrawable(null);
Posting for future visitors. Previous answers are old and not easy. All you have to do is to set null to app:closeIcon this way app:closeIcon="#null"
<androidx.appcompat.widget.SearchView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:closeIcon="#null" <!-- This simple solution -->
app:iconifiedByDefault="false" />
You can get a link to the button from a SearchView object (AppCompat v23.2.1):
searchView = (SearchView) MenuItemCompat.getActionView(menu.findItem(R.id.action_search));
ImageView mCloseButton = (ImageView) searchView.findViewById(android.support.v7.appcompat.R.id.search_close_btn);
Then you can assign a listener to the SearchView text changes (SearchView also changes the visibility of the button, but the listener will be executed afterwards and will override those changes):
searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
#Override
public boolean onQueryTextSubmit(String query) {
return false;
}
#Override
public boolean onQueryTextChange(String newText) {
mCloseButton.setVisibility(newText.isEmpty() ? View.GONE : View.VISIBLE);
return false;
}
});
And finally, a listener to hide the icon when SearchView is expanded from iconified state:
searchView.setOnSearchClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// hide "x" button if there is no text
String query = searchView.getQuery().toString();
mCloseButton.setVisibility(query.isEmpty() ? View.GONE : View.VISIBLE);
}
});
With AndroidX, android.support.v7.appcompat.R.id.search_close_btn won't work
This will do the trick,
app:closeIcon="#null"

Validate text input in SearchView

I have a SearchView in ActionBar.
I'd like to validate the text input by the user before submitting it to SearchManager.
What I mean is, if a user entered text less than 3 characters, then a Toast will pop up instead going to another activity that shows the search results.
Here is how I implement the SearchView:
In MainActivity:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.search, menu);
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
SearchView searchView = (SearchView) menu.findItem(R.id.menu_search).getActionView();
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
SearchView.OnQueryTextListener queryTextListener = new SearchView.OnQueryTextListener() {
#Override
public boolean onQueryTextSubmit(String s) {
Log.d(TAG, "submit= "+s);
if (s.length() < 4) Toast.makeText(getApplicationContext(), "More than 3 letter pl0x", Toast.LENGTH_LONG).show();
return true;
}
#Override
public boolean onQueryTextChange(String s) {
return true;
}
};
searchView.setOnQueryTextListener(queryTextListener);
return super.onCreateOptionsMenu(menu);
}
I just wanna make sure the user input is more than 3 characters. Is there a possible way to do this?
From the docs: "The listener can override the standard behavior by returning true to indicate that it has handled the submit request. Otherwise return false to let the SearchView handle the submission by launching any associated intent."
if (s.length() < 4) {
Toast.makeText(getApplicationContext(), "More than 3 letter pl0x", Toast.LENGTH_LONG).show();
return true;
} else {
return false;
}
there is a library from zasadnyy for this.
Click here https://github.com/zasadnyy/z-validations
I downloaded that library and added the class "HasMinimumLength". With that, you can check whether the length of the text is longer than the provided minimum character length.
Please take care, that you need to copy the strings from strings.xml into your own strings and that you have to switch the imports. Meaning, in the validation classes instead of
import ua.org.zasadnyy.zvalidations.R you should use import your.package.name.R

Unable to hide the virtual keyboard of SearchView iconfiedbydefault(false)

I have a search view which is set as expanded by default with default search query but i don't want the virtual keyboard.In below code i tried to hide keyboard in onCreateOptionsMenu but still keyboard is visible.
imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
MenuItem item = menu.findItem(R.id.menu_search);
item.expandActionView();
mSearchView = (SearchView) item.getActionView();
mSearchView.setIconifiedByDefault(false);
mSearchView.setQuery(query, true);
imm.hideSoftInputFromWindow(mSearchView.getWindowToken(), 0);
I am using sherlock search view widget. any suggestion to hide the virtual keyboard.What i am doing wrong?
Inspired by Parnit's answer, I've found a better method, which also works and is more beautiful:
mSearchView.clearFocus();
Edit: I added the better solution on top, but also kept the old answer as a reference.
#Override
public boolean onQueryTextSubmit(String query) {
searchView.clearFocus();
return false;
}
Original Answer: I programmed using a setOnQueryTextListener. When the searchview is hidden the keyboard goes away and then when it is visible again the keyboard does not pop back up.
//set query change listener
searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener(){
#Override
public boolean onQueryTextChange(String newText) {
// TODO Auto-generated method stub
return false;
}
#Override
public boolean onQueryTextSubmit(String query) {
/**
* hides and then unhides search tab to make sure keyboard disappears when query is submitted
*/
searchView.setVisibility(View.INVISIBLE);
searchView.setVisibility(View.VISIBLE);
return false;
}
});
try
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
add the below line in the manifest for particular Activity.
android:windowSoftInputMode="adjustPan|stateHidden"
simple solution its work for my
add to XML:
android:focusable="false"
In Android Manifest:
android:windowSoftInputMode="adjustPan|stateHidden"
In class open and close the keyboard:
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle action buttons
switch(item.getItemId()) {
case R.id.search:
//TODO Whatever
search.clearFocus();
//Open and close the keyboard
InputMethodManager imm = (InputMethodManager)MyApplication.getAppContext().getSystemService(
Context.INPUT_METHOD_SERVICE);
imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0);
imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0);
return true;
u just have to use:
"object(edittext, searchview, etc)".clearfocus() ;
use it after u generate a search or an action. Example: in the method OnQueryTextListener, after that i use a search. For searchview.

Android SearchView onclick

I have a searchView which looks like this:
private void setupSearchView() {
mSearchView = (SearchView) getActivity().findViewById(
R.id.search_view_neue);
setSearchViewBackground();
mSearchView.setOnClickListener(this);
mSearchView.setOnQueryTextListener(this);
}
public boolean onQueryTextSubmit(String query) {
searchcounter = searchcounter + 1;
setSearchViewBackground();
ArrayList<WissensdokumenteRecord> documents = settingListContent(new ArrayList<WissensdokumenteRecord>());
setListAdapter(new NeueWissensdokumentItemAdapter(
inflater.getContext(), R.layout.row_example, documents));
InputMethodManager im = (InputMethodManager) getActivity()
.getSystemService(Context.INPUT_METHOD_SERVICE);
im.hideSoftInputFromWindow(getActivity().getCurrentFocus()
.getWindowToken(), 0);
return false;
}
<SearchView
android:id="#+id/search_view_neue"
android:layout_width="match_parent"
android:layout_height="60dp"
android:layout_marginLeft="40dp"
android:layout_marginRight="40dp"
android:background="#drawable/border_searchview"
android:maxWidth="540dp"
android:queryHint="Neue Dokumente suchen" >
</SearchView>
So, the behaviour of the search view is, that the keyboard opens by clicking the search button. Now I can search for something. Is it possible to do a search by clicking anywhere in the searchview? Does anyone has an example for me?
I managed to do this in the following way:
Setup the search view on click listener
mSearchView.setOnClickListener(this);
Catch the onClick event:
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.searchView:
mSearchView.onActionViewExpanded();
break;
}
}
In this way the keyboard and search are activated if you click antwhere on the search bar.
This will do exactly what you're trying to achieve.
setIconified(false) will keep the cross icon at this end of the SearchView so that the user can still cancel the same way as if the magnifying glass was clicked.
searchView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
searchView.setIconified(false);
}
});
I must suggest to use setOnSearchClickListener listner to detect SearchView click as According to Android docs :
setOnSearchClickListener
void setOnSearchClickListener (View.OnClickListener listener)
Sets a listener to inform when the search button is pressed.
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater menuInflater = getMenuInflater();
menuInflater.inflate(R.menu.orders_menu, menu);
MenuItem searchItem = menu.findItem(R.id.action_search);
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
if (searchView != null) {
searchView = (SearchView) searchItem.getActionView();
searchView.setOnSearchClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
//perform your click operation here
}
});
return true;
}
I don't see why you need to to set OnClickListener on it.
By clicking on a SearchView you will update text cursor. To perform search you have a keyboard IME action. If clicking on it would perform search it would be impossible to change cursor etc. It is the generally wrong behaviour to make something else than focus / update cursor in text fields.
As far as I remember - you don't need to hide keyboard in OnQueryTextListener. It should hite automatically. Handle your search in OnQueryTextSubmit
search with Sherlock ActionBar SearchView setOnKeyListener
A search widget that intercepts all touches on its children and does a callback on touch down:
class InterceptTouchSearchView(context: Context, attrs: AttributeSet) : SearchView(context, attrs) {
var onActionDownIntercepted: (() -> (Unit))? = null
override fun onInterceptTouchEvent(ev: MotionEvent?): Boolean {
return true
}
#SuppressLint("ClickableViewAccessibility")
override fun onTouchEvent(ev: MotionEvent?): Boolean {
if (ev?.action == MotionEvent.ACTION_DOWN) {
onActionDownIntercepted?.invoke()
}
return false
}
}
Usage: search_view.onActionDownIntercepted = { onSearchFieldClicked() }
If you set android:iconifiedByDefault="false" and setOnSearchClickListener is not efftected.
You can try
searchView.setOnQueryTextListener(QueryTextListener(searchView))
class QueryTextListener(private val searchView: SearchView) : OnQueryTextListener {
override fun onQueryTextSubmit(query: String?): Boolean {
// do something
searchView.clearFocus()
return true
}
override fun onQueryTextChange(newText: String?): Boolean {
return true
}
}

Categories

Resources