Как скрыть мягкую клавиатуру изнутри фрагмента?
У меня есть FragmentActivity
, используя ViewPager
для обслуживания нескольких фрагментов. Каждый из них является ListFragment
со следующим расположением:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="8dp">
<ListView android:id="@id/android:list"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
<EditText android:id="@+id/entertext"
android:layout_width="fill_parent"
android:layout_height="wrap_content" />
</LinearLayout>
</LinearLayout>
При запуске активности отображается мягкая клавиатура. Чтобы исправить это, я сделал следующее внутри фрагмента:
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
//Save the container view so we can access the window token
viewContainer = container;
//get the input method manager service
imm = (InputMethodManager)getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
. . .
}
@Override
public void onStart() {
super.onStart();
//Hide the soft keyboard
imm.hideSoftInputFromWindow(viewContainer.getWindowToken(), 0);
}
Я сохраняю входящий параметр ViewGroup container
из onCreateView
в качестве способа доступа к токену окна для основного действия. Это выполняется без ошибок, но клавиатура не скрывается от вызова до hideSoftInputFromWindow
в onStart
.
Первоначально я пытался использовать раздутый макет вместо container
, i.e:
imm.hideSoftInputFromWindow(myInflatedLayout.getWindowToken(), 0);
но это запустило NullPointerException
, предположительно потому, что сам фрагмент не является активностью и не имеет уникального токена окна?
Есть ли способ скрыть мягкую клавиатуру внутри фрагмента или создать метод в FragmentActivity
и вызвать его из фрагмента?
Ответы
Ответ 1
Пока ваш фрагмент создает представление, вы можете использовать IBinder (токен окна) из этого представления после его присоединения. Например, вы можете переопределить onActivityCreated в своем фрагменте:
@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
final InputMethodManager imm = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(getView().getWindowToken(), 0);
}
Ответ 2
Для меня работала только следующая строка кода:
getActivity().getWindow().setSoftInputMode(
WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
Ответ 3
Если вы добавите следующий атрибут в определение манифеста активности, он полностью отключит клавиатуру от всплытия при открытии вашей активности. Надеюсь, это поможет:
(Добавить в определение манифеста вашей активности):
android:windowSoftInputMode="stateHidden"
Ответ 4
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_my, container,
false);
someClass.onCreate(rootView);
return rootView;
}
Храните экземпляр моего корневого представления в моем классе
View view;
public void onCreate(View rootView) {
view = rootView;
Используйте представление, чтобы скрыть клавиатуру.
public void removePhoneKeypad() {
InputMethodManager inputManager = (InputMethodManager) view
.getContext()
.getSystemService(Context.INPUT_METHOD_SERVICE);
IBinder binder = view.getWindowToken();
inputManager.hideSoftInputFromWindow(binder,
InputMethodManager.HIDE_NOT_ALWAYS);
}
Ответ 5
Исключение для DialogFragment
, хотя фокус встроенного Dialog
должен быть скрыт, вместо этого только первый EditText
внутри встроенного Dialog
this.getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
Ответ 6
в Fragemnt Работа с этим кодом
getActivity().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
Ответ 7
это будет работать в моем случае, когда во вкладках я переключаюсь с одного фрагмента на другой
@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
super.setUserVisibleHint(isVisibleToUser);
if (isVisibleToUser) {
try {
InputMethodManager mImm = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
mImm.hideSoftInputFromWindow(getView().getWindowToken(), 0);
mImm.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(), 0);
} catch (Exception e) {
Log.e(TAG, "setUserVisibleHint: ", e);
}
}
}
Ответ 8
Используйте этот статический метод из любого места (Activity/Fragment), которое вам нравится.
public static void hideKeyboard(Activity activity) {
try{
InputMethodManager inputManager = (InputMethodManager) activity
.getSystemService(Context.INPUT_METHOD_SERVICE);
View currentFocusedView = activity.getCurrentFocus();
if (currentFocusedView != null) {
inputManager.hideSoftInputFromWindow(currentFocusedView.getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
}
}catch (Exception e){
e.printStackTrace();
}
}
Если вы хотите использовать для фрагмента, просто вызовите hideKeyboard(((Activity) getActivity()))
.
Ответ 9
Ничего из этого не работало на API27. Мне пришлось добавить это в контейнер макета, для меня это был ConstraintLayout:
<android.support.constraint.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:focusable="true"
android:focusableInTouchMode="true"
android:focusedByDefault="true">
//Your layout
</android.support.constraint.ConstraintLayout>
Ответ 10
Просто добавьте эту строку в ваш код:
getActivity().getWindow().setSoftInputMode(
WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
Ответ 11
В Котлине:
(activity?.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager).hideSoftInputFromWindow(view?.windowToken,0)