Domanda

I have a system that generates a lot of documents. Its contents are defined in ResourceBundles.

I want to customize the way MessageFormat prints currency values. Sometimes I want it to display currencies without fraction digits (but not always).

This should be working as expected but it is not:

System.err.println(
  com.ibm.icu.text.MessageFormat.format(
      "{0,number,\u00A4#}", 
      new com.ibm.icu.util.CurrencyAmount(1, 
        com.ibm.icu.util.Currency.getInstance("USD"))));

Unfortunately it prints out:

US$1,00

Does anyone of you use custom formats for currency in resource bundle 'properties' files?

I don't want to change it system wide.

And by the way this works fine with java.text.MessageFormat.

È stato utile?

Soluzione

OK, I read your question once again. I don't really know why you want to chop down the cents part (in US, it makes sense in Korea or Japan as they don't use them at all).
Anyway, I don't think it is a good idea to just cut-off cents part, but if you want to do it, it is as simple as using NumberFormat with setMaximumIntegerDigits(int).

BTW, I still don't know I know why by using resource bundles you can't use NumberFormat. You still can call formatter in MessageFormat.format():

NumberFormat currencyFormatter = NumberFormat.getCurrencyInstance(Locale.US);
currencyFormatter.setMaximumFractionDigits(0);
System.err.println(MessageFormat.format("Some amount: {0}.",
        currencyFormatter.format(1d)));

Predictably it prints out:

Some amount: $1.

If you need to retain the currency, I'd suggest to play with setCurrency(Currency) method by retain local format - you are asking this question in Internalization tag anyway.


Edit: Including information about MessageFormat capabilities

If you need to use custom currency formats for a Locale, you actually need to instantiate MessageFormat class (regular static MessageFormat.format(String, Object...) won't work in web applications for it uses default Locale - Locale.getDefault(Locale.Category.FORMAT) in Java 7 - server Locale if you prefer).

So what you really want is to write a helper method (sorry, no bonus) that will look similar to this (out of memory, sorry):

public static String format(String pattern, Locale locale, Object... args) {
  final String emptyPattern = "";
  final FieldPosition zero = new FieldPosition(0);
  MessageFormat fmt = new MessageFormat(emptyPattern, locale);
  StringBuffer buf = new StringBuffer(); // I just love it...

  fmt.applyPattern(pattern);
  fmt.format(args, buf, zero);

  return buf.toString();
}

For performance reasons, you might think of creating StringBuffer once and then clean it all the time, but I leave optimizations to yourself.
You also would need to modify patterns a bit and I will explain in a moment why:

String pattern = "{1}{0,number,\u00A4#}";

You would need to pass the amount and the currency symbol and left to translators where to place the symbol and how to format value for a Locale (don't forget to add comments to properties file!).

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top