Отключить программную клавиатуру на NumberPicker - PullRequest
162 голосов
/ 13 января 2012

Я пытаюсь отключить программную клавиатуру при использовании NumberPicker для ввода числовых значений (по эстетическим соображениям).Это мой макет xml-кода:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >

    <LinearLayout
        android:id="@+id/linearLayout2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_horizontal"
        android:layout_marginBottom="30dp"
        android:layout_marginTop="30dp" >

        <NumberPicker
            android:id="@+id/repetitionPicker"
            android:layout_width="40dp"
            android:layout_height="wrap_content" />

        <TextView
            android:id="@+id/textView1"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical"
            android:text="@string/repetitions_short_divider"
            android:textAppearance="?android:attr/textAppearanceMedium" />

        <NumberPicker
            android:id="@+id/weightPicker"
            android:layout_width="40dp"
            android:layout_height="wrap_content"
            android:layout_marginLeft="40dp" />

        <TextView
            android:id="@+id/textView2"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical"
            android:text="@string/pounds"
            android:textAppearance="?android:attr/textAppearanceMedium" />
    </LinearLayout>


    <Button
        android:id="@+id/saveButton"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center_horizontal"
        android:text="@string/save" />

</LinearLayout>

И, наконец, это код, в котором я пытаюсь заблокировать клавиатуру в методе onCreate () - метод:

// hide keyboard
View.OnClickListener disableKeyBoardListener = new View.OnClickListener() {
    public void onClick(View v) {
        ((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE))
                .hideSoftInputFromWindow(v.getWindowToken(), InputMethodManager.HIDE_NOT_ALWAYS);
    }
};

((EditText) weightPicker.getChildAt(1)).setInputType(InputType.TYPE_NULL);
((EditText) repetitionPicker.getChildAt(1)).setInputType(InputType.TYPE_NULL);

((EditText) weightPicker.getChildAt(1)).setOnClickListener(disableKeyBoardListener);
//((EditText) repetitionPicker.getChildAt(1)).setOnClickListener(disableKeyBoardListener);
//weightPicker.setOnClickListener(disableKeyBoardListener);
//repetitionPicker.setOnClickListener(disableKeyBoardListener);     

getWindow().setSoftInputMode(
        WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN); 

К сожалению,программная клавиатура по-прежнему отображается при нажатии на NumberPicker.Есть идеи?

Ответы [ 10 ]

455 голосов
/ 03 февраля 2012

Только что нашел это, и он работает как шарм:

myNumberPicker.setDescendantFocusability(NumberPicker.FOCUS_BLOCK_DESCENDANTS);

Вы также можете установить это в XML:

android:descendantFocusability="blocksDescendants" 
53 голосов
/ 01 августа 2015

XML-версия ответа Эндрю Уэббера

android:descendantFocusability="blocksDescendants"

Пример

<NumberPicker
        android:id="@+id/your_numberpicker"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:descendantFocusability="blocksDescendants"/>
7 голосов
/ 17 января 2012

После прочтения исходного кода com / android / internal / widget / NumberPicker.java я нашел следующее решение:

// Hide soft keyboard on NumberPickers by overwriting the OnFocusChangeListener
OnFocusChangeListener fcl = new OnFocusChangeListener() {
    public void onFocusChange(View v, boolean hasFocus) {
        // Do nothing to suppress keyboard
    }
};

((EditText) numberPicker.getChildAt(1)).setOnFocusChangeListener(fcl);

// Suppress soft keyboard from the beginning
((EditText) numberPicker.getChildAt(1)).setInputType(InputType.TYPE_NULL);
6 голосов
/ 21 января 2012

Просто улучшил ответ @MaxVogler (так что если вы хотите проголосовать и за этот голос @MaxVogler) и сделайте его хакеромТакже нам не нужно звонить setOnFocusChangeListener и setInputType.Подойдет только setFocusable для false.

Ниже приведен вспомогательный API для включения / отключения функции

public static void enableNumberPickerManualEditing(NumberPicker numPicker,
        boolean enable) {
    int childCount = numPicker.getChildCount();

    for (int i = 0; i < childCount; i++) {
        View childView = numPicker.getChildAt(i);

        if (childView instanceof EditText) {
            EditText et = (EditText) childView;
            et.setFocusable(enable);
            return;
        }
    }
}
4 голосов
/ 08 мая 2014

Вот еще один способ сделать это, который позволяет пользователю по-прежнему редактировать число, если он хочет - он просто подавляет программную клавиатуру на начальном этапе. Используйте NumberPicker.setDescendantFocusability(FOCUS_BLOCK_DESCENDANTS), чтобы отключить экранную клавиатуру, когда интерфейс впервые отображается согласно ответам выше. Затем заставьте ваш диалог или занятие реализовать View.OnTouchListener, вызовите setOnTouchListener(this) на вашем NumberPicker, а в вашей реализации onTouch(View v,MotionEvent e) сбросьте фокусируемость потомков номерного выбора до его нормального значения, а затем верните false.

Возвращение false означает, что касание все еще обрабатывается NumberPicker, что означает, что если пользователь нажимает на поле редактирования, появляется программная клавиатура. Это как раз то, что я хотел, столкнувшись с той же проблемой - когда программная клавиатура выводит диалоговое окно, когда оно появляется впервые, вызывает недовольство, поскольку оно сдвигает диалоговое окно вверх после его появления.

public class GetBufferDialog extends DialogFragment implements View.OnTouchListener {

после создания диалога в методе onCreateDialog() и поиска NumberPicker:

m_oldFocus = m_numberpicker.getDescendantFocusability();
m_numberpicker.setDescendantFocusability(NumberPicker.FOCUS_BLOCK_DESCENDANTS); 
m_numberpicker.setOnTouchListener(this);

и вот метод OnTouch:

public boolean onTouch(View v, MotionEvent event) {
    m_numberpicker.setDescendantFocusability(m_oldFocus);
    return false;
}
2 голосов
/ 15 мая 2014

Самым простым, что я нашел для работы, было:

numberPicker               = (NumberPicker) myDialogView.findViewById(R.id.myViewId);
EditText numberPickerChild = (EditText) numberPicker.getChildAt(0);
numberPickerChild.setFocusable(false);
numberPickerChild.setInputType(InputType.TYPE_NULL);
1 голос
/ 20 мая 2018

Если вы хотите скрыть программную клавиатуру только при загрузке представления с помощью средства выбора номеров, но при этом хотите, чтобы пользователи могли редактировать после загрузки представления, то вам не следует блокировать возможность фокусировки по потомкам.Вместо этого просто не позволяйте сборщику чисел быть первым сфокусированным элементом в вашем представлении.

Подробнее см. в этом ответе .

На основе приведенного выше ответа:

    <!-- Dummy item to prevent Number Picker from receiving focus -->
    <LinearLayout        
        android:focusable="true" 
        android:focusableInTouchMode="true"
        android:layout_width="0px" 
        android:layout_height="0px"/>

    <!-- :nextFocusUp and :nextFocusLeft have been set to the id of this component 
         to prevent the dummy from receiving focus again -->
    <NumberPicker 
        android:id="@+id/number_picker"
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content"
        android:nextFocusUp="@id/number_picker" 
        android:nextFocusLeft="@id/number_picker"/>
1 голос
/ 13 марта 2018

Я не знаю, почему это работает, но настройка OnClickListener, которая ничего не делает, не позволяет клавиатуре показывать (Lollipop)

numberPicker.setOnClickListener(new View.OnClickListener() {
  @Override
  public void onClick(View view) {
  }
});
0 голосов
/ 17 апреля 2019

Рабочий код Программно:

mp.setDescendantFocusability(NumberPicker.FOCUS_BLOCK_DESCENDANTS);

XML:

android:descendantFocusability="blocksDescendants" 
0 голосов
/ 10 июля 2015
/**
 * set focus to top level window
 * disposes descendant focus
 * disposes softInput
 * @param context - activity context
 * @param enable - state of focus
 * */
public static void topLevelFocus(Context context, boolean enable){
    if(Activity.class.isAssignableFrom(context.getClass())){
        ViewGroup tlView = (ViewGroup) ((Activity) context).getWindow().getDecorView();
        if(tlView!=null){
            tlView.setFocusable(enable);
            tlView.setFocusableInTouchMode(enable);
            tlView.setDescendantFocusability(ViewGroup.FOCUS_BEFORE_DESCENDANTS);
            tlView.requestFocus();
        }
    }
}

* позвонив по этому номеру:

  • не будет блокировать возможность фокусировки по потомкам (средство выбора номера будет редактируемым)

  • скрывает программный ввод при создании

  • before (обработка ввода) getValue () позволит получить правильное значение


...