mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2024-12-29 06:02:07 +03:00
LibJS: Use decimal compact patterns for currency style sub-patterns
When formatting a currency style pattern with compact notation, we were (trying to) doubly insert the currency symbol into the formatted string. We would first look up the currency pattern in GetNumberFormatPattern (for the en locale, this is "¤#,##0.00", which our generator transforms to "{currency}{number}"). When we hit the "{number}" field, NumberFormat will do a second lookup for the compact pattern to use for the number being formatted. By using the currency compact patterns, we receive a second pattern that also has the currency symbol (for the en locale, if formatting the number 1000, this is "¤0K", which our generator transforms to "{currency}{number}{compactIdentifier:0}". This second lookup is not supposed to have currency symbols (or any other symbols), thus we hit a VERIFY_NOT_REACHED(). Instead, we are meant to use the decimal compact pattern, and allow the currency symbol to be handled by only the outer currency pattern.
This commit is contained in:
parent
e3f693ca7c
commit
ca0d926036
Notes:
sideshowbarker
2024-07-17 08:35:21 +09:00
Author: https://github.com/trflynn89 Commit: https://github.com/SerenityOS/serenity/commit/ca0d926036 Pull-request: https://github.com/SerenityOS/serenity/pull/20948
@ -1634,15 +1634,11 @@ int compute_exponent_for_magnitude(NumberFormat& number_format, int magnitude)
|
||||
|
||||
// b. Let exponent be an implementation- and locale-dependent (ILD) integer by which to scale a number of the given magnitude in compact notation for the current locale.
|
||||
// c. Return exponent.
|
||||
Vector<::Locale::NumberFormat> format_rules;
|
||||
|
||||
if (number_format.style() == NumberFormat::Style::Currency)
|
||||
format_rules = ::Locale::get_compact_number_system_formats(number_format.data_locale(), number_format.numbering_system(), ::Locale::CompactNumberFormatType::CurrencyShort);
|
||||
else if (number_format.compact_display() == NumberFormat::CompactDisplay::Long)
|
||||
format_rules = ::Locale::get_compact_number_system_formats(number_format.data_locale(), number_format.numbering_system(), ::Locale::CompactNumberFormatType::DecimalLong);
|
||||
else
|
||||
format_rules = ::Locale::get_compact_number_system_formats(number_format.data_locale(), number_format.numbering_system(), ::Locale::CompactNumberFormatType::DecimalShort);
|
||||
auto compact_format_type = number_format.compact_display() == NumberFormat::CompactDisplay::Short || number_format.style() == NumberFormat::Style::Currency
|
||||
? ::Locale::CompactNumberFormatType::DecimalShort
|
||||
: ::Locale::CompactNumberFormatType::DecimalLong;
|
||||
|
||||
auto format_rules = ::Locale::get_compact_number_system_formats(number_format.data_locale(), number_format.numbering_system(), compact_format_type);
|
||||
::Locale::NumberFormat const* best_number_format = nullptr;
|
||||
|
||||
for (auto const& format_rule : format_rules) {
|
||||
|
@ -1298,6 +1298,146 @@ describe("style=currency", () => {
|
||||
expect(ar2.format(1.23)).toBe("1.23 دولار أمريكي");
|
||||
});
|
||||
|
||||
test("notation=compact, compactDisplay=long", () => {
|
||||
const en = new Intl.NumberFormat("en", {
|
||||
style: "currency",
|
||||
currency: "USD",
|
||||
notation: "compact",
|
||||
compactDisplay: "long",
|
||||
});
|
||||
expect(en.format(1)).toBe("$1");
|
||||
expect(en.format(1200)).toBe("$1.2K");
|
||||
expect(en.format(1290)).toBe("$1.3K");
|
||||
expect(en.format(12000)).toBe("$12K");
|
||||
expect(en.format(12900)).toBe("$13K");
|
||||
expect(en.format(1200000)).toBe("$1.2M");
|
||||
expect(en.format(1290000)).toBe("$1.3M");
|
||||
expect(en.format(12000000)).toBe("$12M");
|
||||
expect(en.format(12900000)).toBe("$13M");
|
||||
|
||||
const ar = new Intl.NumberFormat("ar", {
|
||||
style: "currency",
|
||||
currency: "USD",
|
||||
notation: "compact",
|
||||
compactDisplay: "long",
|
||||
});
|
||||
expect(ar.format(1)).toBe("١ US$");
|
||||
expect(ar.format(1200)).toBe("١٫٢ ألف US$");
|
||||
expect(ar.format(1290)).toBe("١٫٣ ألف US$");
|
||||
expect(ar.format(12000)).toBe("١٢ ألف US$");
|
||||
expect(ar.format(12900)).toBe("١٣ ألف US$");
|
||||
expect(ar.format(1200000)).toBe("١٫٢ مليون US$");
|
||||
expect(ar.format(1290000)).toBe("١٫٣ مليون US$");
|
||||
expect(ar.format(12000000)).toBe("١٢ مليون US$");
|
||||
expect(ar.format(12900000)).toBe("١٣ مليون US$");
|
||||
|
||||
const ja = new Intl.NumberFormat("ja", {
|
||||
style: "currency",
|
||||
currency: "JPY",
|
||||
notation: "compact",
|
||||
compactDisplay: "long",
|
||||
});
|
||||
expect(ja.format(1)).toBe("¥1");
|
||||
expect(ja.format(1200)).toBe("¥1200");
|
||||
expect(ja.format(1290)).toBe("¥1290");
|
||||
expect(ja.format(12000)).toBe("¥1.2万");
|
||||
expect(ja.format(12900)).toBe("¥1.3万");
|
||||
expect(ja.format(1200000)).toBe("¥120万");
|
||||
expect(ja.format(1290000)).toBe("¥129万");
|
||||
expect(ja.format(12000000)).toBe("¥1200万");
|
||||
expect(ja.format(12900000)).toBe("¥1290万");
|
||||
expect(ja.format(120000000)).toBe("¥1.2億");
|
||||
expect(ja.format(129000000)).toBe("¥1.3億");
|
||||
expect(ja.format(12000000000)).toBe("¥120億");
|
||||
expect(ja.format(12900000000)).toBe("¥129億");
|
||||
|
||||
const de = new Intl.NumberFormat("de", {
|
||||
style: "currency",
|
||||
currency: "EUR",
|
||||
notation: "compact",
|
||||
compactDisplay: "long",
|
||||
});
|
||||
expect(de.format(1)).toBe("1 €");
|
||||
expect(de.format(1200)).toBe("1200 €");
|
||||
expect(de.format(1290)).toBe("1290 €");
|
||||
expect(de.format(12000)).toBe("12.000 €");
|
||||
expect(de.format(12900)).toBe("12.900 €");
|
||||
expect(de.format(1200000)).toBe("1,2 Mio. €");
|
||||
expect(de.format(1290000)).toBe("1,3 Mio. €");
|
||||
expect(de.format(12000000)).toBe("12 Mio. €");
|
||||
expect(de.format(12900000)).toBe("13 Mio. €");
|
||||
});
|
||||
|
||||
test("notation=compact, compactDisplay=short", () => {
|
||||
const en = new Intl.NumberFormat("en", {
|
||||
style: "currency",
|
||||
currency: "USD",
|
||||
notation: "compact",
|
||||
compactDisplay: "short",
|
||||
});
|
||||
expect(en.format(1)).toBe("$1");
|
||||
expect(en.format(1200)).toBe("$1.2K");
|
||||
expect(en.format(1290)).toBe("$1.3K");
|
||||
expect(en.format(12000)).toBe("$12K");
|
||||
expect(en.format(12900)).toBe("$13K");
|
||||
expect(en.format(1200000)).toBe("$1.2M");
|
||||
expect(en.format(1290000)).toBe("$1.3M");
|
||||
expect(en.format(12000000)).toBe("$12M");
|
||||
expect(en.format(12900000)).toBe("$13M");
|
||||
|
||||
const ar = new Intl.NumberFormat("ar", {
|
||||
style: "currency",
|
||||
currency: "USD",
|
||||
notation: "compact",
|
||||
compactDisplay: "short",
|
||||
});
|
||||
expect(ar.format(1)).toBe("١ US$");
|
||||
expect(ar.format(1200)).toBe("١٫٢ ألف US$");
|
||||
expect(ar.format(1290)).toBe("١٫٣ ألف US$");
|
||||
expect(ar.format(12000)).toBe("١٢ ألف US$");
|
||||
expect(ar.format(12900)).toBe("١٣ ألف US$");
|
||||
expect(ar.format(1200000)).toBe("١٫٢ مليون US$");
|
||||
expect(ar.format(1290000)).toBe("١٫٣ مليون US$");
|
||||
expect(ar.format(12000000)).toBe("١٢ مليون US$");
|
||||
expect(ar.format(12900000)).toBe("١٣ مليون US$");
|
||||
|
||||
const ja = new Intl.NumberFormat("ja", {
|
||||
style: "currency",
|
||||
currency: "JPY",
|
||||
notation: "compact",
|
||||
compactDisplay: "short",
|
||||
});
|
||||
expect(ja.format(1)).toBe("¥1");
|
||||
expect(ja.format(1200)).toBe("¥1200");
|
||||
expect(ja.format(1290)).toBe("¥1290");
|
||||
expect(ja.format(12000)).toBe("¥1.2万");
|
||||
expect(ja.format(12900)).toBe("¥1.3万");
|
||||
expect(ja.format(1200000)).toBe("¥120万");
|
||||
expect(ja.format(1290000)).toBe("¥129万");
|
||||
expect(ja.format(12000000)).toBe("¥1200万");
|
||||
expect(ja.format(12900000)).toBe("¥1290万");
|
||||
expect(ja.format(120000000)).toBe("¥1.2億");
|
||||
expect(ja.format(129000000)).toBe("¥1.3億");
|
||||
expect(ja.format(12000000000)).toBe("¥120億");
|
||||
expect(ja.format(12900000000)).toBe("¥129億");
|
||||
|
||||
const de = new Intl.NumberFormat("de", {
|
||||
style: "currency",
|
||||
currency: "EUR",
|
||||
notation: "compact",
|
||||
compactDisplay: "short",
|
||||
});
|
||||
expect(de.format(1)).toBe("1 €");
|
||||
expect(de.format(1200)).toBe("1200 €");
|
||||
expect(de.format(1290)).toBe("1290 €");
|
||||
expect(de.format(12000)).toBe("12.000 €");
|
||||
expect(de.format(12900)).toBe("12.900 €");
|
||||
expect(de.format(1200000)).toBe("1,2 Mio. €");
|
||||
expect(de.format(1290000)).toBe("1,3 Mio. €");
|
||||
expect(de.format(12000000)).toBe("12 Mio. €");
|
||||
expect(de.format(12900000)).toBe("13 Mio. €");
|
||||
});
|
||||
|
||||
test("signDisplay=never", () => {
|
||||
const en1 = new Intl.NumberFormat("en", {
|
||||
style: "currency",
|
||||
|
Loading…
Reference in New Issue
Block a user