我正在使用下面的InputFilter过滤掉无效(十进制值大于127的ASCII),并且当输入无效字符时,EditText会显示文本两次。我确实希望EditText显示有效字符,下面是发生的事情的一个例子。
- 用户在EditText组件中输入 XYZ€
屏幕上显示“toast”消息,指出“无效的非Ascii字符”
-EditText组件在屏幕上显示xyz,这是我所期望的
- 用户输入有效字符 A ,以便屏幕显示 XYZA
-InputFilter运行并返回 XYZA ,但 XYZXYZA 出现在EditText组件中,这是不正确的。它复制 XYZ
有关处理无效字符后复制输入文本的原因的任何想法吗?
屏幕:
<EditText android:id="@+id/editText"
android:layout_width="fill_parent" android:layout_height="120dp"
android:layout_marginTop="10dp" android:layout_marginLeft="10dp"
android:layout_marginRight="10dp" android:maxLength="45"
android:focusable="true" android:inputType="text"
android:cursorVisible="true" android:imeOptions="actionDone"
/>
活动:
public class EditTextActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
EditText eText = (EditText) findViewById(R.id.editText);
setAsciiTextFilter();
}
private void setAsciiTextFilter() {
InputFilter filter = new InputFilter() {
int asciiNo;
@Override
public CharSequence filter(CharSequence source, int start, int end,
Spanned dest, int dstart, int dend) {
for (int i = start; i < end; i++) {
asciiNo = source.charAt(i);
if(asciiNo > 127) {
toast = mUtility.showToast("Invalid non-Ascii Character", Toast.LENGTH_SHORT);
//Replace the invalid ascii character with empty String
return source.toString().replace(source.charAt(i)+"", "");
}
}
return null;
}
};
eText.setFilters(new InputFilter[]{filter});
}
}
新尝试:
InputFilter filter = new InputFilter() {
@Override
public CharSequence filter(CharSequence source, int start, int end,
Spanned dest, int dstart, int dend) {
if (source instanceof SpannableStringBuilder) {
SpannableStringBuilder sourceAsSpannableBuilder = (SpannableStringBuilder)source;
for (int i = end - 1; i >= start; i--) {
char currentChar = source.charAt(i);
int ascii = currentChar;
if (ascii > 127) {
sourceAsSpannableBuilder.delete(i, i+1);
toast = mUtility.showToast("Invalid non-Ascii Character", Toast.LENGTH_SHORT);
}
}
return source;
} else {
StringBuilder filteredStringBuilder = new StringBuilder();
for (int i = 0; i < end; i++) {
char currentChar = source.charAt(i);
int ascii = currentChar;
if (ascii <= 127) {
filteredStringBuilder.append(currentChar);
}
}
return filteredStringBuilder.toString();
}
}
};
答案 0 :(得分:1)
<强>编辑:强>
我认为问题是你要返回整个字符串,当你应该只返回该字符的替换时。 filter()
会在文本发生变化时运行,并不一定会替换EditText
中的整个字符串。你需要注意这一点,所以你不要把整个字符串推到一个角色应该去的地方。
This question是相关的(只用非ascii代替非字母数字),答案很容易被接受,所以你应该能够用它来得到你想要的东西。
对于令人困惑的回答/删除事情感到抱歉。我在离开家之前就回答了。几分钟后,我意识到我的逻辑存在一个巨大的缺陷,所以我跳上移动并删除了它。我讨厌在手机上输入一个完整的答案,所以它只需要等一下。
答案 1 :(得分:1)
我发现最好使用单个for循环并回答。
另请注意,将源传递给SpannableStringBuilder构造函数以从源复制跨度非常重要。如果你不这样做,那么事情会变得很糟糕。
@Override
public CharSequence filter(CharSequence source, int start,
int end, Spanned dest, int dstart, int dend) {
SpannableStringBuilder ret;
if (source instanceof SpannableStringBuilder) {
ret = (SpannableStringBuilder)source;
} else {
ret = new SpannableStringBuilder(source);
}
for (int i = end - 1; i >= start; i--) {
char currentChar = source.charAt(i);
char currentChar = source.charAt(i);
int ascii = currentChar;
if (ascii > 127) {
ret.delete(i, i+1);
toast = mUtility.showToast("Invalid non-Ascii Character", Toast.LENGTH_SHORT);
}
}
return ret;
}