1 /*
2 *******************************************************************************
3 * Copyright (C) 2015, International Business Machines Corporation and
4 * others. All Rights Reserved.
5 *******************************************************************************
6 */
7
8 #include "unicode/plurrule.h"
9 #include "unicode/unistr.h"
10 #include "unicode/utypes.h"
11
12 #if !UCONFIG_NO_FORMATTING
13
14 #include "digitformatter.h"
15 #include "digitgrouping.h"
16 #include "digitinterval.h"
17 #include "digitlst.h"
18 #include "precision.h"
19 #include "plurrule_impl.h"
20 #include "smallintformatter.h"
21 #include "uassert.h"
22 #include "valueformatter.h"
23 #include "visibledigits.h"
24
25 U_NAMESPACE_BEGIN
26
~ValueFormatter()27 ValueFormatter::~ValueFormatter() {}
28
29 VisibleDigitsWithExponent &
toVisibleDigitsWithExponent(int64_t value,VisibleDigitsWithExponent & digits,UErrorCode & status) const30 ValueFormatter::toVisibleDigitsWithExponent(
31 int64_t value,
32 VisibleDigitsWithExponent &digits,
33 UErrorCode &status) const {
34 switch (fType) {
35 case kFixedDecimal:
36 return fFixedPrecision->initVisibleDigitsWithExponent(
37 value, digits, status);
38 break;
39 case kScientificNotation:
40 return fScientificPrecision->initVisibleDigitsWithExponent(
41 value, digits, status);
42 break;
43 default:
44 U_ASSERT(FALSE);
45 break;
46 }
47 return digits;
48 }
49
50 VisibleDigitsWithExponent &
toVisibleDigitsWithExponent(DigitList & value,VisibleDigitsWithExponent & digits,UErrorCode & status) const51 ValueFormatter::toVisibleDigitsWithExponent(
52 DigitList &value,
53 VisibleDigitsWithExponent &digits,
54 UErrorCode &status) const {
55 switch (fType) {
56 case kFixedDecimal:
57 return fFixedPrecision->initVisibleDigitsWithExponent(
58 value, digits, status);
59 break;
60 case kScientificNotation:
61 return fScientificPrecision->initVisibleDigitsWithExponent(
62 value, digits, status);
63 break;
64 default:
65 U_ASSERT(FALSE);
66 break;
67 }
68 return digits;
69 }
70
isNoGrouping(const DigitGrouping & grouping,int32_t value,const FixedPrecision & precision)71 static UBool isNoGrouping(
72 const DigitGrouping &grouping,
73 int32_t value,
74 const FixedPrecision &precision) {
75 IntDigitCountRange range(
76 precision.fMin.getIntDigitCount(),
77 precision.fMax.getIntDigitCount());
78 return grouping.isNoGrouping(value, range);
79 }
80
81 UBool
isFastFormattable(int32_t value) const82 ValueFormatter::isFastFormattable(int32_t value) const {
83 switch (fType) {
84 case kFixedDecimal:
85 {
86 if (value == INT32_MIN) {
87 return FALSE;
88 }
89 if (value < 0) {
90 value = -value;
91 }
92 return fFixedPrecision->isFastFormattable() && fFixedOptions->isFastFormattable() && isNoGrouping(*fGrouping, value, *fFixedPrecision);
93 }
94 case kScientificNotation:
95 return FALSE;
96 default:
97 U_ASSERT(FALSE);
98 break;
99 }
100 return FALSE;
101 }
102
103 DigitList &
round(DigitList & value,UErrorCode & status) const104 ValueFormatter::round(DigitList &value, UErrorCode &status) const {
105 if (value.isNaN() || value.isInfinite()) {
106 return value;
107 }
108 switch (fType) {
109 case kFixedDecimal:
110 return fFixedPrecision->round(value, 0, status);
111 case kScientificNotation:
112 return fScientificPrecision->round(value, status);
113 default:
114 U_ASSERT(FALSE);
115 break;
116 }
117 return value;
118 }
119
120 UnicodeString &
formatInt32(int32_t value,FieldPositionHandler & handler,UnicodeString & appendTo) const121 ValueFormatter::formatInt32(
122 int32_t value,
123 FieldPositionHandler &handler,
124 UnicodeString &appendTo) const {
125 switch (fType) {
126 case kFixedDecimal:
127 {
128 IntDigitCountRange range(
129 fFixedPrecision->fMin.getIntDigitCount(),
130 fFixedPrecision->fMax.getIntDigitCount());
131 return fDigitFormatter->formatPositiveInt32(
132 value,
133 range,
134 handler,
135 appendTo);
136 }
137 break;
138 case kScientificNotation:
139 default:
140 U_ASSERT(FALSE);
141 break;
142 }
143 return appendTo;
144 }
145
146 UnicodeString &
format(const VisibleDigitsWithExponent & value,FieldPositionHandler & handler,UnicodeString & appendTo) const147 ValueFormatter::format(
148 const VisibleDigitsWithExponent &value,
149 FieldPositionHandler &handler,
150 UnicodeString &appendTo) const {
151 switch (fType) {
152 case kFixedDecimal:
153 return fDigitFormatter->format(
154 value.getMantissa(),
155 *fGrouping,
156 *fFixedOptions,
157 handler,
158 appendTo);
159 break;
160 case kScientificNotation:
161 return fDigitFormatter->format(
162 value,
163 *fScientificOptions,
164 handler,
165 appendTo);
166 break;
167 default:
168 U_ASSERT(FALSE);
169 break;
170 }
171 return appendTo;
172 }
173
174 int32_t
countChar32(const VisibleDigitsWithExponent & value) const175 ValueFormatter::countChar32(const VisibleDigitsWithExponent &value) const {
176 switch (fType) {
177 case kFixedDecimal:
178 return fDigitFormatter->countChar32(
179 value.getMantissa(),
180 *fGrouping,
181 *fFixedOptions);
182 break;
183 case kScientificNotation:
184 return fDigitFormatter->countChar32(
185 value,
186 *fScientificOptions);
187 break;
188 default:
189 U_ASSERT(FALSE);
190 break;
191 }
192 return 0;
193 }
194
195 void
prepareFixedDecimalFormatting(const DigitFormatter & formatter,const DigitGrouping & grouping,const FixedPrecision & precision,const DigitFormatterOptions & options)196 ValueFormatter::prepareFixedDecimalFormatting(
197 const DigitFormatter &formatter,
198 const DigitGrouping &grouping,
199 const FixedPrecision &precision,
200 const DigitFormatterOptions &options) {
201 fType = kFixedDecimal;
202 fDigitFormatter = &formatter;
203 fGrouping = &grouping;
204 fFixedPrecision = &precision;
205 fFixedOptions = &options;
206 }
207
208 void
prepareScientificFormatting(const DigitFormatter & formatter,const ScientificPrecision & precision,const SciFormatterOptions & options)209 ValueFormatter::prepareScientificFormatting(
210 const DigitFormatter &formatter,
211 const ScientificPrecision &precision,
212 const SciFormatterOptions &options) {
213 fType = kScientificNotation;
214 fDigitFormatter = &formatter;
215 fScientificPrecision = &precision;
216 fScientificOptions = &options;
217 }
218
219 U_NAMESPACE_END
220
221 #endif /* !UCONFIG_NO_FORMATTING */
222