我有一个编辑文本,在我的应用程序中用作搜索框。在我的Nexus 7上的Jelly Bean中,当我在正在监听的文本框中输入内容并点击时,输入KeyEvent = null并将ActionId = 0传递给onEditorAction()方法。有人遇到过这种情况么?我认为这可能是一个错误。
在下面的第二个if语句中,我得到一个空指针,因为actionId = 0和KeyEvent = null;
// Search field logic.
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
Log.d(TAG, "onEditorAction");
if (event != null && event.getAction() != KeyEvent.ACTION_DOWN)
return false;
if (actionId == EditorInfo.IME_ACTION_SEARCH
|| event.getKeyCode() == KeyEvent.KEYCODE_ENTER) {
.....Do some stuff();
}
}
答案 0 :(得分:40)
结束为KeyEvent添加空检查。感谢commonsware指出这种情况发生在3.0+。似乎更像是一种解决方法,然后是解决方案,但它确实有效。
// Search field logic.
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
Log.d(TAG, "onEditorAction");
if (event != null && event.getAction() != KeyEvent.ACTION_DOWN) {
return false;
} else if (actionId == EditorInfo.IME_ACTION_SEARCH
|| event == null
|| event.getKeyCode() == KeyEvent.KEYCODE_ENTER) {
.....Do some stuff();
}
}
答案 1 :(得分:6)
我发现了我的"类似bug的行为"是由于imeActionLabel
使事情复杂化。我只使用它,因为在Text Fields Guide中提到它是一种拥有自定义返回键标签的方法。以下是我在Lollipop的测试结果,
案例1:默认,返回键符号=结束尖括号
<EditText
android:singleLine="true"
android:inputType="textUri"/>
onEditorAction被调用一次。
EditorInfo.IME_ACTION_NEXT
案例2: imeOptions
,返回键符号=选中标记
<EditText
android:singleLine="true"
android:inputType="textUri"
android:imeOptions="actionDone"/>
onEditorAction被调用一次。
EditorInfo.IME_ACTION_DONE
案例3: imeActionLabel
,返回键符号=&#34; URdone&#34;
<EditText
android:singleLine="true"
android:inputType="textUri"
android:imeOptions="actionDone"
android:imeActionLabel="URdone"/>
onEditorAction可以多次调用。
KeyEvent = null,actionId = 0
KeyEvent = KeyEvent.ACTION_DOWN
,actionId = 0
KeyEvent = KeyEvent.ACTION_UP
,actionId = 0
注意:
我不确定actionId = 0是来自EditorInfo.IME_ACTION_UNSPECIFIED
还是EditorInfo.IME_NULL
。
如果下一个可聚焦是不可编辑的,则返回键符号将变为左箭头。
您还可以使用setOnFocusChangeListener
覆盖onFocusChange
,这将根据上述光标行为进行调用。
答案 2 :(得分:3)
在KeyEvent.ACTION_UP
旁边,我们还需要捕获KeyEvent.ACTION_DOWN
。除非KeyEvent.ACTION_UP
永远不会传递给EditText
,否则我们的onEditorAction
将无效。
例如:
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
final boolean isEnterEvent = event != null
&& event.getKeyCode() == KeyEvent.KEYCODE_ENTER;
final boolean isEnterUpEvent = isEnterEvent && event.getAction() == KeyEvent.ACTION_UP;
final boolean isEnterDownEvent = isEnterEvent && event.getAction() == KeyEvent.ACTION_DOWN;
if (actionId == EditorInfo.IME_ACTION_DONE || isEnterUpEvent ) {
// Do your action here
performLogin();
return true;
} else if (isEnterDownEvent) {
// Capture this event to receive ACTION_UP
return true;
} else {
// We do not care on other actions
return false;
}
}
您必须根据EditorInfo.IME_ACTION_DONE
EditorInfo.IME_ACTION_
以更正android:imeOptions="actionNext"
的版本
答案 3 :(得分:1)
值得注意的是,点击Enter可以获得多个事件(取决于Android版本)。一个用于KeyDown(KeyEvent.ACTION_DOWN),一个用于KeyUp(KeyEvent.ACTION_UP)。当我忘记检查我是否意外启动了两次服务器调用以进行相同的操作时。
searchBox.setOnEditorActionListener(new OnEditorActionListener() {
// enter key in search box triggers search
@Override
public boolean onEditorAction(TextView v, int actionId,
KeyEvent event) {
if ((event != null && event.getAction() == KeyEvent.ACTION_UP) || event==null) {
onSearchButtonClicked();
}
return true;
}
});
答案 4 :(得分:1)
如果您自定义返回键,则不会发现真相。您需要在布局中设置 imeActionLabel 和 imeActionId 。如:
int ch_search(char array_to_search[], char char_to_search_for, int array_size)
{
char *buffer = malloc(array_size + 1);
// Add test here to check if malloc was succesful
strncpy(buffer, array_to_search, array_size);
buffer[array_size] = '\0';
int count = 0;
for (char *i = buffer; (i = strchr(i, char_to_search_for)) != NULL; i++) {
count++;
}
free(buffer);
return count;
}
在你的java代码中:
imeActionLabel="xxxx"
imeActionId = "6"
它会正常工作。
答案 5 :(得分:0)
对于任何enter事件,操作ID默认情况下都设置为0。
actionId int:动作的标识符。这将是您提供的标识符,如果由于按下Enter键而被调用,则将是EditorInfo#IME_NULL。
所以处理输入键事件的正确方法是:
@Override
public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
if (actionId == EditorInfo.IME_NULL) {
// Handle return key here
return true;
}
return false;
}