我有以下问题。我有EditText和TextWatcher,它根据一些规则格式化输入文本。在方法afterTextChanged()我格式化它。然后我格式化了字符串,我想用格式化的值替换EditText的旧值。 接下来我们有两个选择:
如果我们使用第一个选项,EditText的工作速度非常慢并且会丢失符号。 但是如果我们使用第二种方法,Editable不会替换旧文本,但会将新文本附加到旧文本中。
也许有人有类似的问题?
更新:使用Editable.clear()然后Editable.append()或insert()具有类似的效果
代码:
public static class LoginWatcher implements TextWatcher {
private EditText target;
private LoginFilter loginFilter = new LoginFilter();
private int lastLength;
private boolean wasPhoneNumber = false;
private AsYouTypeFormatter formatter;
private boolean isFormattingStopped;
public LoginWatcher(OnLoginEnterListener onLoginInputListener, EditText target) {
listener = onLoginInputListener;
this.target = target;
lastLength = target.getText().length();
formatter = PhoneNumberUtil.getInstance().getAsYouTypeFormatter(Locale.getDefault().getCountry());
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
if (isFormattingStopped) {
return;
}
if (count > 0 && hasSeparator(s, start, count)) {
stopFormatting();
}
}
@Override
public void afterTextChanged(Editable s) {
target.removeTextChangedListener(this);
boolean isSymbolsChecked = loginFilter.check(s.toString());
boolean isEmail = StringUtils.isEmailValid(s.toString());
boolean isPhoneNumber = isPhoneNumber(s.toString());
if (lastLength <= s.length()) {
if (isPhoneNumber && !isFormattingStopped) {
String formatted = reformat(s, Selection.getSelectionEnd(s));
if (formatted != null) {
target.setText(formatted);
target.setSelection(target.getText().length());
}
} else if (wasPhoneNumber) {
String unformatted = unFormatPhoneNumber(s.toString());
target.setText(unformatted); // or s.clear(); s.append();
target.setSelection(target.getText().length());
}
}
lastLength = s.length();
wasPhoneNumber = isPhoneNumber;
if (isFormattingStopped) {
isFormattingStopped = s.length() != 0;
}
target.addTextChangedListener(this);
}
private String unFormatPhoneNumber(String s) {
char[] chars = s.toCharArray();
if (s.isEmpty()) {
return s;
}
if (chars[0] == '+') {
boolean isPhoneNumber = true;
for (int i = 1; i < chars.length; ++i) {
if (!Character.isDigit(chars[i])) {
isPhoneNumber = false;
break;
}
}
if (isPhoneNumber) {
return s;
}
}
return s.replaceAll("[\\+\\(\\)\\s\\-]+", "");
}
private String reformat(CharSequence s, int cursor) {
int curIndex = cursor - 1;
String formatted = null;
formatter.clear();
char lastNonSeparator = 0;
boolean hasCursor = false;
int len = s.length();
for (int i = 0; i < len; i++) {
char c = s.charAt(i);
if (PhoneNumberUtils.isNonSeparator(c)) {
if (lastNonSeparator != 0) {
formatted = getFormattedNumber(lastNonSeparator, hasCursor);
hasCursor = false;
}
lastNonSeparator = c;
}
if (i == curIndex) {
hasCursor = true;
}
}
if (lastNonSeparator != 0) {
formatted = getFormattedNumber(lastNonSeparator, hasCursor);
}
return formatted;
}
private String getFormattedNumber(char lastNonSeparator, boolean hasCursor) {
return hasCursor ? formatter.inputDigitAndRememberPosition(lastNonSeparator)
: formatter.inputDigit(lastNonSeparator);
}
private boolean isPhoneNumber(String s) {
return !TextUtils.isEmpty(s) && Patterns.PHONE.matcher(s).matches();
}
private boolean hasSeparator(final CharSequence s, final int start, final int count) {
for (int i = start; i < start + count; i++) {
char c = s.charAt(i);
if (!PhoneNumberUtils.isNonSeparator(c)) {
return true;
}
}
return false;
}
private void stopFormatting() {
isFormattingStopped = true;
formatter.clear();
}
}
答案 0 :(得分:0)
尝试使用Editable
提供的方法 @Override
public void afterTextChanged(Editable s) {
target.removeTextChangedListener(this);
boolean isSymbolsChecked = loginFilter.check(s.toString());
boolean isEmail = StringUtils.isEmailValid(s.toString());
boolean isPhoneNumber = isPhoneNumber(s.toString());
if (lastLength <= s.length()) {
if (isPhoneNumber && !isFormattingStopped) {
String formatted = reformat(s, Selection.getSelectionEnd(s));
if (formatted != null) {
s.replace(0, s.length(), formatted)
target.setSelection(formatted.length());
}
} else if (wasPhoneNumber) {
String unformatted = unFormatPhoneNumber(s.toString());
s.replace(0, s.length(), formatted)
target.setSelection(formatted.length());
}
}
lastLength = s.length();
wasPhoneNumber = isPhoneNumber;
if (isFormattingStopped) {
isFormattingStopped = s.length() != 0;
}
target.addTextChangedListener(this);
}