Мне нужно сделать очень простую вещь - выяснить, отображается ли программная клавиатура. Возможно ли это в Android?
516
Мне нужно сделать очень простую вещь - выяснить, отображается ли программная клавиатура. Возможно ли это в Android?
Ответы:
НОВЫЙ ОТВЕТ добавлен 25 января 2012
После написания приведенного ниже ответа, кто-то рассказал мне о существовании ViewTreeObserver и его друзей, API, которые скрывались в SDK начиная с версии 1.
Вместо того, чтобы требовать пользовательский тип макета, гораздо более простое решение состоит в том, чтобы дать корневому представлению вашей деятельности известный идентификатор, скажем
@+id/activityRoot
, подключить GlobalLayoutListener к ViewTreeObserver и оттуда вычислить разницу в размерах между корнем представления вашей деятельности и размером окна:Использование утилиты, такой как:
Легко!
Примечание. Ваше приложение должно установить этот флаг в манифесте Android,
android:windowSoftInputMode="adjustResize"
иначе указанное выше решение не будет работать.ОРИГИНАЛЬНЫЙ ОТВЕТ
Да, это возможно, но это намного сложнее, чем должно быть.
Если мне нужно позаботиться о том, когда клавиатура появляется и исчезает (что происходит довольно часто), тогда я настраиваю класс макета верхнего уровня, который переопределяет
onMeasure()
. Основная логика заключается в том, что если раскладка оказывается заполненной значительно меньше, чем общая площадь окна, то, вероятно, отображается программная клавиатура.Тогда в вашем классе деятельности ...
источник
((ViewGroup) findViewById(android.R.id.content)).getChildAt(0)
android.R.id.content
), вы сможете с большей уверенностью сказать, чтоSystem
объект, а не ваше приложение, изменяет свою высоту. Для команды Android было бы намного безопаснее дать нам передышку и сообщить нам хотя бы основные сведения о вводе SoftKeyboard.heightDiff
всегда будет указана высота панели действий. В новом ответе, который был проигнорирован при тестировании, если эта высота больше некоторой константы, но 100 пикселей недостаточно для устройств xxhdpi, таких как Nexus 4. Рассмотрите возможность преобразования этого значения в DP, если вы действительно хотите использовать эту хакерскую работу. около.Надеюсь, это поможет кому-то.
Новый ответ, который дал Рубен Скраттон, великолепен и действительно эффективен, но он действительно работает, только если вы установили свой windowSoftInputMode в AdjustResize. Если вы установите его в AdjustPan, по-прежнему невозможно определить, видна ли клавиатура, используя его фрагмент кода. Чтобы обойти это, я сделал маленькую модификацию кода выше.
источник
TwoDScrollerView
похожего на stackoverflow.com/a/5224088/530513, хотя и с масштабированием. Ребенок был не простой,ImageView
а пользовательской раскладкой (расширяетRelativeLayout
), но не смог обнаружить клавиатуру, используя рекомендованное решение, несмотря на настройкиandroid:windowSoftInputMode="adjustResize"
. Спасибо!ActionBar
иActionBarSherlock
. Большое спасибо! Кстати, есть способr.height()
:)heightDiff > root.getRootView().getHeight() / 4
это хорошая ценность для работы с устройством с высоким разрешением. 100px - короткая. в Nexus 5 с разрешением 1080x1920, 1920 - (996-75)>? 100 = 999 1920 - (1776-75)>? 100 = 219 // Клавиатура работает в Galaxy S2 с разрешением 480x800, 800 - (800-38)>? 100 = 38 800 - (410-38)>? 100 = 428 // клавиатура включена, поэтому магическое число 100px недостаточно хорошо.Это было всегда с точки зрения компьютера, но этот вопрос все еще невероятно актуален!
Итак, я взял приведенные выше ответы и немного их объединил и уточнил ...
Работает для меня :)
ПРИМЕЧАНИЕ. Если вы заметили, что DefaultKeyboardDP не подходит для вашего устройства, играйте со значением и оставьте комментарий, чтобы все знали, каково должно быть значение ... в конце концов мы получим правильное значение для всех устройств!
Для более подробной информации, проверьте реализацию на Киборг
источник
Извините за поздний ответ, но я создал небольшой вспомогательный класс для обработки событий открытия / закрытия с уведомлением слушателей и другими полезными вещами, возможно, кто-то посчитает это полезным:
Пример использования:
источник
getLastKeyboardHeightInPx()
строки не включает высоту этого ряда. Знаете ли вы, как принять это во внимание?Некоторые улучшения, позволяющие избежать неправильного определения видимости программной клавиатуры на устройствах высокой плотности:
Порог разности высот должен быть определен как 128 dp , а не 128 пикселей .
Обратитесь к Google Design Doc о метриках и сетке , 48 dp - удобный размер для сенсорного объекта и 32 dp - минимум для кнопок. Стандартная программная клавиатура должна включать 4 ряда клавиш, поэтому минимальная высота клавиатуры должна быть: 32 dp * 4 = 128 dp , что означает, что пороговый размер должен передаваться в пикселях путем умножения плотности устройства. Для устройств xxxhdpi (плотность 4) порог высоты программной клавиатуры должен составлять 128 * 4 = 512 пикселей.
Разница высот между корневым представлением и его видимой областью:
высота корневого представления - высота строки состояния - видимая высота рамки = нижняя часть корневого представления - нижняя часть видимой рамки, поскольку высота строки состояния равна верхней части видимой рамки корневого представления.
источник
Я потратил немного времени, чтобы выяснить это ... Я запустил некоторые исключения CastException, но понял, что вы можете заменить LinearLayout в layout.xml именем класса.
Нравится:
Таким образом, вы не столкнетесь с какими-либо проблемами.
... и если вы не хотите делать это на каждой странице, я рекомендую вам использовать «MasterPage в Android». Смотрите ссылку здесь: http://jnastase.alner.net/archive/2011/01/08/ldquomaster-pagesrdquo-in-android.aspx
источник
Проверка высоты элементов не надежна, потому что некоторые клавиатуры, такие как WifiKeyboard, имеют нулевую высоту.
Вместо этого вы можете использовать результат обратного вызова showSoftInput () и hideSoftInput (), чтобы проверить состояние клавиатуры. Полная информация и пример кода на
https://rogerkeays.com/how-to-check-if-the-software-keyboard-is-shown-in-android
источник
Идея заключается в том, что если вам нужно одновременно скрыть клавиатуру и проверить состояние программного ввода, используйте следующее решение:
Этот метод возвращает true, если перед скрытием была показана клавиатура.
источник
Я обнаружил, что комбинация метода @ Reuben_Scratton и метода @ Йогеша, кажется, работает лучше всего. Объединение их методов приведет к чему-то вроде этого:
источник
Вы можете наблюдать, как скрывается программная клавиша, с помощью decorView вида деятельности.
источник
Вместо того, чтобы предполагать разностное кодирование, я сделал что-то вроде этого, так как у меня не было пунктов меню в моем приложении.
источник
Существует также решение с системными вставками, но оно работает только с
API >= 21
(Android L
). Скажем, у вас естьBottomNavigationView
дочерний элемент,LinearLayout
и вам нужно скрыть его, когда отображается клавиатура:Все, что вам нужно сделать, это расширить
LinearLayout
таким образом:Идея состоит в том, что когда клавиатура показана, системные вставки меняются с довольно большим
.bottom
значением.источник
Для этого может помочь скрытый метод
InputMethodManager.getInputMethodWindowVisibleHeight
. Но я не знаю, почему это скрыто.источник
Ни одно из этих решений не будет работать для Lollipop как есть. В Lollipop
activityRootView.getRootView().getHeight()
включена высота панели кнопок, а при измерении вида нет. Я адаптировал лучшее / простое решение выше для работы с Lollipop.источник
Я только что столкнулся с ошибкой при использовании большинства решений выше, которые предлагают добавить фиксированное число.
S4 имеет высокое значение dpi, в результате чего высота навигационной панели составляет 100 пикселей, поэтому мое приложение считает, что клавиатура постоянно открыта.
Так что, учитывая выпуск всех новых телефонов с высоким разрешением, я считаю, что использование жестко закодированных значений не является хорошей идеей в долгосрочной перспективе.
Лучший подход, который я нашел после некоторого тестирования на различных экранах и устройствах, заключался в использовании процента. Получите разницу между decorView и содержимым вашего приложения, а затем проверьте процент этой разницы. Из статистики, которую я получил, большинство навигационной панели (независимо от размера, разрешения и т. Д.) Будет занимать от 3% до 5% экрана. Где, как будто клавиатура открыта, она занимала от 47% до 55% экрана.
В качестве решения я решил проверить, составляет ли разница больше 10%, тогда я предполагаю, что клавиатура открыта.
источник
Я использовал небольшой вариант ответа Реубана, который оказался более полезным в определенных обстоятельствах, особенно с устройствами с высоким разрешением.
источник
R.id.activityRoot
, вы можете просто использоватьandroid.R.id.content
именно то, что вам нужно.Это было всегда с точки зрения компьютера, но этот вопрос все еще невероятно актуален! Итак, я взял приведенные выше ответы и немного их объединил и уточнил ...
Меня устраивает.
источник
Попробуй это:
источник
Мой ответ в основном совпадает с ответом Качи, но я обернул его в хороший вспомогательный класс, чтобы очистить то, как он используется в моем приложении.
Вы можете использовать это для обнаружения изменений клавиатуры в любом месте приложения следующим образом:
Примечание: используйте только один из «зарегистрированных» вызовов. Все они работают одинаково и только для удобства
источник
Вы можете попробовать это, отлично работает для меня:
источник
У меня были трудности с поддержанием состояния клавиатуры при изменении ориентации фрагментов в окне просмотра. Я не уверен почему, но это только кажется вялым и действует не так, как в стандартном действии.
Чтобы сохранить состояние клавиатуры в этом случае, сначала вы должны добавить
android:windowSoftInputMode = "stateUnchanged"
к своемуAndroidManifest.xml
. Однако вы можете заметить, что это на самом деле не решает всей проблемы - клавиатура не открывалась для меня, если она была открыта до изменения ориентации. Во всех остальных случаях поведение казалось правильным.Затем нам нужно реализовать одно из упомянутых здесь решений. Самым чистым из найденных мной был Джордж Майсурадзе - используйте логический обратный вызов из hideSoftInputFromWindow:
Я сохранил это значение в
onSaveInstanceState
методе моего фрагмента и получил егоonCreate
. Затем я принудительно показал клавиатуру,onCreateView
если у нее было значениеtrue
(она возвращает true, если клавиатура видна до фактического ее скрытия до уничтожения фрагмента).источник
Вот мое решение, и оно работает. Вместо того, чтобы искать размер в пикселях, просто убедитесь, что высота представления содержимого изменилась или нет:
источник
Не делайте никакого жесткого кода. Лучший способ - изменить размеры своих представлений во время работы над Get Focus на EditText с помощью KeyBord Show. Вы можете сделать это, добавив свойство resize для активности в файл Manifest, используя приведенный ниже код.
android:windowSoftInputMode="adjustResize"
источник
Существует прямой способ выяснить это. И это не требует каких-либо изменений макета.
Таким образом, он работает и в полноэкранном режиме с погружением.
Хитрость в том, что вы пытаетесь скрыть или показать программную клавиатуру и зафиксировать результат этой попытки.
Никакой паники, это не совсем показывает или скрывает клавиатуру. Мы просто просим о состоянии.
Чтобы оставаться в курсе, вы можете просто повторить операцию, например, каждые 200 миллисекунд, используя обработчик.
Вы найдете реализацию здесь: https://stackoverflow.com/a/27567074/2525452
источник
Я думаю, что этот метод поможет вам узнать, является ли клавиатура видимой или нет.
источник
Новый ответ Рубена Скрэттона (рассчитать HeightDiff
int heightDiff = activityRootView.getRootView().getHeight() - activityRootView.getHeight();
) не будет работать в действии, если вы установите режим полупрозрачной строки состояния.Если вы используете полупрозрачную строку состояния,
activityRootView.getHeight()
никогда не изменится погода, если видна программная клавиатура. он всегда будет возвращать высоту активности и статусную строку.Например, Nexus 4, Android 5.0.1, установленный
android:windowTranslucentStatus
в true, вернет 1184 навсегда, даже если у меня есть opend. Если вы установитеandroid:windowTranslucentStatus
значение false, он вернёт высоту правильно, если ime невидим, он вернёт 1134 (не включая строку состояния). Закройте ime, возможно, вернётся 5xx (зависит от высоты ime)Я не знаю, погода ли это, я пробовал на 4.4.4 и 5.0.1, результат тот же.
Итак, до сих пор, второй наиболее согласованный ответ, решение Качи будет самым безопасным способом для расчета высоты им. Вот копия:
источник
Метод, который который не нуждается в LayoutListener
В моем случае я хотел бы сохранить состояние клавиатуры перед заменой моего фрагмента. Я вызываю метод hideSoftInputFromWindow из
onSaveInstanceState
, который закрывает клавиатуру и возвращает меня была ли клавиатура видна или нет.Этот метод прост, но может изменить состояние вашей клавиатуры.
источник
Я знаю, что это старый пост, но я думаю, что это самый простой из известных мне подходов, и моим тестовым устройством является Nexus 5. Я не пробовал его на других устройствах. Надеюсь, что другие поделятся своим подходом, если они найдут мой код нехорошим :)
imm.hideSoftInputFromWindow возвращает логическое значение.
Спасибо,
источник
Вышеуказанная функция используется для проверки видимости клавиатуры. Если это так, то я закрываю это.
Ниже показаны два необходимых метода.
Сначала определите работоспособную высоту окна в onCreate.
Затем добавьте логический метод, который получает высоту окна в этом экземпляре. Если он не соответствует оригиналу (при условии, что вы не меняете его по пути ...), клавиатура открыта.
Frotz!
источник
Я знаю, как точно вы можете определить, скрыта клавиатура или нет.
Это работает для планшетов. Когда панель навигации отображается горизонтально.
источник