【问题标题】:Android edit text decimal formatAndroid编辑文本十进制格式
【发布时间】:2017-02-02 07:20:36
【问题描述】:

我能问一下如何格式化字符串值吗? 5000000.005,000,000.00?显然我正在为 android 应用程序做与货币相关的事情,我可以设法将字符串值 5000000 格式化为 5,000,000,而无需在编辑文本中使用点分隔符。我想存储字符串值以供以后用于 parseDouble 以便我需要计算并有一些小数。我设法只使用逗号分隔符,但是关于如何使点也显示在编辑文本中的任何想法? 以下是我的代码:

amountText.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {
            }

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {
            }

            @Override
            public void afterTextChanged(Editable s) {
                amountText.removeTextChangedListener(this);
                if(!amountText.getText().toString().equals(""))
                {
                    try {
                        String editText = amountText.getText().toString();
                        String newStr = editText.replace("$", "").replace(",", "");
                        customer.getProperty().get(groupPosition).setAmount(newStr);
                        String formattedString = formatString(customer.getProperty().get(groupPosition).getAmount());
                        amountText.setText(formattedString);
                        amountText.setSelection(amountText.getText().length());
                        // to place the cursor at the end of text
                    } catch (NumberFormatException nfe) {
                        nfe.printStackTrace();
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
                amountText.addTextChangedListener(this);
            }
        });

public String formatString(String s)
{
        String givenstring = s.toString();
        Long longval;
        if (givenstring.contains(",")) {
            givenstring = givenstring.replaceAll(",", "");
        }
        longval = Long.parseLong(givenstring);
        DecimalFormat formatter = new DecimalFormat("#,###,###");
        String formattedString = formatter.format(longval);
        return formattedString;
}

我已经测试过使用 parseDouble 但是当我输入“。”时在EditText 中,它不会出现,如果我改用长变量,它会给出错误的格式和错误。 (java.lang.NumberFormatException:无效的长:“500000.00”)。所有值都在字符串中完成,稍后处理我将在计算时解析值。 感谢您并感谢任何人的指导,如果存在类似的帖子,我深表歉意,因为我还没有设法找到解决方案。

【问题讨论】:

  • 我也尝试过使用十进制格式的不同模式“###,###.###”,但没有运气,它仍然不起作用。

标签: android android-studio android-edittext decimalformat


【解决方案1】:

这是有效且经过全面测试的代码,只需复制并粘贴即可尝试

TextWatcher amountTextWatcher = new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {

            }

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {
            }

            @Override
            public void afterTextChanged(Editable s) {
                    int cursorPosition = etAmount.getSelectionEnd();
                    String originalStr = etAmount.getText().toString();

                    //To restrict only two digits after decimal place
                    etAmount.setFilters(new InputFilter[]{new MoneyValueFilter(Integer.parseInt(2))});

                try {
                        etAmount.removeTextChangedListener(this);
                        String value = etAmount.getText().toString();

                        if (value != null && !value.equals("")) {
                            if (value.startsWith(".")) {
                                etAmount.setText("0.");
                            }
                            if (value.startsWith("0") && !value.startsWith("0.")) {
                                etAmount.setText("");
                            }
                            String str = etAmount.getText().toString().replaceAll(",", "");
                            if (!value.equals(""))
                                etAmount.setText(getDecimalFormattedString(str));

                            int diff = etAmount.getText().toString().length() - originalStr.length();
                            etAmount.setSelection(cursorPosition + diff);
                        }
                        etAmount.addTextChangedListener(this);
                    } catch (Exception ex) {
                        ex.printStackTrace();
                        etAmount.addTextChangedListener(this);
                    }
                }
            }
        };
        etAmount.addTextChangedListener(amountTextWatcher);

这是给十进制数添加逗号分隔符的方法

/**
     * Get decimal formated string to include comma seperator to decimal number
     *
     * @param value
     * @return
     */
    public static String getDecimalFormattedString(String value) {
        if (value != null && !value.equalsIgnoreCase("")) {
            StringTokenizer lst = new StringTokenizer(value, ".");
            String str1 = value;
            String str2 = "";
            if (lst.countTokens() > 1) {
                str1 = lst.nextToken();
                str2 = lst.nextToken();
            }
            String str3 = "";
            int i = 0;
            int j = -1 + str1.length();
            if (str1.charAt(-1 + str1.length()) == '.') {
                j--;
                str3 = ".";
            }
            for (int k = j; ; k--) {
                if (k < 0) {
                    if (str2.length() > 0)
                        str3 = str3 + "." + str2;
                    return str3;
                }
                if (i == 3) {
                    str3 = "," + str3;
                    i = 0;
                }
                str3 = str1.charAt(k) + str3;
                i++;
            }
        }
        return "";
    }

在edittext中限制小数点后两位数字的方法

/**
     * Restrict digits after decimal point value as per currency
     */
    class MoneyValueFilter extends DigitsKeyListener {
        private int digits;

        public MoneyValueFilter(int i) {
            super(false, true);
            digits = i;
        }

        @Override
        public CharSequence filter(CharSequence source, int start, int end, Spanned dest, int dstart, int dend) {
            CharSequence out = super.filter(source, start, end, dest, dstart, dend);

            // if changed, replace the source
            if (out != null) {
                source = out;
                start = 0;
                end = out.length();
            }

            int len = end - start;

            // if deleting, source is empty
            // and deleting can't break anything
            if (len == 0) {
                return source;
            }

            int dlen = dest.length();

            // Find the position of the decimal .
            for (int i = 0; i < dstart; i++) {
                if (dest.charAt(i) == '.') {
                    // being here means, that a number has
                    // been inserted after the dot
                    // check if the amount of digits is right
                    return getDecimalFormattedString((dlen - (i + 1) + len > digits) ? "" : String.valueOf(new SpannableStringBuilder(source, start, end)));
                }
            }

            for (int i = start; i < end; ++i) {
                if (source.charAt(i) == '.') {
                    // being here means, dot has been inserted
                    // check if the amount of digits is right
                    if ((dlen - dend) + (end - (i + 1)) > digits)
                        return "";
                    else
                        break; // return new SpannableStringBuilder(source,
                    // start, end);
                }
            }

            // if the dot is after the inserted part,
            // nothing can break
            return getDecimalFormattedString(String.valueOf(new SpannableStringBuilder(source, start, end)));
        }
    }

【讨论】:

  • 您好,感谢您的帖子,我可以知道 cursorPosition 和 originalStr 在哪里吗?
  • 谢谢,效果很好,我原来用的是editText.setSelection(amountText.getText().length());而不是光标位置和 originalStr,它仍然会带到文本的末尾。但是使用它并不会限制小数位,任何想法如何使它在“。”之后只有 2 位小数。输入?
  • 很高兴听到这个消息
  • @johnnyhill 我已经更新了我的答案并添加了一个限制小数点后两位数字的方法,还在 afterTextChanged 中添加了带有注释的实现
【解决方案2】:

试试这个:

public void afterTextChanged(Editable view) {
    String s = null;
    try {
        // The comma in the format specifier does the trick
        s = String.format("%,d", Long.parseLong(view.toString()));
    } catch (NumberFormatException e) {
    }
    // Set s back to the view after temporarily removing the text change listener
}

来源:How to Automatically add thousand separators as number is input in EditText

【讨论】:

  • 感谢您的回复,但我认为这对我来说不可行?因为我正在实时输入输入,并且每当我输入输入时都需要更改格式。例如,我键入 5、50、500、5000,然后当它达到 5000 时,它会自动格式化为 5,000。这段代码给了我错误“java.lang.NumberFormatException: Invalid long:”com.example.daniel.test.CustomEditText{ffcf1c2 VFED..CL. .F...... 80,0-400,86 #7f0d00aa app:id/installmentET}""
  • 它会,一旦你添加一个 TextChangedListener 到你的编辑文本。 stackoverflow.com/questions/5567373/…
  • 此代码有效,但不适用于后点“。”在我输入“。”后的部分,当我单击其他视图时不显示该值 n 再次单击编辑文本,即“。”由于错误 java.lang.NumberFormatException: Invalid long: "50000000.00" 导致值丢失后
猜你喜欢
  • 2021-01-12
  • 1970-01-01
  • 2012-09-21
  • 1970-01-01
  • 2012-04-04
  • 2012-02-07
  • 1970-01-01
  • 2012-05-10
  • 1970-01-01
相关资源
最近更新 更多