ImmutableNumberFormat nf,
StringBuilder appendTo,
FieldPosition fieldPosition) {
- if (measure.getUnit() instanceof Currency) {
+ Number n = measure.getNumber();
+ MeasureUnit unit = measure.getUnit();
+ if (unit instanceof Currency) {
return appendTo.append(
currencyFormat.format(
- new CurrencyAmount(measure.getNumber(), (Currency) measure.getUnit()),
+ new CurrencyAmount(n, (Currency) unit),
new StringBuffer(),
fieldPosition));
}
- Number n = measure.getNumber();
- MeasureUnit unit = measure.getUnit();
- UFieldPosition fpos = new UFieldPosition(fieldPosition.getFieldAttribute(), fieldPosition.getField());
- StringBuffer formattedNumber = nf.format(n, new StringBuffer(), fpos);
- String keyword = rules.select(new PluralRules.FixedDecimal(n.doubleValue(), fpos.getCountVisibleFractionDigits(), fpos.getFractionDigits()));
-
- int pluralForm = StandardPlural.indexOrOtherIndexFromString(keyword);
- SimplePatternFormatter formatter = getPluralFormatter(unit, formatWidth, pluralForm);
- int[] offsets = new int[1];
- formatter.formatAndAppend(appendTo, offsets, formattedNumber);
- if (offsets[0] != -1) { // there is a number (may not happen with, say, Arabic dual)
- // Fix field position
- if (fpos.getBeginIndex() != 0 || fpos.getEndIndex() != 0) {
- fieldPosition.setBeginIndex(fpos.getBeginIndex() + offsets[0]);
- fieldPosition.setEndIndex(fpos.getEndIndex() + offsets[0]);
- }
- }
- return appendTo;
+ StringBuffer formattedNumber = new StringBuffer();
+ StandardPlural pluralForm = QuantityFormatter.selectPlural(
+ n, nf.nf, rules, formattedNumber, fieldPosition);
+ SimplePatternFormatter formatter = getPluralFormatter(unit, formatWidth, pluralForm.ordinal());
+ return QuantityFormatter.format(formatter, formattedNumber, appendTo, fieldPosition);
}
-
+
/**
* Instances contain all MeasureFormat specific data for a particular locale.
* This data is cached. It is never copied, but is shared via shared pointers.
*/
package com.ibm.icu.text;
+import java.text.FieldPosition;
+
import com.ibm.icu.impl.SimplePatternFormatter;
import com.ibm.icu.impl.StandardPlural;
+import com.ibm.icu.text.PluralRules.FixedDecimal;
/**
* QuantityFormatter represents an unknown quantity of something and formats a known quantity
}
/**
- * Format formats a quantity with this object.
- * @param quantity the quantity to be formatted
- * @param numberFormat used to actually format the quantity.
- * @param pluralRules uses the quantity and the numberFormat to determine what plural
+ * Format formats a number with this object.
+ * @param number the number to be formatted
+ * @param numberFormat used to actually format the number.
+ * @param pluralRules uses the number and the numberFormat to determine what plural
* variant to use for fetching the formatting template.
* @return the formatted string e.g '3 apples'
*/
- public String format(double quantity, NumberFormat numberFormat, PluralRules pluralRules) {
- String formatStr = numberFormat.format(quantity);
- String variant = pluralRules.select(quantity, numberFormat);
- return getByVariant(variant).format(formatStr);
+ public String format(double number, NumberFormat numberFormat, PluralRules pluralRules) {
+ String formatStr = numberFormat.format(number);
+ StandardPlural p = selectPlural(number, numberFormat, pluralRules);
+ SimplePatternFormatter formatter = templates[p.ordinal()];
+ if (formatter == null) {
+ formatter = templates[StandardPlural.OTHER_INDEX];
+ assert formatter != null;
+ }
+ return formatter.format(formatStr);
}
-
+
/**
* Gets the SimplePatternFormatter for a particular variant.
* @param variant "zero", "one", "two", "few", "many", "other"
return (template == null && idx != StandardPlural.OTHER_INDEX) ?
templates[StandardPlural.OTHER_INDEX] : template;
}
+
+ // The following methods live here so that class PluralRules does not depend on number formatting,
+ // and the SimplePatternFormatter does not depend on FieldPosition.
+
+ /**
+ * Selects the standard plural form for the number/formatter/rules.
+ */
+ public static StandardPlural selectPlural(double number, NumberFormat numberFormat, PluralRules rules) {
+ String pluralKeyword;
+ if (numberFormat instanceof DecimalFormat) {
+ pluralKeyword = rules.select(((DecimalFormat) numberFormat).getFixedDecimal(number));
+ } else {
+ pluralKeyword = rules.select(number);
+ }
+ return StandardPlural.orOtherFromString(pluralKeyword);
+ }
+
+ /**
+ * Selects the standard plural form for the number/formatter/rules.
+ */
+ public static StandardPlural selectPlural(
+ Number number, NumberFormat fmt, PluralRules rules,
+ StringBuffer formattedNumber, FieldPosition pos) {
+ UFieldPosition fpos = new UFieldPosition(pos.getFieldAttribute(), pos.getField());
+ fmt.format(number, formattedNumber, fpos);
+ // TODO: Long, BigDecimal & BigInteger may not fit into doubleValue().
+ FixedDecimal fd = new FixedDecimal(
+ number.doubleValue(),
+ fpos.getCountVisibleFractionDigits(), fpos.getFractionDigits());
+ String pluralKeyword = rules.select(fd);
+ pos.setBeginIndex(fpos.getBeginIndex());
+ pos.setEndIndex(fpos.getEndIndex());
+ return StandardPlural.orOtherFromString(pluralKeyword);
+ }
+
+ /**
+ * Formats the pattern with the value and adjusts the FieldPosition.
+ */
+ public static StringBuilder format(SimplePatternFormatter pattern, CharSequence value,
+ StringBuilder appendTo, FieldPosition pos) {
+ int[] offsets = new int[1];
+ pattern.formatAndAppend(appendTo, offsets, value);
+ if (pos.getBeginIndex() != 0 || pos.getEndIndex() != 0) {
+ if (offsets[0] >= 0) {
+ pos.setBeginIndex(pos.getBeginIndex() + offsets[0]);
+ pos.setEndIndex(pos.getEndIndex() + offsets[0]);
+ } else {
+ pos.setBeginIndex(0);
+ pos.setEndIndex(0);
+ }
+ }
+ return appendTo;
+ }
}