このコードが機能しない理由がわかりません。バックスペースとリターンキーのみが検出されます。リスナーは他のキーに対して起動しません。私のデバイスはNexusOneです。
アクティビティのOnKeyDownメソッドをオーバーライドしようとしましたが、それはさらに悪いことです。検出されたボタンはハードウェアの戻るボタンだけでした。
TextWatcherとonTextChangedを使用するという提案が出回っていますが、それが機能する場合もありますが、実際の回避策ではありません。たとえば、テキストボックスが空の場合、ユーザーがBackSpace(Delete)ボタンを押したかどうかは検出されません。だから何かアイデア?
TextView txtInput = (TextView)findViewById(R.id.txtInput);
txtInput.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
makeToast(keyCode + " key pressed");
return true;
}
});
OK。やっと自分のやりたいことを思いついたのですが、Androidを誇りに思っていません。
クライアントでSoftKeyboardを開き、押されたキー(文字とDELキー)を送信する必要があるサーバー/クライアントアプリケーションを書いています...キーが押されるたびに、その文字がサーバーに送信されます。 DELを押すと、シーケンス{BS}がサーバーに送信されます。
そのためには、EditTextが空でユーザーがDelキーを押した場合を除いて、適切に機能するTextWatcherとonTextChangeを実装する必要がありました。 EditTextに変更がないため、DELキーが押されたことを検出する方法はありません。
TextWatcherに加えて、EditTextコントロールにアタッチしたonKeyListenerを実装する必要がありました。このonKeyListenerは、DELとRETURNを除くSoftKeyboardのすべてのキーを無視します。理由がわかりませんか?たぶんバグ?
これが私のコードです:
TextView txtInput = (TextView)findViewById(R.id.txtInput);
txtInput.addTextChangedListener(inputTextWatcher);
txtInput.setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
Log.d(TAG, keyCode + " character(code) to send");
return false;
}
});
そしてTextWatcher ....
private TextWatcher inputTextWatcher = new TextWatcher() {
public void afterTextChanged(Editable s) { }
public void beforeTextChanged(CharSequence s, int start, int count, int after)
{ }
public void onTextChanged(CharSequence s, int start, int before, int count) {
Log.d(TAG, s.charAt(count-1) + " character to send");;
}
};
ここで1つの間違いをしました。
そうすべき return true
、イベントを処理した場合。 イベントを次のレシーバーで処理できるようにする、return false
あなたは常に真を返しています
注:edittextでのinputtypeの言及。
<EditText Android:id="@+id/select_category"
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:inputType="textCapSentences|textAutoCorrect" >
edittext.setOnEditorActionListener(new OnEditorActionListener() {
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
if ((actionId & EditorInfo.IME_MASK_ACTION) == EditorInfo.IME_ACTION_DONE) {
//do something here.
return true;
}
return false;
}
});
そのビューに特定のリスナーサブクラスを使用してみましたか?
EditTextでも同様の問題がありました。以下のコードは機能しました:
private OnKeyListener keyListener = new EditText.OnKeyListener(){
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
EditText et = (EditText) v;
Log.i("APPEVENT", "Key hit: "+ event);
//...
return false;
}
};
しかし、View.OnKeyListener
を使用した場合は、バックスペースを記録して入力するだけです。 TextView
でも同様の問題である可能性があります。おそらく、サブクラスのキーリスナーは、指定されたView
サブクラスのより多くのイベントに敏感です。
参照元:
http://developer.Android.com/reference/Android/view/View.OnKeyListener.html
View.OnKeyListener
クラスの概要ハードウェアキーイベントがこのビューにディスパッチされたときに呼び出されるコールバックのインターフェイス定義。コールバックは、キーイベントがビューに渡される前に呼び出されます。これは、ハードウェアキーボードにのみ役立ちます。ソフトウェア入力方式には、このリスナーをトリガーする義務はありません。
OnKeyListenerはハードウェアキー専用に設計されたようです!
IPhoneでもTextWatcherの問題が発生しました。バッファが空の場合、キーボードはdelイベントを送信しません。キーボードバッファに1000文字をプリロードすることで回避しました。幸い、私たちのアプリは編集フィールドをキーボードの後ろに隠したので、1000文字は表示されません。それは醜いですが、それは機能します(ユーザーがデータを入力する前に連続して1000回の削除をヒットしない限り!)