Отключить ввод EditText, сохраняя при этом фокусировку
У меня есть поле EditText
, имя переменной valueInputField
.
Я слушаю изменение ввода текста, чего хочу достичь во время ввода, когда формат ввода НЕ соответствует регулярному выражению, я хотел бы прекратить показывать больше входов, но сохранить фокусировку поля и пользователь может набрать клавиатура все еще только, что никакой реальный эффект не выйдет на поле.
@OnTextChanged(R.id.value_input)
protected void onTextChanged(CharSequence charSequence) {
String inputChars = charSequence.toString().trim();
// if doesn't match regular expression, stop showing more inputs
if (!inputChars.matches(MY_REGEXP)) {
// this doesn't achieve what I need.
valueInputField.setInputType(0)
}
}
Я пробовал выше, это не работает. Как достичь того, что мне нужно?
Ответы
Ответ 1
Вы должны добавить InputFilter в свой textView:
вот пример:
editText.filters = arrayOf(object: InputFilter {
override fun filter(source: CharSequence?, start: Int, end: Int, dest: Spanned?, dstart: Int, dend: Int): CharSequence {
if (Regex("[0-9]*").matches(source!!)) {
return source
} else {
return source.subSequence(start, end-1)
}
}
})
Этот метод фильтра вызывается каждый раз, когда вызывается вход в editText. Вы можете вернуть исходный код, когда он соответствует регулярному выражению, в противном случае вы можете вернуть subSequence источника без последнего вставленного символа.
Пример кода в Kotlin, перевод не должен давать вам никаких проблем :)
Ответ 2
Вы уже используете setInputType(InputType.TYPE_NULL)
. Но он должен использоваться с setEnabled(false)
чтобы заставить его работать.
Это также изменит цвет фона. Это настоятельно рекомендуется, поскольку дает пользователю понять, что он не будет принимать входные данные. Однако вы можете изменить его как setBackgroundColor(Color.TRANSPARENT)
если хотите.
Если вы хотите скрыть курсор, добавьте setCursorVisible(false)
.
В качестве альтернативы вы можете использовать afterTextChanged
вместо onTextChanged
чтобы вы могли манипулировать текстом.
Ответ 3
возможно, вы должны попробовать ниже логики
maxLength=inputChars.length
if (!inputChars.matches(MY_REGEXP)) {
editText.setFilters(new InputFilter[] {new InputFilter.LengthFilter(maxLength)});
}
выше программа установит максимальную длину EditText, если она не соответствует регулярному выражению.
Ответ 4
Отключение ввода типа для редактирования текста не работает должным образом, когда его фокусировка или редактирование. После того, как вы установите для типа inout значение null, представление начнет принимать методы обратного вызова нажатия клавиши. Итак, у меня есть переменная класса для проверки поля и отмены нажатых клавиш. Вот пример кода.
public class SplashActivity extends AppCompatActivity{
EditText valueInputField;
private boolean allowValueField2Edit = true;
@Override
protected void onCreate(Bundle savedInstanceState) {
....
valueInputField.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2{
}
@Override
public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {
String inputChars = charSequence.toString().trim();
// if doesn't match regular expression, stop showing more inputs
if (!inputChars.matches(MY_REGEXP)) {
// this doesn't achieve what I need.
valueInputField.setInputType(InputType.null);
allowValueField2Edit = false;
}
}
@Override
public void afterTextChanged(Editable editable) {
}
});
//Once you set the input type to none fore edit control, on Key lister will receive callbacks
valueInputField.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View view, int i, KeyEvent keyEvent) {
//Here, you can add your custom logic to have key actions.
//retrun false will have key effect, return true
return !allowValueField2Edit;
}
});
Надеюсь это поможет...
Ответ 5
Если вы хотите остановить предложения в текстовом редакторе, вы должны попробовать что-то вроде:
editText.setInputType(InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS);
И чтобы включить снова после любого условия, используйте это:
editText.setInputType(InputType. TYPE_CLASS_TEXT);
Вот пример с вводом с порогом размера, здесь также следует работать с вашим регулярным выражением:
editText.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
if(s.length()< threshold){
editText.setInputType(InputType. TYPE_CLASS_TEXT);
}
if(s.length()>= threshold){
editText.setInputType(InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS);
}
}
@Override
public void afterTextChanged(Editable s) {
}
});
Ответ 6
Метод matcher lookingAt() работает как метод matches() с одним существенным отличием. Метод lookAt() соответствует только регулярному выражению в начале текста, а match() соответствует регулярному выражению для всего текста. Другими словами, если регулярное выражение соответствует началу текста, но не всему тексту, lookAt() вернет true, а match() вернет false.
Вот пример Matcher.lookingAt():
String text = "This is the text to be searched " + "for occurrences of the http:// pattern.";
String patternString = "This is the";
Pattern pattern = Pattern.compile(patternString, Pattern.CASE_INSENSITIVE);
Matcher matcher = pattern.matcher(text);
String lookingat = ("lookingAt = " + matcher.lookingAt());
String matches= ("matches = " + matcher.matches());
Этот пример соответствует регулярному выражению "this is" как от начала текста, так и от всего текста. Согласование регулярного выражения с началом текста (lookAt()) вернет true.
Согласование регулярного выражения со всем текстом (matches()) вернет false, потому что текст имеет больше символов, чем регулярное выражение. Регулярное выражение говорит, что текст должен соответствовать тексту "Это точно", без дополнительных символов до или после выражения.
Ответ 7
псевдокод:
- дождитесь, пока текст ввода будет соответствовать вашему шаблону
- когда совпадение найдено, установите фильтр
- фильтр должен будет вернуть одну и ту же предыдущую строку при каждом нажатии клавиши
Исходный код:
editText.addTextChangedListener(new TextWatcher() {
...
@Override
public void afterTextChanged(Editable editable) {
String text = editable.toString();
// STEP 1
if(text.matches(myRegex) && !flag) {
// make sure that this code block is executed only once
flag = true;
// STEP 2
// when match is found, always return the same string
// therefore disabling further editing of the editText field
editText.setFilters(new InputFilter[]{
new InputFilter() {
@Override
public CharSequence filter(CharSequence charSequence, int i, int i1,
Spanned spanned, int i2, int i3) {
// STEP 3
return spanned.subSequence(i2, i3);
}
}
});
}
}
});
При настройке входного фильтра, пожалуйста, обратите внимание на правильный способ его выполнения. Пожалуйста, проверьте этот ответ от Стивена Байла.