检测用户何时解除软键盘

我在我的视图中有一个EditText小部件。 当用户selectEditText小部件时,我会显示一些说明,并出现软键盘。

我使用OnEditorActionListener来检测用户何时完成文本input,然后closures键盘,隐藏指令并执行一些操作。

我的问题是当用户按BACK键closures键盘。 操作系统closures键盘,但我的指示(我需要隐藏)仍然可见。

我已经尝试覆盖OnKeyDown,但是当BACKbutton被用来closures键盘时,这似乎不会被调用。

我已经尝试在EditText小部件上设置OnKeyListener,但似乎并没有被调用。

我怎样才能检测软键盘被解雇?

这个问题(没有答案,看起来严峻)似乎是问同样的问题: 如何检查Android软件键盘的可见性?

我知道一个办法做到这一点。 子类EditText并实现:

@Override public boolean onKeyPreIme(int keyCode, KeyEvent event) { if (event.getKeyCode() == KeyEvent.KEYCODE_BACK) { // Do your thing. return true; // So it is not propagated. } return super.dispatchKeyEvent(event); } 

这是一个关于如何使用自定义视图的链接(用于子类EditText时): http : //developer.android.com/guide/topics/ui/custom-components.html

周杰伦,你的解决scheme很好! 谢谢 :)

 public class EditTextBackEvent extends EditText { private EditTextImeBackListener mOnImeBack; public EditTextBackEvent(Context context) { super(context); } public EditTextBackEvent(Context context, AttributeSet attrs) { super(context, attrs); } public EditTextBackEvent(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); } @Override public boolean onKeyPreIme(int keyCode, KeyEvent event) { if (event.getKeyCode() == KeyEvent.KEYCODE_BACK && event.getAction() == KeyEvent.ACTION_UP) { if (mOnImeBack != null) mOnImeBack.onImeBack(this, this.getText().toString()); } return super.dispatchKeyEvent(event); } public void setOnEditTextImeBackListener(EditTextImeBackListener listener) { mOnImeBack = listener; } } public interface EditTextImeBackListener { public abstract void onImeBack(EditTextBackEvent ctrl, String text); } 

我通过调用super.onKeyPreIme()在Jay的解决scheme上做了一些小改动:

 _e = new EditText(inflater.getContext()) { @Override public boolean onKeyPreIme(int keyCode, KeyEvent event) { if (event.getKeyCode() == KeyEvent.KEYCODE_BACK){ cancelTextInput(); } return super.onKeyPreIme(keyCode, event); } }; 

精彩的解决scheme,Jay,+1!

这是我的自定义EditText检测键盘是否显示

 /** * Created by TheFinestArtist on 9/24/15. */ public class KeyboardEditText extends EditText { public KeyboardEditText(Context context) { super(context); } public KeyboardEditText(Context context, AttributeSet attrs) { super(context, attrs); } public KeyboardEditText(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @Override protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) { super.onFocusChanged(focused, direction, previouslyFocusedRect); if (listener != null) listener.onStateChanged(this, true); } @Override public boolean onKeyPreIme(int keyCode, @NonNull KeyEvent event) { if (event.getKeyCode() == KeyEvent.KEYCODE_BACK && event.getAction() == KeyEvent.ACTION_UP) { if (listener != null) listener.onStateChanged(this, false); } return super.onKeyPreIme(keyCode, event); } /** * Keyboard Listener */ KeyboardListener listener; public void setOnKeyboardListener(KeyboardListener listener) { this.listener = listener; } public interface KeyboardListener { void onStateChanged(KeyboardEditText keyboardEditText, boolean showing); } } 

只要创build一个扩展Edittext的类并在代码中使用该edittext,就应该在自定义edittext中重写下面的方法:

 @Override public boolean onKeyPreIme(int keyCode, KeyEvent event) { if (keyCode == KeyEvent.KEYCODE_BACK) { //Here it catch all back keys //Now you can do what you want. } else if (keyCode == KeyEvent.KEYCODE_MENU) { // Eat the event return true; } return false;} 

这是关键监听器的解决scheme。 我不知道为什么这个工作,但OnKeyListener的作品,如果你只是在你的自定义EditText上重写onKeyPreIme。

SomeClass.java

 customEditText.setOnKeyListener((v, keyCode, event) -> { if(event.getAction() == KeyEvent.ACTION_DOWN) { switch (keyCode) { case KeyEvent.KEYCODE_BACK: getPresenter().onBackPressed(); break; } } return false; }); 

CustomEditText.java

 @Override public boolean onKeyPreIme(int keyCode, KeyEvent event) { return super.dispatchKeyEvent(event); }