@nkootstra/block-kit 0.3.1 → 0.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +43 -18
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -6285,6 +6285,39 @@ const TIME_ZONE_LABELS = {
|
|
|
6285
6285
|
function timeZoneLabel(timeZone) {
|
|
6286
6286
|
return TIME_ZONE_LABELS[timeZone] ?? timeZone;
|
|
6287
6287
|
}
|
|
6288
|
+
/** A timestamp's wall-clock date ("2026-01-01") and time ("11:00") in `timeZone`. */
|
|
6289
|
+
function wallClock(ts, timeZone) {
|
|
6290
|
+
const parts = new Intl.DateTimeFormat("en-US", {
|
|
6291
|
+
timeZone,
|
|
6292
|
+
year: "numeric",
|
|
6293
|
+
month: "2-digit",
|
|
6294
|
+
day: "2-digit",
|
|
6295
|
+
hour: "2-digit",
|
|
6296
|
+
minute: "2-digit",
|
|
6297
|
+
hourCycle: "h23"
|
|
6298
|
+
}).formatToParts(/* @__PURE__ */ new Date(ts * 1e3));
|
|
6299
|
+
const get = (type) => parts.find((p) => p.type === type)?.value ?? "00";
|
|
6300
|
+
return {
|
|
6301
|
+
date: `${get("year")}-${get("month")}-${get("day")}`,
|
|
6302
|
+
time: `${get("hour")}:${get("minute")}`
|
|
6303
|
+
};
|
|
6304
|
+
}
|
|
6305
|
+
/** The timestamp of a wall-clock date and time in `timeZone`. Around a daylight saving change it
|
|
6306
|
+
* resolves like JavaScript's `Date`: a time the clocks skip moves forward by the gap, and a time
|
|
6307
|
+
* they repeat takes its first occurrence. */
|
|
6308
|
+
function fromWallClock(date, time, timeZone) {
|
|
6309
|
+
const asUtc = Date.parse(`${date}T${time}:00Z`) / 1e3;
|
|
6310
|
+
const offsetAt = (ts) => {
|
|
6311
|
+
const wall = wallClock(ts, timeZone);
|
|
6312
|
+
return Date.parse(`${wall.date}T${wall.time}:00Z`) / 1e3 - ts;
|
|
6313
|
+
};
|
|
6314
|
+
const before = asUtc - offsetAt(asUtc - 86400);
|
|
6315
|
+
const matches = [before, asUtc - offsetAt(asUtc + 86400)].filter((ts) => {
|
|
6316
|
+
const wall = wallClock(ts, timeZone);
|
|
6317
|
+
return wall.date === date && wall.time === time;
|
|
6318
|
+
});
|
|
6319
|
+
return matches.length > 0 ? Math.min(...matches) : before;
|
|
6320
|
+
}
|
|
6288
6321
|
//#endregion
|
|
6289
6322
|
//#region src/elements/inputBlockContext.ts
|
|
6290
6323
|
/** True while rendering the element of an `input` block, where Slack lays some elements out differently. */
|
|
@@ -6470,16 +6503,6 @@ function DatePicker({ element, blockId }) {
|
|
|
6470
6503
|
}
|
|
6471
6504
|
//#endregion
|
|
6472
6505
|
//#region src/elements/DateTimePicker.tsx
|
|
6473
|
-
function toISODate(ts) {
|
|
6474
|
-
return (/* @__PURE__ */ new Date(ts * 1e3)).toISOString().slice(0, 10);
|
|
6475
|
-
}
|
|
6476
|
-
function toHM(ts) {
|
|
6477
|
-
const d = /* @__PURE__ */ new Date(ts * 1e3);
|
|
6478
|
-
return `${String(d.getUTCHours()).padStart(2, "0")}:${String(d.getUTCMinutes()).padStart(2, "0")}`;
|
|
6479
|
-
}
|
|
6480
|
-
function combine(date, time) {
|
|
6481
|
-
return Math.floor((/* @__PURE__ */ new Date(`${date}T${time}:00Z`)).getTime() / 1e3);
|
|
6482
|
-
}
|
|
6483
6506
|
/** Slack's Builder splits a datetimepicker's closed control into a date box ("January 1st,
|
|
6484
6507
|
* 2026") and a separate time box ("11:00 AM"), rather than one combined string. */
|
|
6485
6508
|
function formatDate(ts, timeZone) {
|
|
@@ -6488,7 +6511,7 @@ function formatDate(ts, timeZone) {
|
|
|
6488
6511
|
month: "long",
|
|
6489
6512
|
day: "numeric",
|
|
6490
6513
|
year: "numeric",
|
|
6491
|
-
timeZone
|
|
6514
|
+
timeZone
|
|
6492
6515
|
}).formatToParts(d);
|
|
6493
6516
|
const month = parts.find((p) => p.type === "month")?.value ?? "";
|
|
6494
6517
|
const day = Number(parts.find((p) => p.type === "day")?.value ?? "1");
|
|
@@ -6499,7 +6522,7 @@ function formatTime$1(ts, timeZone) {
|
|
|
6499
6522
|
return (/* @__PURE__ */ new Date(ts * 1e3)).toLocaleString("en-US", {
|
|
6500
6523
|
hour: "numeric",
|
|
6501
6524
|
minute: "2-digit",
|
|
6502
|
-
timeZone
|
|
6525
|
+
timeZone
|
|
6503
6526
|
});
|
|
6504
6527
|
}
|
|
6505
6528
|
function DateTimePicker({ element, blockId }) {
|
|
@@ -6507,8 +6530,10 @@ function DateTimePicker({ element, blockId }) {
|
|
|
6507
6530
|
const { ask, dialog } = useConfirm(element.confirm);
|
|
6508
6531
|
const [value, setValueState] = useState(element.initial_date_time);
|
|
6509
6532
|
const [open, setOpen] = useState(false);
|
|
6510
|
-
const
|
|
6511
|
-
const
|
|
6533
|
+
const zone = timeZone ?? "UTC";
|
|
6534
|
+
const initial = element.initial_date_time !== void 0 ? wallClock(element.initial_date_time, zone) : void 0;
|
|
6535
|
+
const [draftDate, setDraftDate] = useState(initial?.date);
|
|
6536
|
+
const [draftTime, setDraftTime] = useState(initial?.time ?? "12:00");
|
|
6512
6537
|
const rootRef = useRef(null);
|
|
6513
6538
|
const focusRef = useFocusOnLoad(element);
|
|
6514
6539
|
const actionId = element.action_id ?? "";
|
|
@@ -6521,7 +6546,7 @@ function DateTimePicker({ element, blockId }) {
|
|
|
6521
6546
|
async function apply() {
|
|
6522
6547
|
if (!draftDate) return;
|
|
6523
6548
|
if (!await ask()) return;
|
|
6524
|
-
const ts =
|
|
6549
|
+
const ts = fromWallClock(draftDate, draftTime, zone);
|
|
6525
6550
|
setValueState(ts);
|
|
6526
6551
|
setOpen(false);
|
|
6527
6552
|
setValue(blockId, actionId, {
|
|
@@ -6552,7 +6577,7 @@ function DateTimePicker({ element, blockId }) {
|
|
|
6552
6577
|
/* @__PURE__ */ jsx(CalendarIcon, { className: "sbk-datetimepicker__icon" }),
|
|
6553
6578
|
/* @__PURE__ */ jsx("span", {
|
|
6554
6579
|
className: value !== void 0 ? "sbk-datetimepicker__value" : "sbk-datetimepicker__placeholder",
|
|
6555
|
-
children: value !== void 0 ? formatDate(value,
|
|
6580
|
+
children: value !== void 0 ? formatDate(value, zone) : "Select a date"
|
|
6556
6581
|
}),
|
|
6557
6582
|
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "sbk-datetimepicker__chevron" })
|
|
6558
6583
|
]
|
|
@@ -6567,13 +6592,13 @@ function DateTimePicker({ element, blockId }) {
|
|
|
6567
6592
|
/* @__PURE__ */ jsx(ClockIcon, { className: "sbk-datetimepicker__icon" }),
|
|
6568
6593
|
/* @__PURE__ */ jsx("span", {
|
|
6569
6594
|
className: value !== void 0 ? "sbk-datetimepicker__value" : "sbk-datetimepicker__placeholder",
|
|
6570
|
-
children: value !== void 0 ? formatTime$1(value,
|
|
6595
|
+
children: value !== void 0 ? formatTime$1(value, zone) : "Select a time"
|
|
6571
6596
|
}),
|
|
6572
6597
|
/* @__PURE__ */ jsx(ChevronDownIcon, { className: "sbk-datetimepicker__chevron" })
|
|
6573
6598
|
]
|
|
6574
6599
|
}), /* @__PURE__ */ jsxs("p", {
|
|
6575
6600
|
className: "sbk-datetimepicker__timezone",
|
|
6576
|
-
children: ["Time zone: ", timeZoneLabel(
|
|
6601
|
+
children: ["Time zone: ", timeZoneLabel(zone)]
|
|
6577
6602
|
})]
|
|
6578
6603
|
})]
|
|
6579
6604
|
}),
|