我有自定义EditText,它将转换输入并能够反转它。但是它总是使输入十进制,输入后面有1或2个值。现在我正在制作一些需要整数的计算应用程序。如何使这个自定义EditText只进行整数输入和输出?
代码:
@TargetApi(Build.VERSION_CODES.GINGERBREAD)
public class NumericEditText extends EditText {
private final char GROUPING_SEPARATOR = DecimalFormatSymbols.getInstance().getGroupingSeparator();
private final char DECIMAL_SEPARATOR = DecimalFormatSymbols.getInstance().getDecimalSeparator();
private final String LEADING_ZERO_FILTER_REGEX = "^0+(?!$)";
private String mDefaultText = null;
private String mPreviousText = "";
private String mNumberFilterRegex = "[^\\d\\" + DECIMAL_SEPARATOR + "]";
/**
* Interface to notify listeners when numeric value has been changed or cleared
*/
public interface NumericValueWatcher {
/**
* Fired when numeric value has been changed
* @param newValue new numeric value
*/
void onChanged(double newValue);
/**
* Fired when numeric value has been cleared (text field is empty)
*/
void onCleared();
}
private List<NumericValueWatcher> mNumericListeners = new ArrayList<NumericValueWatcher>();
private final TextWatcher mTextWatcher = new TextWatcher() {
private boolean validateLock = false;
@Override
public void afterTextChanged(Editable s) {
if (validateLock) {
return;
}
// valid decimal number should not have more than 2 decimal separators
if (StringUtils.countMatches(s.toString(), String.valueOf(DECIMAL_SEPARATOR)) > 1) {
validateLock = true;
setText(mPreviousText); // cancel change and revert to previous input
setSelection(mPreviousText.length());
validateLock = false;
return;
}
if (s.length() == 0) {
handleNumericValueCleared();
return;
}
setTextInternal(format(s.toString()));
setSelection(getText().length());
handleNumericValueChanged();
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
// do nothing
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
// do nothing
}
};
private void handleNumericValueCleared() {
mPreviousText = "";
for (NumericValueWatcher listener : mNumericListeners) {
listener.onCleared();
}
}
private void handleNumericValueChanged() {
mPreviousText = getText().toString();
for (NumericValueWatcher listener : mNumericListeners) {
listener.onChanged(getNumericValue());
}
}
public NumericEditText(Context context, AttributeSet attrs) {
super(context, attrs);
addTextChangedListener(mTextWatcher);
setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// disable moving cursor
setSelection(getText().length());
}
});
}
/**
* Add listener for numeric value changed events
* @param watcher listener to add
*/
public void addNumericValueChangedListener(NumericValueWatcher watcher) {
mNumericListeners.add(watcher);
}
/**
* Remove all listeners to numeric value changed events
*/
public void removeAllNumericValueChangedListeners() {
while (!mNumericListeners.isEmpty()) {
mNumericListeners.remove(0);
}
}
/**
* Set default numeric value and how it should be displayed, this value will be used if
* {@link #clear} is called
* @param defaultNumericValue numeric value
* @param defaultNumericFormat display format for numeric value
*/
public void setDefaultNumericValue(double defaultNumericValue, final String defaultNumericFormat) {
mDefaultText = String.format(defaultNumericFormat, defaultNumericValue);
setTextInternal(mDefaultText);
}
/**
* Clear text field and replace it with default value set in {@link #setDefaultNumericValue} if
* any
*/
public void clear() {
setTextInternal(mDefaultText != null ? mDefaultText : "");
if (mDefaultText != null) {
handleNumericValueChanged();
}
}
/**
* Return numeric value repesented by the text field
* @return numeric value or {@link Double.NaN} if not a number
*/
public double getNumericValue() {
String original = getText().toString().replaceAll(mNumberFilterRegex, "");
try {
return NumberFormat.getInstance().parse(original).doubleValue();
} catch (ParseException e) {
return Double.NaN;
}
}
/**
* Add grouping separators to string
* @param original original string, may already contains incorrect grouping separators
* @return string with correct grouping separators
*/
private String format(final String original) {
final String[] parts = original.split("\\" + DECIMAL_SEPARATOR, -1);
String number = parts[0] // since we split with limit -1 there will always be at least 1 part
.replaceAll(mNumberFilterRegex, "")
.replaceFirst(LEADING_ZERO_FILTER_REGEX, "");
// add grouping separators, need to reverse back and forth since Java regex does not support
// right to left matching
number = StringUtils.reverse(
StringUtils.reverse(number).replaceAll("(.{3})", "$1" + GROUPING_SEPARATOR));
// remove leading grouping separator if any
number = StringUtils.removeStart(number, String.valueOf(GROUPING_SEPARATOR));
// add fraction part if any
if (parts.length > 1) {
number += DECIMAL_SEPARATOR + parts[1];
}
return number;
}
/**
* Change display text without triggering numeric value changed
* @param text new text to apply
*/
private void setTextInternal(String text) {
removeTextChangedListener(mTextWatcher);
setText(text);
addTextChangedListener(mTextWatcher);
}
}
示例:
输入10000 它会在瞬间达到10,000, 输入10000.12 它将是10,000.12我尝试过的事情:
int input2 = 0;
String text2 = etpersen2.getText().toString();
if (text2.length() > 0)
input2 = Integer.parseInt(text2);
String e = String.valueOf(input2);
etresult.setText("" + e);
答案 0 :(得分:1)
使用Math.round()
应该将浮点数舍入到最接近的整数。它返回一个int值,因此使用(int)
进行类型转换是多余的。
public class Test{
public static void main(String args[]){
double d = 100.675;
double e = 100.500;
float f = 100;
float g = 90f;
System.out.println(Math.round(d));
System.out.println(Math.round(e));
System.out.println(Math.round(f));
System.out.println(Math.round(g));
}
}