mirror of
https://github.com/RGBCube/serenity
synced 2025-07-27 00:07:36 +00:00
LibJS: Implement Intl.Locale.prototype.hourCycles property
This commit is contained in:
parent
4d32f38a76
commit
ee2be5895f
6 changed files with 55 additions and 1 deletions
|
@ -258,6 +258,7 @@ namespace JS {
|
|||
P(hour) \
|
||||
P(hour12) \
|
||||
P(hourCycle) \
|
||||
P(hourCycles) \
|
||||
P(hours) \
|
||||
P(hoursDisplay) \
|
||||
P(hoursInDay) \
|
||||
|
|
|
@ -107,4 +107,23 @@ Array* collations_of_locale(GlobalObject& global_object, Locale const& locale_ob
|
|||
return create_array_from_list_or_restricted(global_object, move(list), move(restricted));
|
||||
}
|
||||
|
||||
// 1.1.4 HourCyclesOfLocale ( loc ), https://tc39.es/proposal-intl-locale-info/#sec-hour-cycles-of-locale
|
||||
Array* hour_cycles_of_locale(GlobalObject& global_object, Locale const& locale_object)
|
||||
{
|
||||
// 1. Let restricted be loc.[[HourCycle]].
|
||||
Optional<String> restricted = locale_object.has_hour_cycle() ? locale_object.hour_cycle() : Optional<String> {};
|
||||
|
||||
// 2. Let locale be loc.[[Locale]].
|
||||
auto const& locale = locale_object.locale();
|
||||
|
||||
// 3. Assert: locale matches the unicode_locale_id production.
|
||||
VERIFY(Unicode::parse_unicode_locale_id(locale).has_value());
|
||||
|
||||
// 4. Let list be a List of 1 or more unique hour cycle identifiers, which must be lower case String values indicating either the 12-hour format ("h11", "h12") or the 24-hour format ("h23", "h24"), sorted in descending preference of those in common use for date and time formatting in locale.
|
||||
auto list = Unicode::get_keywords_for_locale(locale, "hc"sv);
|
||||
|
||||
// 5. Return ! CreateArrayFromListOrRestricted( list, restricted ).
|
||||
return create_array_from_list_or_restricted(global_object, move(list), move(restricted));
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -76,5 +76,6 @@ private:
|
|||
|
||||
Array* calendars_of_locale(GlobalObject& global_object, Locale const& locale);
|
||||
Array* collations_of_locale(GlobalObject& global_object, Locale const& locale);
|
||||
Array* hour_cycles_of_locale(GlobalObject& global_object, Locale const& locale);
|
||||
|
||||
}
|
||||
|
|
|
@ -40,6 +40,7 @@ void LocalePrototype::initialize(GlobalObject& global_object)
|
|||
define_native_accessor(vm.names.collation, collation, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.collations, collations, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.hourCycle, hour_cycle, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.hourCycles, hour_cycles, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.numberingSystem, numbering_system, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.numeric, numeric, {}, Attribute::Configurable);
|
||||
define_native_accessor(vm.names.language, language, {}, Attribute::Configurable);
|
||||
|
@ -204,10 +205,12 @@ JS_DEFINE_NATIVE_FUNCTION(LocalePrototype::region)
|
|||
|
||||
#define JS_ENUMERATE_LOCALE_INFO_PROPERTIES \
|
||||
__JS_ENUMERATE(calendars) \
|
||||
__JS_ENUMERATE(collations)
|
||||
__JS_ENUMERATE(collations) \
|
||||
__JS_ENUMERATE(hour_cycles)
|
||||
|
||||
// 1.4.16 get Intl.Locale.prototype.calendars, https://tc39.es/proposal-intl-locale-info/#sec-Intl.Locale.prototype.calendars
|
||||
// 1.4.17 get Intl.Locale.prototype.collations, https://tc39.es/proposal-intl-locale-info/#sec-Intl.Locale.prototype.collations
|
||||
// 1.4.18 get Intl.Locale.prototype.hourCycles, https://tc39.es/proposal-intl-locale-info/#sec-Intl.Locale.prototype.hourCycles
|
||||
#define __JS_ENUMERATE(keyword) \
|
||||
JS_DEFINE_NATIVE_FUNCTION(LocalePrototype::keyword) \
|
||||
{ \
|
||||
|
|
|
@ -31,6 +31,7 @@ private:
|
|||
JS_DECLARE_NATIVE_FUNCTION(collation);
|
||||
JS_DECLARE_NATIVE_FUNCTION(collations);
|
||||
JS_DECLARE_NATIVE_FUNCTION(hour_cycle);
|
||||
JS_DECLARE_NATIVE_FUNCTION(hour_cycles);
|
||||
JS_DECLARE_NATIVE_FUNCTION(numbering_system);
|
||||
JS_DECLARE_NATIVE_FUNCTION(numeric);
|
||||
JS_DECLARE_NATIVE_FUNCTION(language);
|
||||
|
|
|
@ -0,0 +1,29 @@
|
|||
describe("errors", () => {
|
||||
test("called on non-Locale object", () => {
|
||||
expect(() => {
|
||||
Intl.Locale.prototype.hourCycles;
|
||||
}).toThrowWithMessage(TypeError, "Not an object of type Intl.Locale");
|
||||
});
|
||||
});
|
||||
|
||||
describe("normal behavior", () => {
|
||||
test("basic functionality", () => {
|
||||
expect(Array.isArray(new Intl.Locale("en").hourCycles)).toBeTrue();
|
||||
expect(new Intl.Locale("en").hourCycles).toContain("h12");
|
||||
|
||||
expect(Array.isArray(new Intl.Locale("ha").hourCycles)).toBeTrue();
|
||||
expect(new Intl.Locale("ha").hourCycles).toContain("h23");
|
||||
});
|
||||
|
||||
test("extension keyword overrides default data", () => {
|
||||
expect(new Intl.Locale("en-u-hc-h24").hourCycles).toEqual(["h24"]);
|
||||
expect(new Intl.Locale("en", { hourCycle: "h24" }).hourCycles).toEqual(["h24"]);
|
||||
|
||||
expect(new Intl.Locale("ar-u-hc-h24").hourCycles).toEqual(["h24"]);
|
||||
expect(new Intl.Locale("ar", { hourCycle: "h24" }).hourCycles).toEqual(["h24"]);
|
||||
|
||||
// Invalid hourCycles also take precedence when specified in the locale string. Unlike other
|
||||
// properties, Locale("en", { hourCycle: "ladybird" }) will explictly throw.
|
||||
expect(new Intl.Locale("en-u-hc-ladybird").hourCycles).toEqual(["ladybird"]);
|
||||
});
|
||||
});
|
Loading…
Add table
Add a link
Reference in a new issue