168 lines
5.7 KiB
Zig
168 lines
5.7 KiB
Zig
const abi = @import("abi.zig");
|
|
const c = abi.c;
|
|
|
|
/// Time unit for Temporal operations.
|
|
/// See: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Temporal
|
|
pub const Unit = enum {
|
|
auto,
|
|
nanosecond,
|
|
microsecond,
|
|
millisecond,
|
|
second,
|
|
minute,
|
|
hour,
|
|
day,
|
|
week,
|
|
month,
|
|
year,
|
|
|
|
pub fn toCApi(self: Unit) c_uint {
|
|
return switch (self) {
|
|
.auto => c.Unit_Auto,
|
|
.nanosecond => c.Unit_Nanosecond,
|
|
.microsecond => c.Unit_Microsecond,
|
|
.millisecond => c.Unit_Millisecond,
|
|
.second => c.Unit_Second,
|
|
.minute => c.Unit_Minute,
|
|
.hour => c.Unit_Hour,
|
|
.day => c.Unit_Day,
|
|
.week => c.Unit_Week,
|
|
.month => c.Unit_Month,
|
|
.year => c.Unit_Year,
|
|
};
|
|
}
|
|
};
|
|
|
|
/// Rounding mode for Temporal operations.
|
|
/// See: https://tc39.es/ecma402/#table-sanctioned-single-unit-identifiers
|
|
pub const RoundingMode = enum {
|
|
/// Round toward positive infinity
|
|
ceil,
|
|
/// Round toward negative infinity
|
|
floor,
|
|
/// Round away from zero
|
|
expand,
|
|
/// Round toward zero (truncate)
|
|
trunc,
|
|
/// Round half toward positive infinity
|
|
half_ceil,
|
|
/// Round half toward negative infinity
|
|
half_floor,
|
|
/// Round half away from zero
|
|
half_expand,
|
|
/// Round half toward zero
|
|
half_trunc,
|
|
/// Round half to even (banker's rounding)
|
|
half_even,
|
|
|
|
pub fn toCApi(self: RoundingMode) c_uint {
|
|
return switch (self) {
|
|
.ceil => c.RoundingMode_Ceil,
|
|
.floor => c.RoundingMode_Floor,
|
|
.expand => c.RoundingMode_Expand,
|
|
.trunc => c.RoundingMode_Trunc,
|
|
.half_ceil => c.RoundingMode_HalfCeil,
|
|
.half_floor => c.RoundingMode_HalfFloor,
|
|
.half_expand => c.RoundingMode_HalfExpand,
|
|
.half_trunc => c.RoundingMode_HalfTrunc,
|
|
.half_even => c.RoundingMode_HalfEven,
|
|
};
|
|
}
|
|
};
|
|
|
|
/// Sign of a duration or time value.
|
|
pub const Sign = enum {
|
|
positive,
|
|
zero,
|
|
negative,
|
|
|
|
pub fn toCApi(self: Sign) c_int {
|
|
return switch (self) {
|
|
.positive => c.Sign_Positive,
|
|
.zero => c.Sign_Zero,
|
|
.negative => c.Sign_Negative,
|
|
};
|
|
}
|
|
|
|
pub fn fromCApi(value: c_int) Sign {
|
|
return switch (value) {
|
|
c.Sign_Positive => .positive,
|
|
c.Sign_Zero => .zero,
|
|
c.Sign_Negative => .negative,
|
|
else => .zero,
|
|
};
|
|
}
|
|
};
|
|
|
|
/// Options for rounding operations (Instant.round, Duration.round, etc.).
|
|
/// MDN: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Temporal/Duration/round
|
|
pub const RoundingOptions = struct {
|
|
largest_unit: ?Unit = null,
|
|
smallest_unit: ?Unit = null,
|
|
rounding_mode: ?RoundingMode = null,
|
|
rounding_increment: ?u32 = null,
|
|
|
|
pub fn toCApi(self: RoundingOptions) c.RoundingOptions {
|
|
return .{
|
|
.largest_unit = abi.toUnitOption(toCUnit(self.largest_unit)),
|
|
.smallest_unit = abi.toUnitOption(toCUnit(self.smallest_unit)),
|
|
.rounding_mode = abi.toRoundingModeOption(toCRoundingMode(self.rounding_mode)),
|
|
.increment = abi.toOption(c.OptionU32, self.rounding_increment),
|
|
};
|
|
}
|
|
};
|
|
|
|
/// Options for computing differences between instants.
|
|
/// MDN: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Temporal/Instant/until
|
|
pub const DifferenceSettings = struct {
|
|
largest_unit: ?Unit = null,
|
|
smallest_unit: ?Unit = null,
|
|
rounding_mode: ?RoundingMode = null,
|
|
rounding_increment: ?u32 = null,
|
|
|
|
pub fn toCApi(self: DifferenceSettings) c.DifferenceSettings {
|
|
return .{
|
|
.largest_unit = abi.toUnitOption(toCUnit(self.largest_unit)),
|
|
.smallest_unit = abi.toUnitOption(toCUnit(self.smallest_unit)),
|
|
.rounding_mode = abi.toRoundingModeOption(toCRoundingMode(self.rounding_mode)),
|
|
.increment = abi.toOption(c.OptionU32, self.rounding_increment),
|
|
};
|
|
}
|
|
};
|
|
|
|
/// Options for Duration.toString() formatting.
|
|
/// MDN: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Temporal/Duration/toString
|
|
pub const ToStringRoundingOptions = struct {
|
|
fractional_second_digits: ?u8 = null,
|
|
smallest_unit: ?Unit = null,
|
|
rounding_mode: ?RoundingMode = null,
|
|
|
|
pub fn toCApi(self: ToStringRoundingOptions) c.ToStringRoundingOptions {
|
|
const precision: c.Precision = if (self.fractional_second_digits) |fsd|
|
|
.{ .is_minute = false, .precision = abi.toOption(c.OptionU8, fsd) }
|
|
else if (self.smallest_unit) |su|
|
|
switch (su) {
|
|
.second => .{ .is_minute = false, .precision = abi.toOption(c.OptionU8, 0) },
|
|
.millisecond => .{ .is_minute = false, .precision = abi.toOption(c.OptionU8, 3) },
|
|
.microsecond => .{ .is_minute = false, .precision = abi.toOption(c.OptionU8, 6) },
|
|
.nanosecond => .{ .is_minute = false, .precision = abi.toOption(c.OptionU8, 9) },
|
|
else => .{ .is_minute = false, .precision = abi.toOption(c.OptionU8, null) },
|
|
}
|
|
else
|
|
.{ .is_minute = false, .precision = abi.toOption(c.OptionU8, null) };
|
|
|
|
return .{
|
|
.precision = precision,
|
|
.smallest_unit = abi.toUnitOption(toCUnit(self.smallest_unit)),
|
|
.rounding_mode = abi.toRoundingModeOption(toCRoundingMode(self.rounding_mode)),
|
|
};
|
|
}
|
|
};
|
|
|
|
fn toCUnit(opt: ?Unit) ?c.Unit {
|
|
return if (opt) |u| @as(c.Unit, @intCast(u.toCApi())) else null;
|
|
}
|
|
|
|
fn toCRoundingMode(opt: ?RoundingMode) ?c.RoundingMode {
|
|
return if (opt) |m| @as(c.RoundingMode, @intCast(m.toCApi())) else null;
|
|
}
|