1 /**
2 * Copyright (c) 2025 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #ifndef PANDA_PLUGINS_ETS_STDLIB_NATIVE_CORE_INTLNUMBERFORMATTERS_H
17 #define PANDA_PLUGINS_ETS_STDLIB_NATIVE_CORE_INTLNUMBERFORMATTERS_H
18
19 #include <ani.h>
20 #include <string>
21 #include "unicode/numberformatter.h"
22 #include "unicode/numberrangeformatter.h"
23 #include "unicode/locid.h"
24 #include <set>
25
26 namespace ark::ets::stdlib::intl {
27
28 constexpr std::string_view COMPACT_DISPLAY_SHORT = "short";
29 constexpr std::string_view COMPACT_DISPLAY_LONG = "long";
30 constexpr std::string_view CURRENCY_SIGN_ACCOUNTING = "accounting";
31 constexpr std::string_view CURRENCY_SIGN_STANDARD = "standard";
32 constexpr std::string_view CURRENCY_DISPLAY_CODE = "code";
33 constexpr std::string_view CURRENCY_DISPLAY_SYMBOL = "symbol";
34 constexpr std::string_view CURRENCY_DISPLAY_NARROWSYMBOL = "narrowSymbol";
35 constexpr std::string_view CURRENCY_DISPLAY_NAME = "name";
36 constexpr std::string_view NOTATION_STANDARD = "standard";
37 constexpr std::string_view NOTATION_SCIENTIFIC = "scientific";
38 constexpr std::string_view NOTATION_ENGINEERING = "engineering";
39 constexpr std::string_view NOTATION_COMPACT = "compact";
40 constexpr std::string_view SIGN_DISPLAY_AUTO = "auto";
41 constexpr std::string_view SIGN_DISPLAY_NEVER = "never";
42 constexpr std::string_view SIGN_DISPLAY_ALWAYS = "always";
43 constexpr std::string_view SIGN_DISPLAY_EXCEPTZERO = "exceptZero";
44 constexpr std::string_view STYLE_DECIMAL = "decimal";
45 constexpr std::string_view STYLE_PERCENT = "percent";
46 constexpr std::string_view STYLE_CURRENCY = "currency";
47 constexpr std::string_view STYLE_UNIT = "unit";
48 constexpr std::string_view UNIT_DISPLAY_SHORT = "short";
49 constexpr std::string_view UNIT_DISPLAY_LONG = "long";
50 constexpr std::string_view UNIT_DISPLAY_NARROW = "narrow";
51 constexpr std::string_view USE_GROUPING_TRUE = "true";
52 constexpr std::string_view USE_GROUPING_FALSE = "false";
53 constexpr std::string_view USE_GROUPING_MIN2 = "min2";
54 constexpr int32_t STYLE_PERCENT_SCALE_FACTOR = 2;
55 constexpr int32_t PER_UNIT_STR_SIZE = 5;
56 constexpr const char *UNDEFINED_STR = "_";
57
IsUndefinedStr(const std::string & str)58 inline std::string IsUndefinedStr(const std::string &str)
59 {
60 return str.empty() ? UNDEFINED_STR : str;
61 }
62
63 // NOLINTNEXTLINE(fuchsia-statically-constructed-objects)
64 const std::set<std::string> REFERENCE_UNITS({"acre", "bit", "byte",
65 "celsius", "centimeter", "day",
66 "degree", "fahrenheit", "fluid-ounce",
67 "foot", "gallon", "gigabit",
68 "gigabyte", "gram", "hectare",
69 "hour", "inch", "kilobit",
70 "kilobyte", "kilogram", "kilometer",
71 "liter", "megabit", "megabyte",
72 "meter", "mile", "mile-scandinavian",
73 "millimeter", "milliliter", "millisecond",
74 "minute", "month", "ounce",
75 "percent", "petabyte", "pound",
76 "second", "stone", "terabit",
77 "terabyte", "week", "yard",
78 "year"});
79
80 // NOLINTBEGIN(misc-non-private-member-variables-in-classes)
81 struct ParsedOptions {
82 std::string compactDisplay;
83 std::string currencySign;
84 std::string currency;
85 std::string currencyDisplay;
86 std::string locale;
87 std::string minFractionDigits;
88 std::string maxFractionDigits;
89 std::string minSignificantDigits;
90 std::string maxSignificantDigits;
91 std::string minIntegerDigits;
92 std::string notation;
93 std::string numberingSystem;
94 std::string signDisplay;
95 std::string style;
96 std::string unit;
97 std::string unitDisplay;
98 std::string useGrouping;
99
ToStringParsedOptions100 [[maybe_unused]] std::string ToString() const
101 {
102 std::string str;
103 str.append("compactDisplay: " + compactDisplay);
104 str.append(", currencySign: " + currencySign);
105 str.append(", currency: " + currency);
106 str.append(", currencyDisplay: " + currencyDisplay);
107 str.append(", locale: " + locale);
108 str.append(", maxFractionDigits: " + maxFractionDigits);
109 str.append(", maxSignificantDigits: " + maxSignificantDigits);
110 str.append(", minFractionDigits: " + minFractionDigits);
111 str.append(", minIntegerDigits: " + minIntegerDigits);
112 str.append(", minSignificantDigits: " + minSignificantDigits);
113 str.append(", notation: " + notation);
114 str.append(", numberingSystem: " + numberingSystem);
115 str.append(", signDisplay: " + signDisplay);
116 str.append(", style: " + style);
117 str.append(", unit: " + unit);
118 str.append(", unitDisplay: " + unitDisplay);
119 str.append(", useGrouping: " + useGrouping);
120 return str;
121 }
122
TagStringParsedOptions123 std::string TagString() const
124 {
125 std::string tag;
126 tag.append(IsUndefinedStr(compactDisplay));
127 tag.append(IsUndefinedStr(currencySign));
128 tag.append(IsUndefinedStr(currency));
129 tag.append(IsUndefinedStr(currencyDisplay));
130 tag.append(IsUndefinedStr(locale));
131 tag.append(IsUndefinedStr(minFractionDigits));
132 tag.append(IsUndefinedStr(maxFractionDigits));
133 tag.append(IsUndefinedStr(minSignificantDigits));
134 tag.append(IsUndefinedStr(maxSignificantDigits));
135 tag.append(IsUndefinedStr(minIntegerDigits));
136 tag.append(IsUndefinedStr(notation));
137 tag.append(IsUndefinedStr(numberingSystem));
138 tag.append(IsUndefinedStr(signDisplay));
139 tag.append(IsUndefinedStr(style));
140 tag.append(IsUndefinedStr(unit));
141 tag.append(IsUndefinedStr(unitDisplay));
142 tag.append(IsUndefinedStr(useGrouping));
143 return tag;
144 }
145 };
146 // NOLINTEND(misc-non-private-member-variables-in-classes)
147
148 using LocNumFmt = icu::number::LocalizedNumberFormatter;
149 using UnlocNumFmt = icu::number::UnlocalizedNumberFormatter;
150 using LocNumRangeFmt = icu::number::LocalizedNumberRangeFormatter;
151
152 ANI_EXPORT ani_status LocTagToIcuLocale(ani_env *env, const std::string &localeTag, icu::Locale &locale);
153 ANI_EXPORT ani_status InitNumFormatter(ani_env *env, const ParsedOptions &options, LocNumFmt &fmt);
154 ANI_EXPORT ani_status InitNumRangeFormatter(ani_env *env, const ParsedOptions &options, LocNumRangeFmt &fmt);
155 ANI_EXPORT bool IsCorrectUnitIdentifier(const std::string &unit);
156 ANI_EXPORT void ParseOptions(ani_env *env, ani_object self, ParsedOptions &options);
157
158 } // namespace ark::ets::stdlib::intl
159
160 #endif // PANDA_PLUGINS_ETS_STDLIB_NATIVE_CORE_INTLNUMBERFORMATTERS_H
161