【问题标题】:How to specify the thousands and decimal separator used by GWT's NumberFormat如何指定 GWT 的 NumberFormat 使用的千位和小数分隔符
【发布时间】:2012-04-06 01:11:47
【问题描述】:

在 GWT 的 NumberFormat 类文档 (http://google-web-toolkit.googlecode.com/svn/javadoc/1.5/com/google/gwt/i18n/client/NumberFormat.html) 我读到:

"用于无穷大、数字、千位分隔符、小数分隔符等的前缀、后缀和各种符号。可以设置为任意值, “

我的问题是,我如何确保 "."用作千位分隔符和“,”用作小数分隔符,与用户的区域设置无关? 换句话说,当我使用模式 "###,###,###.######" 时,我希望 GWT 将双精度值 1234567.89 always 格式化为 "1.234.567 ,89" 无论用户的语言环境是什么。

【问题讨论】:

  • 更新到我的最终答案。看起来 GWT 计划支持这一点,但还没有这样做。请参阅我建议的 hack。

标签: gwt number-formatting


【解决方案1】:

我使用的方式是通过这种方式覆盖 GWT 的 LocaleInfoImpl:

  1. 查看LocaleInfo,您可以看到它使用了一个私有静态实例LocaleInfo line 36,该实例使用GWT.create(LocaleInfoImpl.class) 构建
  2. 使用GWT Deferred binding,我们可以通过自定义实现覆盖LocalInfoImpl:
<replace-with class="your.app.package.to.CustomLocaleInfoImpl">
  <when-type-is class="com.google.gwt.i18n.client.impl.LocaleInfoImpl" />
</replace-with>
  1. 以与此类似的方式扩展 LocaleInfoImpl,只是覆盖方法 getNumberConstant:

public class CustomLocaleInfoImpl extends LocaleInfoImpl {

    @Override
    public NumberConstants getNumberConstants() {
        final NumberConstants nc = super.getNumberConstants();
        return new NumberConstants() {
            @Override
            public String notANumber() {
                return nc.notANumber();
            }

            @Override
            public String currencyPattern() {
                return nc.currencyPattern();
            }

            @Override
            public String decimalPattern() {
                return nc.decimalPattern();
            }

            @Override
            public String decimalSeparator() {
                return nc.decimalSeparator();
            }

            @Override
            public String defCurrencyCode() {
                return nc.defCurrencyCode();
            }

            @Override
            public String exponentialSymbol() {
                return nc.exponentialSymbol();
            }

            @Override
            public String globalCurrencyPattern() {
                return nc.globalCurrencyPattern();
            }

            @Override
            public String groupingSeparator() {
                return "@";//or any custom separator you desire
            }

            @Override
            public String infinity() {
                return nc.infinity();
            }

            @Override
            public String minusSign() {
                return nc.minusSign();
            }

            @Override
            public String monetaryGroupingSeparator() {
                return nc.monetaryGroupingSeparator();
            }

            @Override
            public String monetarySeparator() {
                return nc.monetarySeparator();
            }

            @Override
            public String percent() {
                return nc.percent();
            }

            @Override
            public String percentPattern() {
                return nc.percentPattern();
            }

            @Override
            public String perMill() {
                return nc.perMill();
            }

            @Override
            public String plusSign() {
                return nc.plusSign();
            }

            @Override
            public String scientificPattern() {
                return nc.scientificPattern();
            }

            @Override
            public String simpleCurrencyPattern() {
                return nc.simpleCurrencyPattern();
            }

            @Override
            public String zeroDigit() {
                return nc.zeroDigit();
            }
        };
    }
}

【讨论】:

  • 这是一个非常好的解决方案,但我无法让它发挥作用。似乎 GWT 不执行 规则,我不知道为什么。我正在使用 GWT 2.8.1
  • 我也在使用 2.8.1,它对我有用,也许您可​​以添加一些日志以跟踪执行情况
  • 我尽我所能在这里发布:stackoverflow.com/questions/51819228/…。如果您有任何想法,请发表评论。
【解决方案2】:

我刚刚遇到了同样的问题。我是这样解决的:

public String formatAmount(Double amount) {
    String pattern = "#,##0.00";
    String groupingSeparator = LocaleInfo.getCurrentLocale().getNumberConstants().groupingSeparator();
    String decimalSeparator = LocaleInfo.getCurrentLocale().getNumberConstants().decimalSeparator();
    NumberFormat format = NumberFormat.getFormat(pattern);
    return format.format(amount).replace(groupingSeparator, "'").replace(decimalSeparator, ".");
}

【讨论】:

    【解决方案3】:

    解决这个问题需要一些工作。从 NumberFormatter 的 docs 和 source 来看,似乎只能使用 Locales 来设置这些值。他们确实说您可以设置 组分隔符,但没有这样的示例对我有用。尽管您可能认为 Java 方法在底部执行此操作是可行的,因为 GWT 模拟了 DecimalFormat 和 DecimalFormalSymbols 类,但它们没有 formally support 它们。也许他们将来会。此外,他们在LocaleInfo class 中说您可以修改语言环境,但我发现没有这样的方法允许这样做。

    所以,这里是 Hack 方法:

        NumberFormat.getFormat("#,##0.0#").format(2342442.23d).replace(",", "@");
    

    正确的方式,但尚不支持 GWT:

    使用十进制格式:

        // formatter
        DecimalFormat format= new DecimalFormat();
        // custom symbol
        DecimalFormatSymbols customSymbols=new DecimalFormatSymbols();
        customSymbols.setGroupingSeparator('@');
        format.setDecimalFormatSymbols(customSymbols);
        // test
        String formattedString = format.format(2342442.23d);
    

    输出:

    2@342@442.23

    【讨论】:

    • 当尝试使用 DecimalFormat 时,我得到:“类 'java.text.DecimalFormat' 不在 JRE Emulation 库中,因此不能在客户端代码中使用”。
    • 当...奇怪,因为它是模拟的。我将发布给 GWT 开发人员。
    猜你喜欢
    • 1970-01-01
    • 2013-11-07
    • 1970-01-01
    • 2017-02-07
    • 2021-11-21
    • 2011-06-10
    • 2015-06-10
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多