Hide soft keyboard Android
There are many times when we need to hide soft keyboard (also called virtual keyboard) when probably there is a focus change, or on click of a button (say “Submit”), or any other action. There could be a case where you don’t want keyboard to pop when user enters an Activity.
You can use any one of the many snippets present all over the web, but after hitting build only you will notice that it was supposed to be called from Activity, or maybe it required a view to be passed. Hence, there is no one size fits all solution for such a simple requirement.
Android provides a class InputMethodManager which deals with current input method for an application.
It would have been easier to directly call a method from InputMethodManager to hide or close the currently displayed keyboard, but this is where problem arises.
Context is required to get the hold of InputMethodManager instance. Getting a context is not a problem, but such methods are usually called from some sort of utility classes which don’t have context.
If it wasn’t frustrating enough to get the correct Context instance, InputMethodManager also requires the View from which keyboard needs to be hidden from. This is where novice as well as seasoned Android App Development Company feel cheated.
Here is a utility method which closes the soft keyboard BUT only when you call it from an Activity:
Sample call to closeKeyboard where MainActivity being your current Activity:
This method requires the current Activity instance in which you are trying to hide the soft keyboard.
The limitation of this utility method is that it requires you to call it from an Activity. This won’t work if calling from a Fragment. You may feel calling it away with Fragment’s parent Activity using getActivity() but it won’t work because while the fragment is displayed, parent Activity is not holding any focus.
To hide the soft keyboard from a Fragment, you can use following utility method:
public static void hideKeyboardFrom(Context context, View view)
This can be called by passing Context and the view from currently displayed screen where you want to hide the keyboard:
There could be cases when there is no focusable view in Fragment and you want to hide the keyboard due to some event or trigger.
Notice that we have changed the way we acquire the “View”.
If you choose the fragment as a parameter, you can update this method to use the Fragment instance to acquire the view.
Whenever an Activity is launched with a focusable view in it, SoftKeyboard is supposed to launch as soon as first focusable view is found because initial focus is assigned to this view. If you want to keep the keyboard hidden when an Activity is launched, you will need to update the “windowSoftInputMode” attribute in AndroidManifest.xml.
This restricts the automatic launch of keyboard when an Activity is launched but it won’t stop the keyboard from popping up when the focusable view is touched.
On the contrary, if the situation demands display of SoftKeyboard when an Activity is launched without having user to touch a focusable or editable view, you can modify the “windowSoftInputMode” attribute accordingly:
These are the few cases that deals with common keyboard scenarios. It’s a good practice to have precise control on keyboard according to use case rather than having Android decide as it can be really frustrating for user to manually close the keyboard when not required. It may lead to accidentally closing the current Activity or Fragment due to pressing back button. It hampers the current operation being performed. This may, unfortunately, result in user losing the interest in your application altogether.
Talk to our experts about your mobile app requirements
Contact us and know more about how our experts can help your business grow.
Источник
Закрыть / скрыть программную клавиатуру Android
У меня есть EditText и Button в моем макете.
После записи в поле редактирования и нажатия на Button , я хочу скрыть виртуальную клавиатуру. Я предполагаю, что это простой кусок кода, но где я могу найти пример этого?
При касании за пределами клавиатуры.
Чтобы прояснить это безумие, я хотел бы начать с извинения от имени всех пользователей Android за совершенно нелепое обращение Google с программной клавиатурой. Причина того, что на один и тот же простой вопрос так много ответов, разных, потому что этот API, как и многие другие в Android, разработан ужасно. Я не могу придумать никакого вежливого способа заявить об этом.
Я хочу спрятать клавиатуру. Я ожидаю , чтобы обеспечить Android со следующим утверждением: Keyboard.hide() . Конец. Большое спасибо. Но у Android есть проблема. Вы должны использовать, InputMethodManager чтобы скрыть клавиатуру. Хорошо, хорошо, это API Android для клавиатуры. НО! Вы должны иметь для Context того, чтобы получить доступ к IMM. Теперь у нас есть проблема. Я могу захотеть скрыть клавиатуру от статического или служебного класса, который не нужен и не нужен Context . или И еще хуже, IMM требует, чтобы вы указали, что View (или даже хуже, что Window ) вы хотите скрыть клавиатуру ОТ.
Это то, что делает скрытие клавиатуры таким сложным. Уважаемый Google: Когда я ищу рецепт торта, RecipeProvider на Земле нет ни одного человека , который отказался бы предоставить мне этот рецепт, если я сначала не отвечу, КТО будет съеден торт И где он будет съеден !!
Эта печальная история заканчивается ужасной правдой: чтобы спрятать клавиатуру Android, вам потребуется предоставить две формы идентификации: а Context и а View или а Window .
Я создал метод статической утилиты, который может выполнять работу ОЧЕНЬ надежно, при условии, что вы вызываете его из Activity .
Имейте в виду, что этот служебный метод работает ТОЛЬКО при вызове из Activity ! Вышеуказанные вызовы метода getCurrentFocus для цели, Activity чтобы получить правильный маркер окна.
Но предположим, что вы хотите скрыть клавиатуру от EditText хоста в DialogFragment ? Вы не можете использовать метод выше для этого:
Это не сработает, потому что вы будете передавать ссылку на Fragment хост Activity , который не будет иметь сфокусированного контроля, пока Fragment отображается! Вот Это Да! Итак, чтобы скрыть клавиатуру от фрагментов, я прибегаю к более низкому уровню, более распространенному и более уродливому:
Ниже приведена дополнительная информация, полученная из-за потраченного времени в погоне за этим решением:
О программе windowSoftInputMode
Есть еще одна точка зрения, о которой нужно знать. По умолчанию Android автоматически назначит начальный фокус первому EditText или фокусируемому элементу управления в вашем устройстве Activity . Естественно, что InputMethod (обычно это программная клавиатура) будет реагировать на событие фокуса, показывая себя. windowSoftInputMode Атрибут AndroidManifest.xml , когда установлено stateAlwaysHidden , инструктирует клавиатуры , чтобы игнорировать это автоматически присвоенный первоначальный фокус.
Почти невероятно, что ничего не делает для предотвращения открытия клавиатуры при прикосновении к элементу управления (если только focusable=»false» и / или focusableInTouchMode=»false» не назначены элементу управления). По-видимому, настройка windowSoftInputMode применяется только к событиям автоматической фокусировки, а не к событиям фокусировки, вызванным событиями касания.
Следовательно, stateAlwaysHidden ОЧЕНЬ плохо назван действительно. Возможно, это следует назвать ignoreInitialFocus вместо.
Надеюсь это поможет.
ОБНОВЛЕНИЕ: Больше способов получить жетон окна
Если нет сфокусированного представления (например, это может произойти, если вы только что изменили фрагменты), есть другие представления, которые предоставят полезный маркер окна.
Это альтернативы для приведенного выше кода. if (view == null) view = new View(activity); Они не относятся явно к вашей деятельности.
Внутри класса фрагмента:
Задан фрагмент fragment в качестве параметра:
Начиная с вашего содержания:
ОБНОВЛЕНИЕ 2: Очистить фокус, чтобы снова не показывать клавиатуру, если вы открываете приложение из фона
Добавьте эту строку в конец метода:
Вы можете заставить Android скрыть виртуальную клавиатуру, используя InputMethodManager , вызывая hideSoftInputFromWindow , передавая токен окна, содержащего ваше сфокусированное представление.
Это заставит клавиатуру быть скрытой во всех ситуациях. В некоторых случаях вы захотите передать InputMethodManager.HIDE_IMPLICIT_ONLY второй параметр, чтобы скрыть клавиатуру только в том случае, если пользователь явно не заставлял ее появляться (удерживая меню).
Примечание: если вы хотите сделать это в Kotlin, используйте: context?.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager
Котлин Синтаксис
Также полезно скрыть софт-клавиатуру:
Это можно использовать для подавления программной клавиатуры до тех пор, пока пользователь фактически не коснется представления редактирования текста.
У меня есть еще одно решение, чтобы скрыть клавиатуру:
Здесь проходят HIDE_IMPLICIT_ONLY в положении showFlag и 0 в положении hiddenFlag . Это принудительно закроет мягкую клавиатуру.
Решение Майера работает и для меня. В моем случае верхний уровень моего приложения — это tabHost, и я хочу скрыть ключевое слово при переключении вкладок — я получаю маркер окна из представления tabHost.
Пожалуйста, попробуйте этот код ниже onCreate()
Обновление: я не знаю, почему это решение больше не работает (я только что протестировал на Android 23). Пожалуйста, используйте вместо этого решение Saurabh Pareek . Вот:
Если все остальные ответы здесь не работают так, как вам хотелось бы, есть другой способ ручного управления клавиатурой.
Создайте функцию, которая будет управлять некоторыми из EditText свойств:
Затем убедитесь, что на Focus EditText вы открываете / закрываете клавиатуру:
Теперь, когда вы хотите открыть клавиатуру вручную, позвоните:
И для закрытия звонка:
Можно использовать и правильные флаги.
Пример реального использования
от такого поиска, здесь я нашел ответ, который работает для меня
Краткий ответ
В вашем OnClick слушателе вызвать onEditorAction из EditText с IME_ACTION_DONE
Развертка
Я чувствую, что этот метод лучше, проще и более соответствует шаблону дизайна Android. В приведенном выше простом примере (и, как правило, в большинстве распространенных случаев) у вас будет EditText фокус, который имеет / имел фокус, и он также обычно вызывал клавиатуру в первую очередь (он определенно способен вызывать ее во многих случаях). общие сценарии). Таким же образом, это должен быть тот, кто отпускает клавиатуру, обычно это может сделать оператор ImeAction . Просто посмотрите, как ведет себя команда EditText with android:imeOptions=»actionDone» , вы хотите добиться того же поведения тем же способом.
Это должно работать:
Я использую пользовательскую клавиатуру для ввода шестнадцатеричного числа, поэтому я не могу показать клавиатуру IMM .
В v3.2.4_r1 setSoftInputShownOnFocus(boolean show) был добавлен контроль погоды или не отображать клавиатуру, когда TextView получает фокус, но он все еще скрыт, поэтому необходимо использовать отражение:
Для более старых версий я получил очень хорошие (но далеко не идеальные) результаты с a OnGlobalLayoutListener , добавленным с помощью a ViewTreeObserver из моего корневого представления, а затем проверив, отображается ли клавиатура следующим образом:
Это последнее решение может показывать клавиатуру в течение доли секунды и портить ручки выбора.
Когда в клавиатуру входит полный экран, onGlobalLayout не вызывается. Чтобы избежать этого, используйте TextView # setImeOptions (int) или в объявлении TextView XML:
Обновление: только что нашел, какие диалоги используют, чтобы никогда не показывать клавиатуру и работает во всех версиях:
Я потратил более двух дней, работая над всеми решениями, опубликованными в ветке, и обнаружил, что их так или иначе не хватает. Мое точное требование — иметь кнопку, которая со 100% надежностью отображает или скрывает экранную клавиатуру. Когда клавиатура находится в скрытом состоянии, она не должна появляться снова, независимо от того, какие поля ввода пользователь нажимает. Когда он находится в своем видимом состоянии, клавиатура не должна исчезать независимо от того, на какие кнопки нажимает пользователь. Это должно работать на Android 2.2+ вплоть до самых последних устройств.
Вы можете увидеть рабочую реализацию этого в моем приложении чистой RPN .
После тестирования многих из предложенных ответов на разных телефонах (включая устройства froyo и пряники) стало очевидно, что приложения для Android могут надежно:
- Временно скрыть клавиатуру. Он появится снова, когда пользователь выделит новое текстовое поле.
- Покажите клавиатуру, когда начинается действие, и установите флаг активности, указывающий, что клавиатура всегда должна быть видна. Этот флаг можно установить только при инициализации действия.
- Отметьте активность, чтобы никогда не показывать и не разрешать использование клавиатуры. Этот флаг можно установить только при инициализации действия.
Для меня временно скрыть клавиатуру недостаточно. На некоторых устройствах оно появится снова, как только будет выделено новое текстовое поле. Поскольку мое приложение использует несколько текстовых полей на одной странице, при фокусировке на новом текстовом поле скрытая клавиатура снова выскочит.
К сожалению, пункты 2 и 3 в списке работают только надёжно, когда работа начинается. После того, как действие стало видимым, вы не сможете постоянно скрывать или показывать клавиатуру. Хитрость заключается в том, чтобы фактически возобновить свою деятельность, когда пользователь нажимает кнопку переключения клавиатуры. В моем приложении, когда пользователь нажимает кнопку переключения клавиатуры, выполняется следующий код:
Это приводит к тому, что текущее действие сохраняет свое состояние в Bundle, а затем действие запускается, проходя через логическое значение, которое указывает, должна ли клавиатура отображаться или скрываться.
Внутри метода onCreate запускается следующий код:
Если должна отображаться программная клавиатура, то InputMethodManager должен показать клавиатуру, а в окне указывается, чтобы программный ввод был всегда видимым. Если программная клавиатура должна быть скрыта, то устанавливается WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM.
Этот подход надежно работает на всех устройствах, на которых я тестировал — от 4-летнего телефона HTC с Android 2.2 до Nexus 7 с 4.2.2. Единственный недостаток этого подхода — вы должны быть осторожны при обращении с кнопкой «назад». Поскольку мое приложение по существу имеет только один экран (это калькулятор), я могу переопределить onBackPressed () и вернуться на домашний экран устройства.
Источник