Кнопка Detect delete на мягкой клавиатуре
У меня есть два EditText (каждый принимает только один символ), и я хочу обрабатывать оба поля, например, у меня было только одно.
Я использую TextWatcher для установки фокуса во втором, когда пользователь пишет символ в первом, но я не знаю, как сделать обратное.
Если пользователь нажмет кнопку удаления во втором EditText (будучи пустым редактором EditText), я хочу переместить фокус на первый EditText и удалить там символ.
Проблема заключается в том, что TextWatcher не работает, когда пользователь пытается удалить пустое поле (потому что на самом деле ничего не меняется). И событие onKeyDown работает только с жесткими клавиатурами, поэтому я не знаю, как справиться с этой проблемой...
Спасибо!
Ответы
Ответ 1
Возможный дубликат Событие с удалением (backspace) Android EditText
только что проверил код из этого вопроса (который действительно пришел из предоставленного вопроса и ответил Labeeb P) с тестовым проектом с двумя изменениями в макете, и, похоже, он работает нормально - я могу получить удаление даже если редактирование пуст.
final EditText edit1 = (EditText) findViewById(R.id.editText1);
edit1.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
// You can identify which key pressed buy checking keyCode value
// with KeyEvent.KEYCODE_
if (keyCode == KeyEvent.KEYCODE_DEL) {
// this is for backspace
Log.e("IME_TEST", "DEL KEY");
}
return false;
}
});
Кажется, что документация по редактированию EditText должна быть более понятной или, по крайней мере, любое руководство для взаимодействия с EditText - Soft Keyboard, потому что есть много типичных, которые должны быть разработаны почти каждым разработчиком.
UPDATE:
Похоже, что этот способ не работает на последних версиях Android (по крайней мере после версии 4.1). Этот ответ, похоже, работает с версиями после 4.1.
Ответ 2
Более простое решение этого вопроса, на которое я наткнулся, - использование InputFilter. Метод filter()
InputFilter filter()
видимому, сообщает обо всех событиях программной клавиатуры - даже тех, в которых значение EditText не изменяется.
Поэтому для решения вашей конкретной ситуации создайте входной фильтр и установите соответственно:
private InputFilter filter = (charSequence, start, end, dest, dStart, dEnd) -> {
if (end == 0 || dStart < dEnd) {
// backspace was pressed! handle accordingly
}
return charSequence;
};
...
myEditText.setFilters(new InputFilter[] { filter });
События Backspace можно оценивать с помощью end
, dStart
и dEnd
. dStart
всегда будет меньше dEnd
если символ был удален. Если EditText
пуст, вы все равно можете оценить нажатия на клавишу возврата, проверив, имеет ли end
== 0.
Обратите внимание, что массовое удаление также будет отражено в этом операторе if
, поэтому вы можете выполнить дополнительную проверку с помощью filter()
. Также обратите внимание, что если вы используете клавиатуру компьютера для ввода в EditTexts в эмуляторах, вы можете получить неожиданные результаты. Лучше всего нажимать программные кнопки для тестирования.
Ответ 3
Используйте расширение, предоставленное по адресу https://github.com/ciasaboark/Android-Shell/blob/master/src/com/example/com/programmingthetux/tutorial/ZanyEditText.java
import java.util.Random;
import android.content.Context;
import android.util.AttributeSet;
import android.view.KeyEvent;
import android.view.inputmethod.EditorInfo;
import android.view.inputmethod.InputConnection;
import android.view.inputmethod.InputConnectionWrapper;
import android.widget.EditText;
/**
* Created by mkallingal on 4/25/2016.
*/
public class CustomEditText extends EditText {
private Random r = new Random();
public CustomEditText(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public CustomEditText(Context context, AttributeSet attrs) {
super(context, attrs);
}
public CustomEditText(Context context) {
super(context);
}
public void setRandomBackgroundColor() {
}
@Override
public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
return new ZanyInputConnection(super.onCreateInputConnection(outAttrs),
true);
}
private class ZanyInputConnection extends InputConnectionWrapper {
public ZanyInputConnection(InputConnection target, boolean mutable) {
super(target, mutable);
}
@Override
public boolean sendKeyEvent(KeyEvent event) {
if (event.getAction() == KeyEvent.ACTION_DOWN
&& event.getKeyCode() == KeyEvent.KEYCODE_DEL) {
CustomEditText.this.setRandomBackgroundColor();
// Un-comment if you wish to cancel the backspace:
// return false;
}
return super.sendKeyEvent(event);
}
@Override
public boolean deleteSurroundingText(int beforeLength, int afterLength) {
// magic: in latest Android, deleteSurroundingText(1, 0) will be called for backspace
if (beforeLength == 1 && afterLength == 0) {
// backspace
return sendKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_DEL))
&& sendKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_DEL));
}
return super.deleteSurroundingText(beforeLength, afterLength);
}
}
}
Теперь вы можете использовать его в своей деятельности следующим образом:
final CustomEditText editText = new CustomEditText(cxt);
editText.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_DEL) {
String _text= editText.getText().toString();
if(StringUtils.isBlank(_text))
//editText is now empty
}
}
return false;
}
});
Ответ 4
Я достиг этого, переопределив EditText
, чтобы получить доступ к объекту InputConnection
, который содержит метод deleteSurroundingText
. Это помогает обнаружить событие удаления (backspace). Пожалуйста, взгляните на решение, которое я ему предоставил: Android - не удается захватить backspace/delete, нажмите soft. клавиатура
Это решение работает правильно как для hardKeyboard, так и для softKeyboard.