From cf92bc42a2286c9d54c2de0a482d7b0425972f43 Mon Sep 17 00:00:00 2001 From: Timothy Flynn Date: Thu, 27 Jan 2022 12:45:23 -0500 Subject: [PATCH] LibJS: Respect per-locale minimum grouping digits when number formatting --- .../LibJS/Runtime/Intl/NumberFormat.cpp | 26 ++++++++++--------- .../NumberFormat.prototype.format.js | 14 ++++++++++ 2 files changed, 28 insertions(+), 12 deletions(-) diff --git a/Userland/Libraries/LibJS/Runtime/Intl/NumberFormat.cpp b/Userland/Libraries/LibJS/Runtime/Intl/NumberFormat.cpp index 56809946b4..20ff8e59b8 100644 --- a/Userland/Libraries/LibJS/Runtime/Intl/NumberFormat.cpp +++ b/Userland/Libraries/LibJS/Runtime/Intl/NumberFormat.cpp @@ -714,27 +714,29 @@ Vector partition_number_pattern(NumberFormat& number_format, d static Vector separate_integer_into_groups(Unicode::NumberGroupings const& grouping_sizes, StringView integer) { Utf8View utf8_integer { integer }; + if (utf8_integer.length() <= grouping_sizes.primary_grouping_size) + return { integer }; + + size_t index = utf8_integer.length() - grouping_sizes.primary_grouping_size; + if (index < grouping_sizes.minimum_grouping_digits) + return { integer }; + Vector groups; auto add_group = [&](size_t index, size_t length) { groups.prepend(utf8_integer.unicode_substring_view(index, length).as_string()); }; - if (utf8_integer.length() > grouping_sizes.primary_grouping_size) { - size_t index = utf8_integer.length() - grouping_sizes.primary_grouping_size; - add_group(index, grouping_sizes.primary_grouping_size); + add_group(index, grouping_sizes.primary_grouping_size); - while (index > grouping_sizes.secondary_grouping_size) { - index -= grouping_sizes.secondary_grouping_size; - add_group(index, grouping_sizes.secondary_grouping_size); - } - - if (index > 0) - add_group(0, index); - } else { - groups.append(integer); + while (index > grouping_sizes.secondary_grouping_size) { + index -= grouping_sizes.secondary_grouping_size; + add_group(index, grouping_sizes.secondary_grouping_size); } + if (index > 0) + add_group(0, index); + return groups; } diff --git a/Userland/Libraries/LibJS/Tests/builtins/Intl/NumberFormat/NumberFormat.prototype.format.js b/Userland/Libraries/LibJS/Tests/builtins/Intl/NumberFormat/NumberFormat.prototype.format.js index 77a4df82d6..e14df84869 100644 --- a/Userland/Libraries/LibJS/Tests/builtins/Intl/NumberFormat/NumberFormat.prototype.format.js +++ b/Userland/Libraries/LibJS/Tests/builtins/Intl/NumberFormat/NumberFormat.prototype.format.js @@ -378,6 +378,13 @@ describe("style=decimal", () => { expect(ar.format(12345)).toBe("\u0661\u0662\u066c\u0663\u0664\u0665"); expect(ar.format(123456)).toBe("\u0661\u0662\u0663\u066c\u0664\u0665\u0666"); expect(ar.format(1234567)).toBe("\u0661\u066c\u0662\u0663\u0664\u066c\u0665\u0666\u0667"); + + const plPl = new Intl.NumberFormat("pl-PL", { useGrouping: true }); + expect(plPl.format(123)).toBe("123"); + expect(plPl.format(1234)).toBe("1234"); + expect(plPl.format(12345)).toBe("12\u00a0345"); + expect(plPl.format(123456)).toBe("123\u00a0456"); + expect(plPl.format(1234567)).toBe("1\u00a0234\u00a0567"); }); test("useGrouping=false", () => { @@ -401,6 +408,13 @@ describe("style=decimal", () => { expect(ar.format(12345)).toBe("\u0661\u0662\u0663\u0664\u0665"); expect(ar.format(123456)).toBe("\u0661\u0662\u0663\u0664\u0665\u0666"); expect(ar.format(1234567)).toBe("\u0661\u0662\u0663\u0664\u0665\u0666\u0667"); + + const plPl = new Intl.NumberFormat("pl-PL", { useGrouping: false }); + expect(plPl.format(123)).toBe("123"); + expect(plPl.format(1234)).toBe("1234"); + expect(plPl.format(12345)).toBe("12345"); + expect(plPl.format(123456)).toBe("123456"); + expect(plPl.format(1234567)).toBe("1234567"); }); });