Why i need call view.postRunnable to show keyboard - android

I have an logic like this: when enter the edit activity, i will show popup first, then show soft keyboard in the onDismissListener callback, but when i call showKeyboard directly in the callback, the soft keyboard doesn't show. Only i call the view.postRunnable, it will show as expected. As well the activity softkeyboard option is set android:windowSoftInputMode="stateHidden|adjustResize"
private void showKeyboard() {
InputMethodManager imm = (InputMethodManager)
getSystemService(Context.INPUT_METHOD_SERVICE);
imm.showSoftInput(mEditText, InputMethodManager.SHOW_IMPLICIT);
}

Unless someone with deep knowledge of the inner gears of the UI framework come by to answer, everyone's answer will be a "best guess". So below is my best guess:
That is most likely related to the Window and WindowManager and how they interact with Views and keyboards.
The EditText being passed to the method have a token to your activity window, and here is my guess:
If the window is not in foreground, it can't show a keyboard. So when you post the method call, then that method gets executed after the Window from the Popup is gone, and the Window from the activity is in Foreground.

The onDismiss() callback is most likely called from non-UI thread, so you can't update your UI directly. That's why you need to post it to the UI thread with view.postRunnable().

Related

Implement tap out from EditText

I have a request from a client which says something like this: after a user inserts his name, on tap out validate with server.
I never heard about tapping out from a field in Android yet. (tap out means when you are writing something into an EditText, then you click on other view, hide keyboard and call focus change listener).
Do you have any idea about this implemented in Android? Thanks.
Update, after marked duplicated: I already did my research for this a lot, this is why I asked here for an opinion.
The above case is just an example. My main interest is regarding tapping out from EditText (TAP on another view with NO action - e.g. a TextView with no clickable function). I hope it's clear now.
You can force Android to hide the virtual keyboard using the InputMethodManager, calling hideSoftInputFromWindow, passing in the token of the window containing your focused view.
InputMethodManager methodManager = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
if (methodManager != null) {
methodManager.hideSoftInputFromWindow(mEditText.getWindowToken(),0);
}

Hide soft keyboard showed by other application

I know that to hide soft keyboard I need to use code like this:
InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(myEditText.getWindowToken(), 0);
My problem is that I starting the ACTION_SEND intent, and use Twitter app to handle it. I pass a message to tweet it. But if the user does not confirm the message, but clicks ActionBar back button, the Twitter activity is finished, and my app lication comes back to the front. But the soft Keyboard, called by Twitter does not hide. I have no idea how to get Twitter's WindowToken. Could anybody help me?
Another way is to do the same in AndroidManifest.xml file. You can annotate your activity with the following line:
android:windowSoftInputMode="stateAlwaysHidden"
which means your activity will always hide keyboard when receives focus.
I have found an unswer.
I had to add this code:
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
in the onResume() method

Using subclass of Input Method Service

I extended InputMethodService hoping to use this Service for showing a soft keyboard even though a hard keyboard is connected(based off the following post Show soft keyboard even though a hardware keyboard is connected). Is there a way to bind to this service within the app without having to declare it in the manifest? The end result is to have InputMethodService.onEvaluateInputViewShown return true so that the soft keyboard will show even though a hard keyboard is connected.
I would like to use the extended class MultiInputMethodService with the inputmethodmanager in show/hideSoftKeyboard:
public class MultiInputMethodService extends InputMethodService {
#Override
public boolean onEvaluateInputViewShown () {
Log.i("onEvaluateInputViewShow","onEvaluateInputViewShown");
return true;
}
}
my activity:
private void showSoftKeyboard() {
InputMethodManager imm = (InputMethodManager) this.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.toggleSoftInput(InputMethodManager.SHOW_FORCED,InputMethodManager.HIDE_IMPLICIT_ONLY );
}
private void hideSoftKeyboard() {
InputMethodManager imm = (InputMethodManager) this.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(this.myInput.getEditText().getWindowToken(), 0);
}
The IMS framework really needs to be used as a whole. If you want to be the keyboard, the user will need to select you as the default keyboard via settings. If you were to try to bind with the service directly I'm not sure what the result would be, but my guess would be that it ends badly. By having the user set you as the default keyboard, you will automatically be used as the keyboard in all apps.
Of course, you can't just set that yourself, for security purposes. Otherwise keyboards would be fighting over the setting. The user has to set it manually.
EDIT:
I found the documentation you are referring to(under the "Security Section"):
http://developer.android.com/reference/android/view/inputmethod/InputMethodManager.html
A client application can ask that the system let the user pick a new
IME, but can not programmatically switch to one itself. This avoids
malicious applications from switching the user to their own IME, which
remains running when the user navigates away to another application.
An IME, on the other hand, is allowed to programmatically switch the
system to another IME, since it already has full control of user
input.
The user must explicitly enable a new IME in settings before they can
switch to it, to confirm with the system that they know about it and
want to make it available for use.

How to hide the soft keyboard after hitting the search dialog box

I'm trying to use Android's built-in search dialog, and it's working fine except when I try to use it with a ProgressDialog. The basic chain of events it this:
User press the search button, enters a query and submits it.
The SearchManager calls the search Activity's onCreate method.
In the onCreate method, I call an AsyncTask that runs a query and shows a ProgressDialog in the onPreExecute method and hides it in the onPostExecute method.
This all happens fine except as soon as I submit the query the screen looks like this:
... which is pretty ugly. How can I prevent this from happening?
I dont see the image, but i think it must be the softkeyboard sitting there. It can be removed from the code by calling:
((InputMethodManager) activity.getSystemService(Context.INPUT_METHOD_SERVICE)).hideSoftInputFromWindow(searchField.getWindowToken(), 0);
This should be called before the dialog is made and shown.

Android - Activities and navigation?

I navigate from Activity1 to Activity2
On Activity 2 I have a keyboard and this keyboard stays on the screen after selecting the back button and going to Activity 1.
This is how I fixed this issue
// This code is in Activity 2
#Override
public void onBackPressed() {
startActivity(intentForActivity1);
finish();
}
Is this a wrong solution to my problem?
Is it a bad idea to handle the back button manually?
Since you're capturing the back button press, most probably the soft keyboard does not receive the press and thus it does not hide.
Try hiding it yourself:
#Override
public void onBackPressed() {
InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(myEditText.getWindowToken(), 0);
startActivity(intentForActivity1);
finish();
}
See Reto Meier's answer for more details on this method to hide the keyboard: Close/hide the Android Soft Keyboard
There's nothing inherently wrong with overriding the back button. Just make sure the behavior isn't confusing to the user.
Also, if you ever just want to hide the soft keyboard (say, you're switching between tabs or something like that), you can use InputMethodManager. Here's a thread where people discussed ways to do this.

Categories

Resources