altitude-design 0.2.0 → 0.2.1

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.cjs CHANGED
@@ -37,6 +37,7 @@ __export(index_exports, {
37
37
  AltitudeProvider: () => AltitudeProvider,
38
38
  Avatar: () => Avatar,
39
39
  AvatarGroup: () => AvatarGroup,
40
+ Await: () => Await,
40
41
  Badge: () => Badge,
41
42
  Board: () => Board,
42
43
  BoardCard: () => BoardCard,
@@ -64,11 +65,13 @@ __export(index_exports, {
64
65
  Input: () => Input,
65
66
  Kbd: () => Kbd,
66
67
  Layer: () => Layer,
68
+ LoadingScope: () => LoadingScope,
67
69
  Pile: () => Pile,
68
70
  Popover: () => Popover,
69
71
  Progress: () => Progress,
70
72
  Radio: () => Radio,
71
73
  RadioGroup: () => RadioGroup,
74
+ RevealGroup: () => RevealGroup,
72
75
  ScrollArea: () => ScrollArea,
73
76
  Select: () => Select,
74
77
  SelectItem: () => SelectItem,
@@ -103,6 +106,7 @@ __export(index_exports, {
103
106
  commandScore: () => commandScore,
104
107
  contrast: () => contrast,
105
108
  deriveAccent: () => deriveAccent,
109
+ readPromised: () => readPromised,
106
110
  riseDelay: () => riseDelay,
107
111
  toast: () => toast,
108
112
  useAltitude: () => useAltitude,
@@ -547,9 +551,190 @@ function Kbd({ listen, className, children, ...rest }) {
547
551
  }
548
552
 
549
553
  // project/components/src/controls.tsx
554
+ var React3 = __toESM(require("react"), 1);
555
+
556
+ // project/components/src/suspense.tsx
550
557
  var React2 = __toESM(require("react"), 1);
551
- var Button = React2.forwardRef(function Button2({ variant = "secondary", size = "md", square, loading, leading, trailing, className, children, disabled, type = "button", ...rest }, ref) {
558
+ var isPromise = (v) => !!v && (typeof v === "object" || typeof v === "function") && typeof v.then === "function";
559
+ var hasPromise = (children) => Array.isArray(children) ? children.some(isPromise) : isPromise(children);
560
+ var settled = /* @__PURE__ */ new WeakMap();
561
+ var reactUse = React2.use;
562
+ function readPromised(v) {
563
+ if (!isPromise(v)) return v;
564
+ if (reactUse) return reactUse(v);
565
+ let r = settled.get(v);
566
+ if (!r) {
567
+ const rec = { s: "pending" };
568
+ settled.set(v, rec);
569
+ v.then((x) => {
570
+ rec.s = "done";
571
+ rec.v = x;
572
+ }, (e) => {
573
+ rec.s = "error";
574
+ rec.e = e;
575
+ });
576
+ r = rec;
577
+ }
578
+ if (r.s === "done") return r.v;
579
+ if (r.s === "error") throw r.e;
580
+ throw v;
581
+ }
582
+ function readChildren(children) {
583
+ return Array.isArray(children) ? children.map((c) => readPromised(c)) : readPromised(children);
584
+ }
585
+ function useArrival(waiting) {
586
+ const d = React2.useRef(null);
587
+ if (waiting && !d.current) {
588
+ let done;
589
+ d.current = { p: new Promise((r) => {
590
+ done = r;
591
+ }), done };
592
+ }
593
+ const cur = d.current;
594
+ useIsoLayoutEffect(() => {
595
+ if (!waiting && cur) {
596
+ cur.done();
597
+ if (d.current === cur) d.current = null;
598
+ }
599
+ });
600
+ return waiting && cur ? cur.p : null;
601
+ }
602
+ function Arrive({ when, children }) {
603
+ if (when) readPromised(when);
604
+ return /* @__PURE__ */ React2.createElement(React2.Fragment, null, children);
605
+ }
606
+ function useHasWaited(waiting) {
607
+ const r = React2.useRef(false);
608
+ if (waiting) r.current = true;
609
+ return r.current;
610
+ }
611
+ var ScopeContext = React2.createContext(null);
612
+ function LoadingScope({ children }) {
613
+ const [members] = React2.useState(() => /* @__PURE__ */ new Set());
614
+ const [waiting, setWaiting] = React2.useState(false);
615
+ const report = React2.useCallback((id, w) => {
616
+ if (w) members.add(id);
617
+ else members.delete(id);
618
+ setWaiting(members.size > 0);
619
+ }, [members]);
620
+ const value = React2.useMemo(() => ({ report, waiting }), [report, waiting]);
621
+ return /* @__PURE__ */ React2.createElement(ScopeContext.Provider, { value }, children);
622
+ }
623
+ function useReportWaiting(waiting) {
624
+ const scope = React2.useContext(ScopeContext);
625
+ const [id] = React2.useState(() => ({}));
626
+ const report = scope?.report;
627
+ useIsoLayoutEffect(() => {
628
+ report?.(id, waiting);
629
+ }, [report, waiting]);
630
+ useIsoLayoutEffect(() => () => report?.(id, false), [report]);
631
+ }
632
+ var useScopeWaiting = () => !!React2.useContext(ScopeContext)?.waiting;
633
+ var Group = class {
634
+ constructor() {
635
+ this.waiting = /* @__PURE__ */ new Set();
636
+ this.held = /* @__PURE__ */ new Map();
637
+ }
638
+ wait(id) {
639
+ this.waiting.add(id);
640
+ }
641
+ /** Returns true when this was the last one: everything held is released together. */
642
+ land(id, release) {
643
+ this.waiting.delete(id);
644
+ this.held.set(id, release);
645
+ if (this.waiting.size) return false;
646
+ this.flush();
647
+ return true;
648
+ }
649
+ leave(id) {
650
+ this.waiting.delete(id);
651
+ this.held.delete(id);
652
+ if (!this.waiting.size && this.held.size) this.flush();
653
+ }
654
+ flush() {
655
+ const all = Array.from(this.held.values());
656
+ this.held.clear();
657
+ all.forEach((f) => f());
658
+ }
659
+ };
660
+ var GroupContext = React2.createContext(null);
661
+ function RevealGroup({ children }) {
662
+ const group = React2.useMemo(() => new Group(), []);
663
+ return /* @__PURE__ */ React2.createElement(GroupContext.Provider, { value: group }, children);
664
+ }
665
+ var GRACE = 300;
666
+ function Await({ imprint, shape = "block", inline, enabled = true, className, children }) {
667
+ const group = React2.useContext(GroupContext);
668
+ const box = React2.useRef({ id: {}, since: null });
669
+ React2.useEffect(() => () => group?.leave(box.current.id), [group]);
670
+ if (!enabled) return /* @__PURE__ */ React2.createElement(React2.Fragment, null, children);
671
+ return /* @__PURE__ */ React2.createElement(React2.Suspense, { fallback: /* @__PURE__ */ React2.createElement(Imprint, { box, group, inline }, imprint) }, /* @__PURE__ */ React2.createElement(Landed, { box, group, shape, inline, className, imprint }, children));
672
+ }
673
+ function Imprint({ box, group, inline, children }) {
674
+ useIsoLayoutEffect(() => {
675
+ if (box.current.since === null) box.current.since = performance.now();
676
+ group?.wait(box.current.id);
677
+ }, []);
678
+ return /* @__PURE__ */ React2.createElement("span", { className: "alt-await-wait", "data-inline": inline ? "" : void 0, "aria-busy": "true" }, children, /* @__PURE__ */ React2.createElement("span", { className: "alt-sr" }, "Loading"));
679
+ }
680
+ function Landed({ box, group, shape, inline, className, imprint, children }) {
681
+ const [phase, setPhase] = React2.useState(null);
682
+ const [delay, setDelay] = React2.useState(0);
683
+ const [graceLeft, setGraceLeft] = React2.useState(0);
684
+ const done = React2.useRef(void 0);
685
+ useIsoLayoutEffect(() => {
686
+ const since = box.current.since;
687
+ box.current.since = null;
688
+ if (since === null) return;
689
+ const release = () => {
690
+ clearTimeout(done.current);
691
+ if (performance.now() - since < GRACE) {
692
+ setPhase(null);
693
+ return;
694
+ }
695
+ const d = riseDelay();
696
+ setDelay(d);
697
+ setPhase("reveal");
698
+ done.current = setTimeout(() => setPhase(null), d + 320);
699
+ };
700
+ if (group && !group.land(box.current.id, release)) {
701
+ setGraceLeft(Math.max(0, GRACE - (performance.now() - since)));
702
+ setPhase("held");
703
+ } else if (!group) release();
704
+ }, []);
705
+ React2.useEffect(() => () => clearTimeout(done.current), []);
552
706
  return /* @__PURE__ */ React2.createElement(
707
+ "span",
708
+ {
709
+ className: cx("alt-await", className),
710
+ "data-phase": phase ?? void 0,
711
+ "data-inline": inline ? "" : void 0,
712
+ "data-shape": shape,
713
+ "aria-busy": phase === "held" || void 0,
714
+ style: phase ? { ["--alt-rise-delay"]: delay + "ms", ["--alt-grace-left"]: graceLeft + "ms" } : void 0
715
+ },
716
+ phase === "held" && /* @__PURE__ */ React2.createElement("span", { className: "alt-await-held", "data-early": graceLeft > 0 ? "" : void 0, "aria-hidden": "true" }, imprint),
717
+ phase === "reveal" && shape !== "none" && /* @__PURE__ */ React2.createElement("span", { className: "alt-skeleton alt-await-imprint", "data-shape": shape, "aria-hidden": "true" }),
718
+ /* @__PURE__ */ React2.createElement("span", { className: "alt-await-face" }, children)
719
+ );
720
+ }
721
+ var LINE_WIDTHS = ["100%", "94%", "82%", "97%", "64%"];
722
+ function TextImprint({ lines = 1, width, className }) {
723
+ return /* @__PURE__ */ React2.createElement("span", { className: cx("alt-await-lines", className), style: { ["--lines"]: lines, width } }, Array.from({ length: lines }, (_, i) => /* @__PURE__ */ React2.createElement(
724
+ "span",
725
+ {
726
+ key: i,
727
+ className: "alt-skeleton",
728
+ "data-shape": "text",
729
+ style: { width: lines === 1 ? "100%" : i === lines - 1 ? "60%" : LINE_WIDTHS[i % LINE_WIDTHS.length], ["--i"]: i }
730
+ }
731
+ )));
732
+ }
733
+ var hint = (s) => typeof s === "object" ? s : {};
734
+
735
+ // project/components/src/controls.tsx
736
+ var Button = React3.forwardRef(function Button2({ variant = "secondary", size = "md", square, loading, leading, trailing, className, children, disabled, type = "button", ...rest }, ref) {
737
+ return /* @__PURE__ */ React3.createElement(
553
738
  "button",
554
739
  {
555
740
  ref,
@@ -564,14 +749,15 @@ var Button = React2.forwardRef(function Button2({ variant = "secondary", size =
564
749
  ...rest,
565
750
  onClick: loading ? (e) => e.preventDefault() : rest.onClick
566
751
  },
567
- /* @__PURE__ */ React2.createElement("span", { className: "alt-btn-label" }, leading, children, trailing),
568
- loading && /* @__PURE__ */ React2.createElement("span", { className: "alt-btn-spinner" }, /* @__PURE__ */ React2.createElement(Spinner, { size: size === "sm" ? 14 : 16 }))
752
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-btn-label" }, leading, children, trailing),
753
+ loading && /* @__PURE__ */ React3.createElement("span", { className: "alt-btn-spinner" }, /* @__PURE__ */ React3.createElement(Spinner, { size: size === "sm" ? 14 : 16 }))
569
754
  );
570
755
  });
571
- var Card = React2.forwardRef(function Card2({ interactive, className, onKeyDown, settle, status, heldBy, relevance, style, ...rest }, ref) {
756
+ var Card = React3.forwardRef(function Card2({ interactive, className, onKeyDown, settle, status, heldBy, relevance, style, skeleton, children, ...rest }, ref) {
572
757
  const actionable = interactive && !!rest.onClick;
573
758
  const { style: depthStyle, ...depth } = useDepth({ settle, status, heldBy, relevance });
574
- return /* @__PURE__ */ React2.createElement(
759
+ const { lines = 3 } = hint(skeleton);
760
+ return /* @__PURE__ */ React3.createElement(
575
761
  "div",
576
762
  {
577
763
  ref,
@@ -588,29 +774,51 @@ var Card = React2.forwardRef(function Card2({ interactive, className, onKeyDown,
588
774
  ...depth,
589
775
  style: { ...depthStyle, ...style },
590
776
  ...rest
591
- }
777
+ },
778
+ /* @__PURE__ */ React3.createElement(LoadingScope, null, /* @__PURE__ */ React3.createElement(Await, { shape: "none", enabled: skeleton !== false, imprint: /* @__PURE__ */ React3.createElement("span", { className: "alt-await-card" }, /* @__PURE__ */ React3.createElement(TextImprint, { className: "alt-card-title", width: "45%" }), /* @__PURE__ */ React3.createElement(TextImprint, { className: "alt-await-card-body", lines })) }, children))
592
779
  );
593
780
  });
594
- var CardHeader = ({ className, ...p }) => /* @__PURE__ */ React2.createElement("div", { className: cx("alt-card-header", className), ...p });
595
- var CardTitle = ({ className, ...p }) => /* @__PURE__ */ React2.createElement("h3", { className: cx("alt-card-title", className), ...p });
596
- var CardDescription = ({ className, ...p }) => /* @__PURE__ */ React2.createElement("p", { className: cx("alt-card-desc", className), ...p });
597
- var CardContent = ({ className, ...p }) => /* @__PURE__ */ React2.createElement("div", { className: cx("alt-card-content", className), ...p });
598
- var CardFooter = ({ className, ...p }) => /* @__PURE__ */ React2.createElement("div", { className: cx("alt-card-footer", className), ...p });
599
- var Input = React2.forwardRef(function Input2({ invalid, leading, trailing, size = "md", className, disabled, placeholder, ...rest }, ref) {
781
+ var CardHeader = ({ className, ...p }) => /* @__PURE__ */ React3.createElement("div", { className: cx("alt-card-header", className), ...p });
782
+ var Promised$ = ({ children }) => /* @__PURE__ */ React3.createElement(React3.Fragment, null, readChildren(children));
783
+ function usePendingText(children, skeleton, required) {
784
+ const scopeWaiting = useScopeWaiting();
785
+ const missing = skeleton !== false && children === void 0 && (required || scopeWaiting);
786
+ useReportWaiting(required && skeleton !== false && (children === void 0 || hasPromise(children)));
787
+ const arrival = useArrival(missing);
788
+ const waited = useHasWaited(missing || hasPromise(children));
789
+ return { arrival, waited };
790
+ }
791
+ function PendingText({ children, skeleton, lines, width, required }) {
792
+ const { arrival, waited } = usePendingText(children, skeleton, required);
793
+ if (!waited) return /* @__PURE__ */ React3.createElement(React3.Fragment, null, children);
794
+ const h = hint(skeleton);
795
+ return /* @__PURE__ */ React3.createElement(Await, { shape: "text", enabled: skeleton !== false, imprint: /* @__PURE__ */ React3.createElement(TextImprint, { lines: h.lines ?? lines, width: h.width ?? width }) }, /* @__PURE__ */ React3.createElement(Arrive, { when: arrival }, /* @__PURE__ */ React3.createElement(Promised$, null, children)));
796
+ }
797
+ var CardTitle = ({ className, children, skeleton, ...p }) => /* @__PURE__ */ React3.createElement("h3", { className: cx("alt-card-title", className), ...p }, /* @__PURE__ */ React3.createElement(PendingText, { skeleton, lines: 1, width: "55%", required: true }, children));
798
+ var CardDescription = ({ className, children, skeleton, ...p }) => /* @__PURE__ */ React3.createElement("p", { className: cx("alt-card-desc", className), ...p }, /* @__PURE__ */ React3.createElement(PendingText, { skeleton, lines: 2, required: false }, children));
799
+ var CardContent = ({ className, skeleton, children, ...p }) => {
800
+ const { lines = 3 } = hint(skeleton);
801
+ const scopeWaiting = useScopeWaiting();
802
+ const missing = skeleton !== false && children === void 0 && scopeWaiting;
803
+ const arrival = useArrival(missing);
804
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-card-content", className), ...p }, /* @__PURE__ */ React3.createElement(Await, { shape: "none", enabled: skeleton !== false, imprint: /* @__PURE__ */ React3.createElement(TextImprint, { lines }) }, /* @__PURE__ */ React3.createElement(Arrive, { when: arrival }, children)));
805
+ };
806
+ var CardFooter = ({ className, ...p }) => /* @__PURE__ */ React3.createElement("div", { className: cx("alt-card-footer", className), ...p });
807
+ var Input = React3.forwardRef(function Input2({ invalid, leading, trailing, size = "md", className, disabled, placeholder, ...rest }, ref) {
600
808
  useApproach();
601
809
  useKeyFocus();
602
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-input", className), "data-size": size, "data-approach": "56", "data-invalid": invalid ? "" : void 0, "data-disabled": disabled ? "" : void 0 }, leading && /* @__PURE__ */ React2.createElement("span", { className: "alt-input-adorn" }, leading), /* @__PURE__ */ React2.createElement("input", { ref, disabled, "aria-invalid": invalid || void 0, placeholder: placeholder ?? " ", ...rest }), trailing && /* @__PURE__ */ React2.createElement("span", { className: "alt-input-adorn" }, trailing));
810
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-input", className), "data-size": size, "data-approach": "56", "data-invalid": invalid ? "" : void 0, "data-disabled": disabled ? "" : void 0 }, leading && /* @__PURE__ */ React3.createElement("span", { className: "alt-input-adorn" }, leading), /* @__PURE__ */ React3.createElement("input", { ref, disabled, "aria-invalid": invalid || void 0, placeholder: placeholder ?? " ", ...rest }), trailing && /* @__PURE__ */ React3.createElement("span", { className: "alt-input-adorn" }, trailing));
603
811
  });
604
- var Textarea = React2.forwardRef(function Textarea2({ invalid, className, disabled, placeholder, maxLength, showFill = true, onChange, value, defaultValue, ...rest }, ref) {
605
- const [len, setLen] = React2.useState(() => String(value ?? defaultValue ?? "").length);
606
- React2.useEffect(() => {
812
+ var Textarea = React3.forwardRef(function Textarea2({ invalid, className, disabled, placeholder, maxLength, showFill = true, onChange, value, defaultValue, ...rest }, ref) {
813
+ const [len, setLen] = React3.useState(() => String(value ?? defaultValue ?? "").length);
814
+ React3.useEffect(() => {
607
815
  if (value !== void 0) setLen(String(value).length);
608
816
  }, [value]);
609
817
  const gauge = showFill && maxLength ? Math.min(1, len / maxLength) : null;
610
818
  const level = gauge === null ? void 0 : len >= maxLength ? "full" : gauge >= 0.9 ? "near" : "ok";
611
819
  useApproach();
612
820
  useKeyFocus();
613
- return /* @__PURE__ */ React2.createElement(
821
+ return /* @__PURE__ */ React3.createElement(
614
822
  "div",
615
823
  {
616
824
  className: cx("alt-input", className),
@@ -621,8 +829,8 @@ var Textarea = React2.forwardRef(function Textarea2({ invalid, className, disabl
621
829
  "data-fill": level,
622
830
  style: gauge !== null ? { ["--alt-fill"]: gauge } : void 0
623
831
  },
624
- gauge !== null && /* @__PURE__ */ React2.createElement("span", { className: "alt-input-gauge", "aria-hidden": "true" }),
625
- /* @__PURE__ */ React2.createElement(
832
+ gauge !== null && /* @__PURE__ */ React3.createElement("span", { className: "alt-input-gauge", "aria-hidden": "true" }),
833
+ /* @__PURE__ */ React3.createElement(
626
834
  "textarea",
627
835
  {
628
836
  ref,
@@ -639,22 +847,22 @@ var Textarea = React2.forwardRef(function Textarea2({ invalid, className, disabl
639
847
  }
640
848
  }
641
849
  ),
642
- gauge !== null && /* @__PURE__ */ React2.createElement("span", { className: "alt-input-count", "aria-live": "polite" }, len, " / ", maxLength)
850
+ gauge !== null && /* @__PURE__ */ React3.createElement("span", { className: "alt-input-count", "aria-live": "polite" }, len, " / ", maxLength)
643
851
  );
644
852
  });
645
- function Field({ label, hint, error, required, className, children }) {
646
- const id = React2.useId();
853
+ function Field({ label, hint: hint2, error, required, className, children }) {
854
+ const id = React3.useId();
647
855
  const controlId = children.props.id || id + "-control";
648
- const describedBy = [hint && id + "-hint", error && id + "-error"].filter(Boolean).join(" ") || void 0;
649
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-field", className) }, /* @__PURE__ */ React2.createElement("label", { className: "alt-field-label", htmlFor: controlId }, label, required && /* @__PURE__ */ React2.createElement("span", { className: "alt-field-req", "aria-hidden": "true" }, " *")), React2.cloneElement(children, { id: controlId, "aria-describedby": describedBy, invalid: !!error || children.props.invalid, required }), hint && !error && /* @__PURE__ */ React2.createElement("p", { className: "alt-field-hint", id: id + "-hint" }, hint), error && /* @__PURE__ */ React2.createElement("p", { className: "alt-field-error", id: id + "-error", role: "alert" }, /* @__PURE__ */ React2.createElement(Icons.AlertCircle, { size: 14 }), error));
856
+ const describedBy = [hint2 && id + "-hint", error && id + "-error"].filter(Boolean).join(" ") || void 0;
857
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-field", className) }, /* @__PURE__ */ React3.createElement("label", { className: "alt-field-label", htmlFor: controlId }, label, required && /* @__PURE__ */ React3.createElement("span", { className: "alt-field-req", "aria-hidden": "true" }, " *")), React3.cloneElement(children, { id: controlId, "aria-describedby": describedBy, invalid: !!error || children.props.invalid, required }), hint2 && !error && /* @__PURE__ */ React3.createElement("p", { className: "alt-field-hint", id: id + "-hint" }, hint2), error && /* @__PURE__ */ React3.createElement("p", { className: "alt-field-error", id: id + "-error", role: "alert" }, /* @__PURE__ */ React3.createElement(Icons.AlertCircle, { size: 14 }), error));
650
858
  }
651
- var Checkbox = React2.forwardRef(function Checkbox2({ label, description, indeterminate, onCheckedChange, onChange, className, disabled, ...rest }, ref) {
652
- const inner = React2.useRef(null);
653
- React2.useImperativeHandle(ref, () => inner.current);
654
- React2.useEffect(() => {
859
+ var Checkbox = React3.forwardRef(function Checkbox2({ label, description, indeterminate, onCheckedChange, onChange, className, disabled, ...rest }, ref) {
860
+ const inner = React3.useRef(null);
861
+ React3.useImperativeHandle(ref, () => inner.current);
862
+ React3.useEffect(() => {
655
863
  if (inner.current) inner.current.indeterminate = !!indeterminate;
656
864
  }, [indeterminate]);
657
- return /* @__PURE__ */ React2.createElement("label", { className: cx("alt-check", className), "data-disabled": disabled ? "" : void 0 }, /* @__PURE__ */ React2.createElement(
865
+ return /* @__PURE__ */ React3.createElement("label", { className: cx("alt-check", className), "data-disabled": disabled ? "" : void 0 }, /* @__PURE__ */ React3.createElement(
658
866
  "input",
659
867
  {
660
868
  ref: inner,
@@ -666,20 +874,20 @@ var Checkbox = React2.forwardRef(function Checkbox2({ label, description, indete
666
874
  onCheckedChange?.(e.target.checked);
667
875
  }
668
876
  }
669
- ), /* @__PURE__ */ React2.createElement("span", { className: "alt-check-track", "aria-hidden": "true" }, /* @__PURE__ */ React2.createElement("span", { className: "alt-check-fill" }), /* @__PURE__ */ React2.createElement("svg", { className: "alt-check-mark", viewBox: "0 0 16 16", width: "14", height: "14", fill: "none", stroke: "currentColor", strokeWidth: "2.25", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ React2.createElement("path", { className: "alt-check-tick", d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }), /* @__PURE__ */ React2.createElement("path", { className: "alt-check-dash", d: "M4 8h8", pathLength: 16 }))), (label || description) && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-text" }, label && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-label" }, label), description && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-desc" }, description)));
877
+ ), /* @__PURE__ */ React3.createElement("span", { className: "alt-check-track", "aria-hidden": "true" }, /* @__PURE__ */ React3.createElement("span", { className: "alt-check-fill" }), /* @__PURE__ */ React3.createElement("svg", { className: "alt-check-mark", viewBox: "0 0 16 16", width: "14", height: "14", fill: "none", stroke: "currentColor", strokeWidth: "2.25", strokeLinecap: "round", strokeLinejoin: "round" }, /* @__PURE__ */ React3.createElement("path", { className: "alt-check-tick", d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }), /* @__PURE__ */ React3.createElement("path", { className: "alt-check-dash", d: "M4 8h8", pathLength: 16 }))), (label || description) && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-text" }, label && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-label" }, label), description && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-desc" }, description)));
670
878
  });
671
- var RadioCtx = React2.createContext(null);
879
+ var RadioCtx = React3.createContext(null);
672
880
  function RadioGroup({ value, defaultValue = "", onValueChange, name, disabled, orientation = "vertical", className, children, ...rest }) {
673
- const auto = React2.useId();
881
+ const auto = React3.useId();
674
882
  const [v, set] = useControllable(value, defaultValue, onValueChange);
675
- const root = React2.useRef(null);
676
- const slots = React2.useRef(/* @__PURE__ */ new Map());
677
- const [bead, setBead] = React2.useState(null);
678
- const register = React2.useCallback((val, el) => {
883
+ const root = React3.useRef(null);
884
+ const slots = React3.useRef(/* @__PURE__ */ new Map());
885
+ const [bead, setBead] = React3.useState(null);
886
+ const register = React3.useCallback((val, el) => {
679
887
  if (el) slots.current.set(val, el);
680
888
  else slots.current.delete(val);
681
889
  }, []);
682
- const measure = React2.useCallback(() => {
890
+ const measure = React3.useCallback(() => {
683
891
  const el = slots.current.get(v), r = root.current;
684
892
  if (!el || !r) {
685
893
  setBead(null);
@@ -692,13 +900,13 @@ function RadioGroup({ value, defaultValue = "", onValueChange, name, disabled, o
692
900
  useIsoLayoutEffect(() => {
693
901
  measure();
694
902
  }, [measure]);
695
- React2.useEffect(() => {
903
+ React3.useEffect(() => {
696
904
  const ro = new ResizeObserver(() => measure());
697
905
  if (root.current) ro.observe(root.current);
698
906
  document.fonts?.ready.then(() => measure());
699
907
  return () => ro.disconnect();
700
908
  }, [measure]);
701
- return /* @__PURE__ */ React2.createElement(RadioCtx.Provider, { value: { name: name || auto, value: v, set, disabled, register } }, /* @__PURE__ */ React2.createElement("div", { ref: root, role: "radiogroup", className: cx("alt-radio-group", className), "data-orientation": orientation, "data-disabled": disabled ? "" : void 0, ...rest }, children, bead && /* @__PURE__ */ React2.createElement(
909
+ return /* @__PURE__ */ React3.createElement(RadioCtx.Provider, { value: { name: name || auto, value: v, set, disabled, register } }, /* @__PURE__ */ React3.createElement("div", { ref: root, role: "radiogroup", className: cx("alt-radio-group", className), "data-orientation": orientation, "data-disabled": disabled ? "" : void 0, ...rest }, children, bead && /* @__PURE__ */ React3.createElement(
702
910
  "span",
703
911
  {
704
912
  className: "alt-radio-thumb",
@@ -709,9 +917,9 @@ function RadioGroup({ value, defaultValue = "", onValueChange, name, disabled, o
709
917
  )));
710
918
  }
711
919
  function Radio({ value, label, description, disabled, className }) {
712
- const g = React2.useContext(RadioCtx);
920
+ const g = React3.useContext(RadioCtx);
713
921
  const off = disabled || g?.disabled;
714
- return /* @__PURE__ */ React2.createElement("label", { className: cx("alt-check alt-radio", className), "data-disabled": off ? "" : void 0 }, /* @__PURE__ */ React2.createElement(
922
+ return /* @__PURE__ */ React3.createElement("label", { className: cx("alt-check alt-radio", className), "data-disabled": off ? "" : void 0 }, /* @__PURE__ */ React3.createElement(
715
923
  "input",
716
924
  {
717
925
  type: "radio",
@@ -721,11 +929,11 @@ function Radio({ value, label, description, disabled, className }) {
721
929
  checked: g ? g.value === value : void 0,
722
930
  onChange: () => g?.set(value)
723
931
  }
724
- ), /* @__PURE__ */ React2.createElement("span", { className: "alt-check-track", "data-round": "", "aria-hidden": "true", ref: (el) => g?.register(value, el) }, /* @__PURE__ */ React2.createElement("span", { className: "alt-check-fill" })), (label || description) && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-text" }, label && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-label" }, label), description && /* @__PURE__ */ React2.createElement("span", { className: "alt-check-desc" }, description)));
932
+ ), /* @__PURE__ */ React3.createElement("span", { className: "alt-check-track", "data-round": "", "aria-hidden": "true", ref: (el) => g?.register(value, el) }, /* @__PURE__ */ React3.createElement("span", { className: "alt-check-fill" })), (label || description) && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-text" }, label && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-label" }, label), description && /* @__PURE__ */ React3.createElement("span", { className: "alt-check-desc" }, description)));
725
933
  }
726
934
  function Switch({ checked, defaultChecked = false, onCheckedChange, label, className, disabled, ...rest }) {
727
935
  const [on, set] = useControllable(checked, defaultChecked, onCheckedChange);
728
- const control = /* @__PURE__ */ React2.createElement(
936
+ const control = /* @__PURE__ */ React3.createElement(
729
937
  "button",
730
938
  {
731
939
  type: "button",
@@ -739,29 +947,29 @@ function Switch({ checked, defaultChecked = false, onCheckedChange, label, class
739
947
  set(!on);
740
948
  }
741
949
  },
742
- /* @__PURE__ */ React2.createElement("span", { className: "alt-switch-fill" }),
743
- /* @__PURE__ */ React2.createElement("span", { className: "alt-switch-thumb" })
950
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-switch-fill" }),
951
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-switch-thumb" })
744
952
  );
745
953
  if (!label) return control;
746
- return /* @__PURE__ */ React2.createElement("label", { className: cx("alt-switch-row", className), "data-disabled": disabled ? "" : void 0 }, control, /* @__PURE__ */ React2.createElement("span", null, label));
954
+ return /* @__PURE__ */ React3.createElement("label", { className: cx("alt-switch-row", className), "data-disabled": disabled ? "" : void 0 }, control, /* @__PURE__ */ React3.createElement("span", null, label));
747
955
  }
748
- var TabsCtx = React2.createContext(null);
956
+ var TabsCtx = React3.createContext(null);
749
957
  function Tabs({ value, defaultValue = "", onValueChange, variant = "folder", className, children, ...rest }) {
750
958
  const [v, set] = useControllable(value, defaultValue, onValueChange);
751
- const id = React2.useId();
752
- const nodes = React2.useRef(/* @__PURE__ */ new Map());
753
- const register = React2.useCallback((val, el) => {
959
+ const id = React3.useId();
960
+ const nodes = React3.useRef(/* @__PURE__ */ new Map());
961
+ const register = React3.useCallback((val, el) => {
754
962
  if (el) nodes.current.set(val, el);
755
963
  else nodes.current.delete(val);
756
964
  }, []);
757
- return /* @__PURE__ */ React2.createElement(TabsCtx.Provider, { value: { value: v, set, id, variant, register, nodes } }, /* @__PURE__ */ React2.createElement("div", { className: cx("alt-tabs", className), "data-variant": variant, ...rest }, children));
965
+ return /* @__PURE__ */ React3.createElement(TabsCtx.Provider, { value: { value: v, set, id, variant, register, nodes } }, /* @__PURE__ */ React3.createElement("div", { className: cx("alt-tabs", className), "data-variant": variant, ...rest }, children));
758
966
  }
759
967
  function TabsList({ className, children, ...rest }) {
760
- const t = React2.useContext(TabsCtx);
761
- const listRef = React2.useRef(null);
968
+ const t = React3.useContext(TabsCtx);
969
+ const listRef = React3.useRef(null);
762
970
  const pill = t.variant === "segmented";
763
- const [ind, setInd] = React2.useState({ x: 0, w: 0, ready: false });
764
- const measure = React2.useCallback(() => {
971
+ const [ind, setInd] = React3.useState({ x: 0, w: 0, ready: false });
972
+ const measure = React3.useCallback(() => {
765
973
  if (!pill) return;
766
974
  const el = t.nodes.current.get(t.value);
767
975
  if (!el) return;
@@ -770,7 +978,7 @@ function TabsList({ className, children, ...rest }) {
770
978
  useIsoLayoutEffect(() => {
771
979
  measure();
772
980
  }, [measure]);
773
- React2.useEffect(() => {
981
+ React3.useEffect(() => {
774
982
  if (!pill) return;
775
983
  const ro = new ResizeObserver(measure);
776
984
  if (listRef.current) ro.observe(listRef.current);
@@ -787,7 +995,7 @@ function TabsList({ className, children, ...rest }) {
787
995
  t.nodes.current.get(next)?.focus();
788
996
  }
789
997
  };
790
- return /* @__PURE__ */ React2.createElement("div", { ref: listRef, role: "tablist", className: cx("alt-tabs-list", className), onKeyDown, ...rest }, pill && /* @__PURE__ */ React2.createElement(
998
+ return /* @__PURE__ */ React3.createElement("div", { ref: listRef, role: "tablist", className: cx("alt-tabs-list", className), onKeyDown, ...rest }, pill && /* @__PURE__ */ React3.createElement(
791
999
  "span",
792
1000
  {
793
1001
  className: "alt-tabs-indicator",
@@ -798,9 +1006,9 @@ function TabsList({ className, children, ...rest }) {
798
1006
  ), children);
799
1007
  }
800
1008
  function TabsTrigger({ value, className, children, ...rest }) {
801
- const t = React2.useContext(TabsCtx);
1009
+ const t = React3.useContext(TabsCtx);
802
1010
  const on = t.value === value;
803
- return /* @__PURE__ */ React2.createElement(
1011
+ return /* @__PURE__ */ React3.createElement(
804
1012
  "button",
805
1013
  {
806
1014
  ref: (el) => t.register(value, el),
@@ -818,21 +1026,21 @@ function TabsTrigger({ value, className, children, ...rest }) {
818
1026
  );
819
1027
  }
820
1028
  function TabsContent({ value, className, ...rest }) {
821
- const t = React2.useContext(TabsCtx);
1029
+ const t = React3.useContext(TabsCtx);
822
1030
  if (t.value !== value) return null;
823
- return /* @__PURE__ */ React2.createElement("div", { role: "tabpanel", id: `${t.id}-p-${value}`, "aria-labelledby": `${t.id}-t-${value}`, tabIndex: 0, className: cx("alt-tabs-content", className), ...rest });
1031
+ return /* @__PURE__ */ React3.createElement("div", { role: "tabpanel", id: `${t.id}-p-${value}`, "aria-labelledby": `${t.id}-t-${value}`, tabIndex: 0, className: cx("alt-tabs-content", className), ...rest });
824
1032
  }
825
1033
  function Slider({ value, defaultValue = 50, onValueChange, min = 0, max = 100, step = 1, disabled, format = (v) => v, className, ...rest }) {
826
1034
  const [v, set] = useControllable(value, defaultValue, onValueChange);
827
- const [drag, setDrag] = React2.useState(false);
828
- const track = React2.useRef(null);
1035
+ const [drag, setDrag] = React3.useState(false);
1036
+ const track = React3.useRef(null);
829
1037
  const clamp = (n) => Math.min(max, Math.max(min, Math.round((n - min) / step) * step + min));
830
1038
  const fromX = (x) => {
831
1039
  const r = track.current.getBoundingClientRect();
832
1040
  return clamp(min + (x - r.left) / r.width * (max - min));
833
1041
  };
834
1042
  const pct = (v - min) / (max - min) * 100;
835
- return /* @__PURE__ */ React2.createElement(
1043
+ return /* @__PURE__ */ React3.createElement(
836
1044
  "div",
837
1045
  {
838
1046
  className: cx("alt-slider", className),
@@ -852,8 +1060,8 @@ function Slider({ value, defaultValue = 50, onValueChange, min = 0, max = 100, s
852
1060
  onPointerCancel: () => setDrag(false),
853
1061
  ...rest
854
1062
  },
855
- /* @__PURE__ */ React2.createElement("div", { className: "alt-slider-track", ref: track }, /* @__PURE__ */ React2.createElement("div", { className: "alt-slider-fill", style: { width: pct + "%" } })),
856
- /* @__PURE__ */ React2.createElement(
1063
+ /* @__PURE__ */ React3.createElement("div", { className: "alt-slider-track", ref: track }, /* @__PURE__ */ React3.createElement("div", { className: "alt-slider-fill", style: { width: pct + "%" } })),
1064
+ /* @__PURE__ */ React3.createElement(
857
1065
  "div",
858
1066
  {
859
1067
  className: "alt-slider-thumb",
@@ -874,13 +1082,13 @@ function Slider({ value, defaultValue = 50, onValueChange, min = 0, max = 100, s
874
1082
  }
875
1083
  }
876
1084
  },
877
- /* @__PURE__ */ React2.createElement("span", { className: "alt-slider-bubble", "aria-hidden": "true" }, format(v))
1085
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-slider-bubble", "aria-hidden": "true" }, format(v))
878
1086
  )
879
1087
  );
880
1088
  }
881
1089
  function Progress({ value = null, max = 100, className, ...rest }) {
882
1090
  const ind = value === null || value === void 0;
883
- return /* @__PURE__ */ React2.createElement(
1091
+ return /* @__PURE__ */ React3.createElement(
884
1092
  "div",
885
1093
  {
886
1094
  role: "progressbar",
@@ -891,31 +1099,72 @@ function Progress({ value = null, max = 100, className, ...rest }) {
891
1099
  "data-indeterminate": ind ? "" : void 0,
892
1100
  ...rest
893
1101
  },
894
- /* @__PURE__ */ React2.createElement("div", { className: "alt-progress-fill", style: ind ? void 0 : { width: `${Math.max(0, Math.min(100, value / max * 100))}%` } })
1102
+ /* @__PURE__ */ React3.createElement("div", { className: "alt-progress-fill", style: ind ? void 0 : { width: `${Math.max(0, Math.min(100, value / max * 100))}%` } })
1103
+ );
1104
+ }
1105
+ function Badge({ children, skeleton, ...props }) {
1106
+ const missing = skeleton !== false && children === void 0;
1107
+ useReportWaiting(missing || skeleton !== false && hasPromise(children));
1108
+ const arrival = useArrival(missing);
1109
+ if (!useHasWaited(missing || hasPromise(children))) return /* @__PURE__ */ React3.createElement(BadgeFace, { ...props }, children);
1110
+ const h = hint(skeleton);
1111
+ return /* @__PURE__ */ React3.createElement(
1112
+ Await,
1113
+ {
1114
+ inline: true,
1115
+ shape: "block",
1116
+ enabled: skeleton !== false,
1117
+ imprint: /* @__PURE__ */ React3.createElement("span", { className: "alt-skeleton alt-badge-imprint", "data-variant": props.variant === "count" ? "count" : void 0, style: { width: h.width } })
1118
+ },
1119
+ /* @__PURE__ */ React3.createElement(Arrive, { when: arrival }, /* @__PURE__ */ React3.createElement(BadgeLanded, { ...props }, children))
895
1120
  );
896
1121
  }
897
- function Badge({ tone = "neutral", variant = "plate", lamp, dot, className, children, ...rest }) {
1122
+ function BadgeLanded({ children, ...props }) {
1123
+ return /* @__PURE__ */ React3.createElement(BadgeFace, { ...props }, readChildren(children));
1124
+ }
1125
+ function BadgeFace({ tone = "neutral", variant = "plate", lamp, dot, className, children, ...rest }) {
898
1126
  const v = variant === "soft" ? "tinted" : variant;
899
1127
  const showLamp = v !== "count" && !!(lamp ?? (dot || tone === "positive" || tone === "caution" || tone === "critical"));
900
1128
  const label = typeof children === "string" || typeof children === "number" ? String(children) : void 0;
901
- const [stamp, setStamp] = React2.useState(void 0);
902
- const [lit, setLit] = React2.useState(0);
903
- const prev = React2.useRef({ tone, label });
904
- React2.useEffect(() => {
1129
+ const [stamp, setStamp] = React3.useState(void 0);
1130
+ const [lit, setLit] = React3.useState(0);
1131
+ const prev = React3.useRef({ tone, label });
1132
+ React3.useEffect(() => {
905
1133
  const p = prev.current;
906
1134
  if (p.label !== label) setStamp((x) => x === "a" ? "b" : "a");
907
1135
  if (p.tone !== tone) setLit((n) => n + 1);
908
1136
  prev.current = { tone, label };
909
1137
  }, [tone, label]);
910
- return /* @__PURE__ */ React2.createElement("span", { className: cx("alt-badge", className), "data-tone": tone, "data-variant": v, "data-stamp": stamp, ...rest }, showLamp && /* @__PURE__ */ React2.createElement("span", { key: lit, className: "alt-badge-lamp", "aria-hidden": "true", "data-lit": lit ? "" : void 0, "data-pulse": lamp === "pulse" ? "" : void 0 }), children);
1138
+ return /* @__PURE__ */ React3.createElement("span", { className: cx("alt-badge", className), "data-tone": tone, "data-variant": v, "data-stamp": stamp, ...rest }, showLamp && /* @__PURE__ */ React3.createElement("span", { key: lit, className: "alt-badge-lamp", "aria-hidden": "true", "data-lit": lit ? "" : void 0, "data-pulse": lamp === "pulse" ? "" : void 0 }), children);
911
1139
  }
912
1140
  var TINTS = ["accent", "positive", "caution", "critical"];
913
- function Avatar({ name, src, size = 36, status, live, presence, lamp, className, style, onClick, ...rest }) {
1141
+ function Avatar({ skeleton, ...props }) {
1142
+ const missing = skeleton !== false && props.name === void 0;
1143
+ const promised = isPromise(props.name) || isPromise(props.src);
1144
+ useReportWaiting(missing || skeleton !== false && isPromise(props.name));
1145
+ const arrival = useArrival(missing);
1146
+ if (!useHasWaited(missing || promised)) return /* @__PURE__ */ React3.createElement(AvatarFace, { ...props, name: props.name ?? "", src: props.src });
1147
+ const size = props.size ?? 36;
1148
+ return /* @__PURE__ */ React3.createElement(
1149
+ Await,
1150
+ {
1151
+ inline: true,
1152
+ shape: "circle",
1153
+ enabled: skeleton !== false,
1154
+ imprint: /* @__PURE__ */ React3.createElement("span", { className: "alt-skeleton alt-avatar-imprint", "data-shape": "circle", style: { width: size, height: size } })
1155
+ },
1156
+ /* @__PURE__ */ React3.createElement(Arrive, { when: arrival }, /* @__PURE__ */ React3.createElement(AvatarLanded, { ...props }))
1157
+ );
1158
+ }
1159
+ function AvatarLanded(props) {
1160
+ return /* @__PURE__ */ React3.createElement(AvatarFace, { ...props, name: readPromised(props.name) ?? "", src: readPromised(props.src) });
1161
+ }
1162
+ function AvatarFace({ name, src, size = 36, status, live, presence, lamp, className, style, onClick, ...rest }) {
914
1163
  const initials = name.split(/\s+/).filter(Boolean).slice(0, 2).map((w) => w[0].toUpperCase()).join("");
915
1164
  const tint = TINTS[[...name].reduce((a, c) => a + c.charCodeAt(0), 0) % TINTS.length];
916
1165
  const label = [name, status, live && "live"].filter(Boolean).join(", ");
917
1166
  const showLamp = (lamp ?? size >= 24) && (status === "active" || status === "idle");
918
- return /* @__PURE__ */ React2.createElement(
1167
+ return /* @__PURE__ */ React3.createElement(
919
1168
  "span",
920
1169
  {
921
1170
  className: cx("alt-avatar", className),
@@ -938,29 +1187,29 @@ function Avatar({ name, src, size = 36, status, live, presence, lamp, className,
938
1187
  style: { ["--size"]: size + "px", ...style },
939
1188
  ...rest
940
1189
  },
941
- /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar-shadow", "aria-hidden": "true" }),
942
- /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar-face" }, src ? /* @__PURE__ */ React2.createElement("img", { src, alt: "" }) : initials),
943
- showLamp && /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar-lamp", "aria-hidden": "true" })
1190
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar-shadow", "aria-hidden": "true" }),
1191
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar-face" }, src ? /* @__PURE__ */ React3.createElement("img", { src, alt: "" }) : initials),
1192
+ showLamp && /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar-lamp", "aria-hidden": "true" })
944
1193
  );
945
1194
  }
946
1195
  function AvatarGroup({ className, children, max, style, ...rest }) {
947
- const all = React2.Children.toArray(children);
1196
+ const all = React3.Children.toArray(children);
948
1197
  const shown = max ? all.slice(0, max) : all;
949
1198
  const extra = all.length - shown.length;
950
1199
  const size = shown[0]?.props?.size || 36;
951
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-avatar-group", className), style: { ["--size"]: size + "px", ...style }, ...rest }, shown, extra > 0 && /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar", "data-tint": "more", role: "img", "aria-label": `${extra} more`, style: { ["--size"]: size + "px" } }, /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar-shadow", "aria-hidden": "true" }), /* @__PURE__ */ React2.createElement("span", { className: "alt-avatar-face" }, "+", extra)));
1200
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-avatar-group", className), style: { ["--size"]: size + "px", ...style }, ...rest }, shown, extra > 0 && /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar", "data-tint": "more", role: "img", "aria-label": `${extra} more`, style: { ["--size"]: size + "px" } }, /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar-shadow", "aria-hidden": "true" }), /* @__PURE__ */ React3.createElement("span", { className: "alt-avatar-face" }, "+", extra)));
952
1201
  }
953
- var LINE_WIDTHS = ["100%", "94%", "82%", "97%", "64%"];
1202
+ var LINE_WIDTHS2 = ["100%", "94%", "82%", "97%", "64%"];
954
1203
  function Skeleton({ loaded, shape = "block", lines = 3, width, height, radius, className, style, children, ...rest }) {
955
- const [reveal, setReveal] = React2.useState(null);
956
- const was = React2.useRef(loaded);
957
- React2.useEffect(() => {
1204
+ const [reveal, setReveal] = React3.useState(null);
1205
+ const was = React3.useRef(loaded);
1206
+ React3.useEffect(() => {
958
1207
  if (loaded && !was.current) setReveal(riseDelay());
959
1208
  if (!loaded) setReveal(null);
960
1209
  was.current = loaded;
961
1210
  }, [loaded]);
962
1211
  if (loaded) {
963
- return /* @__PURE__ */ React2.createElement(
1212
+ return /* @__PURE__ */ React3.createElement(
964
1213
  "div",
965
1214
  {
966
1215
  className: cx("alt-reveal", className),
@@ -968,14 +1217,14 @@ function Skeleton({ loaded, shape = "block", lines = 3, width, height, radius, c
968
1217
  style: { ...reveal ? { ["--alt-rise-delay"]: reveal + "ms" } : null, ...style },
969
1218
  ...rest
970
1219
  },
971
- /* @__PURE__ */ React2.createElement("div", { className: "alt-reveal-inner" }, children)
1220
+ /* @__PURE__ */ React3.createElement("div", { className: "alt-reveal-inner" }, children)
972
1221
  );
973
1222
  }
974
1223
  if (shape === "text") {
975
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-skeleton-lines", className), "aria-hidden": "true", style: { width, ...style }, ...rest }, Array.from({ length: lines }, (_, i) => /* @__PURE__ */ React2.createElement("div", { key: i, className: "alt-skeleton", "data-shape": "text", style: { width: i === lines - 1 && lines > 1 ? "60%" : LINE_WIDTHS[i % LINE_WIDTHS.length], height: height ?? 12, ["--i"]: i } })));
1224
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-skeleton-lines", className), "aria-hidden": "true", style: { width, ...style }, ...rest }, Array.from({ length: lines }, (_, i) => /* @__PURE__ */ React3.createElement("div", { key: i, className: "alt-skeleton", "data-shape": "text", style: { width: i === lines - 1 && lines > 1 ? "60%" : LINE_WIDTHS2[i % LINE_WIDTHS2.length], height: height ?? 12, ["--i"]: i } })));
976
1225
  }
977
1226
  const d = shape === "circle" ? width ?? height ?? 40 : void 0;
978
- return /* @__PURE__ */ React2.createElement(
1227
+ return /* @__PURE__ */ React3.createElement(
979
1228
  "div",
980
1229
  {
981
1230
  className: cx("alt-skeleton", className),
@@ -989,13 +1238,13 @@ function Skeleton({ loaded, shape = "block", lines = 3, width, height, radius, c
989
1238
  var toneIcon = { neutral: Icons.Info, accent: Icons.Info, positive: Icons.CircleCheck, caution: Icons.AlertTriangle, critical: Icons.AlertCircle };
990
1239
  function Alert({ tone = "neutral", variant = "flat", title, action, icon: icon2, onDismiss, settle, className, style, children, ...rest }) {
991
1240
  const I = toneIcon[tone];
992
- const [closing, setClosing] = React2.useState(false);
1241
+ const [closing, setClosing] = React3.useState(false);
993
1242
  const { style: depthStyle, ...depth } = useDepth({ settle });
994
1243
  const dismiss = () => {
995
1244
  setClosing(true);
996
1245
  window.setTimeout(() => onDismiss?.(), 400);
997
1246
  };
998
- return /* @__PURE__ */ React2.createElement(
1247
+ return /* @__PURE__ */ React3.createElement(
999
1248
  "div",
1000
1249
  {
1001
1250
  role: tone === "critical" ? "alert" : "status",
@@ -1007,16 +1256,16 @@ function Alert({ tone = "neutral", variant = "flat", title, action, icon: icon2,
1007
1256
  style: { ...depthStyle, ...style },
1008
1257
  ...rest
1009
1258
  },
1010
- /* @__PURE__ */ React2.createElement("div", { className: "alt-alert-inner" }, /* @__PURE__ */ React2.createElement("span", { className: "alt-alert-icon", "aria-hidden": "true" }, icon2 ?? /* @__PURE__ */ React2.createElement(I, { size: 18 })), /* @__PURE__ */ React2.createElement("div", { className: "alt-alert-body" }, title && /* @__PURE__ */ React2.createElement("p", { className: "alt-alert-title" }, title), children && /* @__PURE__ */ React2.createElement("div", { className: "alt-alert-text" }, children)), action && /* @__PURE__ */ React2.createElement("div", { className: "alt-alert-action" }, action), onDismiss && /* @__PURE__ */ React2.createElement("button", { type: "button", className: "alt-alert-close", "aria-label": "Dismiss", onClick: dismiss }, /* @__PURE__ */ React2.createElement(Icons.X, { size: 14 })))
1259
+ /* @__PURE__ */ React3.createElement("div", { className: "alt-alert-inner" }, /* @__PURE__ */ React3.createElement("span", { className: "alt-alert-icon", "aria-hidden": "true" }, icon2 ?? /* @__PURE__ */ React3.createElement(I, { size: 18 })), /* @__PURE__ */ React3.createElement("div", { className: "alt-alert-body" }, title && /* @__PURE__ */ React3.createElement("p", { className: "alt-alert-title" }, title), children && /* @__PURE__ */ React3.createElement("div", { className: "alt-alert-text" }, children)), action && /* @__PURE__ */ React3.createElement("div", { className: "alt-alert-action" }, action), onDismiss && /* @__PURE__ */ React3.createElement("button", { type: "button", className: "alt-alert-close", "aria-label": "Dismiss", onClick: dismiss }, /* @__PURE__ */ React3.createElement(Icons.X, { size: 14 })))
1011
1260
  );
1012
1261
  }
1013
1262
  function AlertStack({ children, expanded, defaultExpanded = false, onExpandedChange, moreLabel = (n) => `+${n} more`, lessLabel = "Show less", className, ...rest }) {
1014
- const list = React2.Children.toArray(children).filter(React2.isValidElement);
1263
+ const list = React3.Children.toArray(children).filter(React3.isValidElement);
1015
1264
  const [open, setOpen] = useControllable(expanded, defaultExpanded, onExpandedChange);
1016
1265
  const topKey = list[0]?.key;
1017
- const prevTop = React2.useRef(topKey);
1018
- const [risen, setRisen] = React2.useState(0);
1019
- React2.useEffect(() => {
1266
+ const prevTop = React3.useRef(topKey);
1267
+ const [risen, setRisen] = React3.useState(0);
1268
+ React3.useEffect(() => {
1020
1269
  if (prevTop.current !== topKey) {
1021
1270
  prevTop.current = topKey;
1022
1271
  if (topKey != null) setRisen((r) => r + 1);
@@ -1024,20 +1273,20 @@ function AlertStack({ children, expanded, defaultExpanded = false, onExpandedCha
1024
1273
  }, [topKey]);
1025
1274
  const hidden = list.length - 1;
1026
1275
  const all = open || hidden < 1;
1027
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-alert-stack", className), "data-expanded": all ? "" : void 0, "data-sheets": all ? void 0 : Math.min(hidden, 2), ...rest }, all ? list.map((el, i) => /* @__PURE__ */ React2.createElement("div", { key: el.key, className: "alt-alert-stack-item", style: { ["--i"]: i } }, el)) : /* @__PURE__ */ React2.createElement(React2.Fragment, null, list.slice(1, 3).map((el, i) => /* @__PURE__ */ React2.createElement("span", { key: el.key, className: "alt-alert-sheet", "aria-hidden": "true", "data-tone": el.props.tone ?? "neutral", style: { ["--i"]: i + 1 } })), /* @__PURE__ */ React2.createElement("div", { key: String(topKey) + risen, className: "alt-alert-stack-top", "data-risen": risen ? "" : void 0 }, list[0])), hidden > 0 && /* @__PURE__ */ React2.createElement("button", { type: "button", className: "alt-alert-more", "aria-expanded": all, onClick: () => setOpen(!open) }, all ? lessLabel : moreLabel(hidden)));
1276
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-alert-stack", className), "data-expanded": all ? "" : void 0, "data-sheets": all ? void 0 : Math.min(hidden, 2), ...rest }, all ? list.map((el, i) => /* @__PURE__ */ React3.createElement("div", { key: el.key, className: "alt-alert-stack-item", style: { ["--i"]: i } }, el)) : /* @__PURE__ */ React3.createElement(React3.Fragment, null, list.slice(1, 3).map((el, i) => /* @__PURE__ */ React3.createElement("span", { key: el.key, className: "alt-alert-sheet", "aria-hidden": "true", "data-tone": el.props.tone ?? "neutral", style: { ["--i"]: i + 1 } })), /* @__PURE__ */ React3.createElement("div", { key: String(topKey) + risen, className: "alt-alert-stack-top", "data-risen": risen ? "" : void 0 }, list[0])), hidden > 0 && /* @__PURE__ */ React3.createElement("button", { type: "button", className: "alt-alert-more", "aria-expanded": all, onClick: () => setOpen(!open) }, all ? lessLabel : moreLabel(hidden)));
1028
1277
  }
1029
1278
  function Accordion({ items, type = "single", defaultValue = [], className, ...rest }) {
1030
- const [open, setOpen] = React2.useState(defaultValue);
1031
- const id = React2.useId();
1279
+ const [open, setOpen] = React3.useState(defaultValue);
1280
+ const id = React3.useId();
1032
1281
  const toggle = (v) => setOpen((o) => o.includes(v) ? o.filter((x) => x !== v) : type === "single" ? [v] : [...o, v]);
1033
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-acc", className), ...rest }, items.map((it) => {
1282
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-acc", className), ...rest }, items.map((it) => {
1034
1283
  const on = open.includes(it.value);
1035
- return /* @__PURE__ */ React2.createElement("div", { key: it.value, className: "alt-acc-item", "data-state": on ? "open" : "closed" }, /* @__PURE__ */ React2.createElement("h3", { className: "alt-acc-heading" }, /* @__PURE__ */ React2.createElement("button", { type: "button", className: "alt-acc-trigger", "aria-expanded": on, "aria-controls": `${id}-${it.value}`, onClick: () => toggle(it.value) }, /* @__PURE__ */ React2.createElement("span", null, it.title), /* @__PURE__ */ React2.createElement(Icons.ChevronDown, { className: "alt-acc-chevron", size: 18 }))), /* @__PURE__ */ React2.createElement("div", { className: "alt-acc-panel", id: `${id}-${it.value}`, role: "region", ...on ? {} : inert }, /* @__PURE__ */ React2.createElement("div", null, /* @__PURE__ */ React2.createElement("div", { className: "alt-acc-content" }, it.content))));
1284
+ return /* @__PURE__ */ React3.createElement("div", { key: it.value, className: "alt-acc-item", "data-state": on ? "open" : "closed" }, /* @__PURE__ */ React3.createElement("h3", { className: "alt-acc-heading" }, /* @__PURE__ */ React3.createElement("button", { type: "button", className: "alt-acc-trigger", "aria-expanded": on, "aria-controls": `${id}-${it.value}`, onClick: () => toggle(it.value) }, /* @__PURE__ */ React3.createElement("span", null, it.title), /* @__PURE__ */ React3.createElement(Icons.ChevronDown, { className: "alt-acc-chevron", size: 18 }))), /* @__PURE__ */ React3.createElement("div", { className: "alt-acc-panel", id: `${id}-${it.value}`, role: "region", ...on ? {} : inert }, /* @__PURE__ */ React3.createElement("div", null, /* @__PURE__ */ React3.createElement("div", { className: "alt-acc-content" }, it.content))));
1036
1285
  }));
1037
1286
  }
1038
1287
  function HoldButton({ onConfirm, duration = 1e3, variant = "danger", holdingLabel, doneLabel, repeatable = false, className, children, style, disabled, onClick, ...rest }) {
1039
- const [state, setState] = React2.useState("idle");
1040
- const timer = React2.useRef(void 0);
1288
+ const [state, setState] = React3.useState("idle");
1289
+ const timer = React3.useRef(void 0);
1041
1290
  const done = state === "done";
1042
1291
  const start = () => {
1043
1292
  if (disabled || state !== "idle") return;
@@ -1054,9 +1303,9 @@ function HoldButton({ onConfirm, duration = 1e3, variant = "danger", holdingLabe
1054
1303
  window.clearTimeout(timer.current);
1055
1304
  setState("idle");
1056
1305
  };
1057
- React2.useEffect(() => () => window.clearTimeout(timer.current), []);
1306
+ React3.useEffect(() => () => window.clearTimeout(timer.current), []);
1058
1307
  const label = done ? doneLabel ?? children : state === "holding" ? holdingLabel ?? children : children;
1059
- return /* @__PURE__ */ React2.createElement(
1308
+ return /* @__PURE__ */ React3.createElement(
1060
1309
  Button,
1061
1310
  {
1062
1311
  ...rest,
@@ -1091,16 +1340,16 @@ function HoldButton({ onConfirm, duration = 1e3, variant = "danger", holdingLabe
1091
1340
  },
1092
1341
  onContextMenu: (e) => e.preventDefault()
1093
1342
  },
1094
- /* @__PURE__ */ React2.createElement("span", { className: "alt-hold-fill", "aria-hidden": "true" }),
1095
- /* @__PURE__ */ React2.createElement("span", { className: "alt-hold-text" }, label),
1096
- /* @__PURE__ */ React2.createElement("span", { className: "alt-sr", "aria-live": "polite" }, state === "holding" ? "Keep holding to confirm" : done ? "Confirmed" : "")
1343
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-hold-fill", "aria-hidden": "true" }),
1344
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-hold-text" }, label),
1345
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-sr", "aria-live": "polite" }, state === "holding" ? "Keep holding to confirm" : done ? "Confirmed" : "")
1097
1346
  );
1098
1347
  }
1099
1348
  function ScrollArea({ header, maxHeight = 280, className, children, ...rest }) {
1100
- const body = React2.useRef(null);
1101
- const inner = React2.useRef(null);
1102
- const [edges, setEdges] = React2.useState({ top: false, bottom: false });
1103
- const update = React2.useCallback(() => {
1349
+ const body = React3.useRef(null);
1350
+ const inner = React3.useRef(null);
1351
+ const [edges, setEdges] = React3.useState({ top: false, bottom: false });
1352
+ const update = React3.useCallback(() => {
1104
1353
  const el = body.current;
1105
1354
  if (!el) return;
1106
1355
  const top = el.scrollTop > 1, bottom = el.scrollTop + el.clientHeight < el.scrollHeight - 1;
@@ -1113,15 +1362,15 @@ function ScrollArea({ header, maxHeight = 280, className, children, ...rest }) {
1113
1362
  if (inner.current) ro.observe(inner.current);
1114
1363
  return () => ro.disconnect();
1115
1364
  }, [update]);
1116
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-scroll", className), "data-top": edges.top ? "" : void 0, "data-bottom": edges.bottom ? "" : void 0, ...rest }, header && /* @__PURE__ */ React2.createElement("div", { className: "alt-scroll-header" }, header), /* @__PURE__ */ React2.createElement("div", { className: "alt-scroll-body", ref: body, onScroll: update, style: { maxHeight }, tabIndex: 0, "aria-label": rest["aria-label"] }, /* @__PURE__ */ React2.createElement("div", { ref: inner }, children)), /* @__PURE__ */ React2.createElement("span", { className: "alt-scroll-lip", "data-edge": "top", "aria-hidden": "true" }), /* @__PURE__ */ React2.createElement("span", { className: "alt-scroll-lip", "data-edge": "bottom", "aria-hidden": "true" }));
1365
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-scroll", className), "data-top": edges.top ? "" : void 0, "data-bottom": edges.bottom ? "" : void 0, ...rest }, header && /* @__PURE__ */ React3.createElement("div", { className: "alt-scroll-header" }, header), /* @__PURE__ */ React3.createElement("div", { className: "alt-scroll-body", ref: body, onScroll: update, style: { maxHeight }, tabIndex: 0, "aria-label": rest["aria-label"] }, /* @__PURE__ */ React3.createElement("div", { ref: inner }, children)), /* @__PURE__ */ React3.createElement("span", { className: "alt-scroll-lip", "data-edge": "top", "aria-hidden": "true" }), /* @__PURE__ */ React3.createElement("span", { className: "alt-scroll-lip", "data-edge": "bottom", "aria-hidden": "true" }));
1117
1366
  }
1118
1367
  function DropZone({ onFiles, accept, multiple = true, state, className, children, ...rest }) {
1119
- const [armed, setArmed] = React2.useState(false);
1120
- const [over, setOver] = React2.useState(false);
1121
- const [landed, setLanded] = React2.useState(0);
1122
- const input = React2.useRef(null);
1368
+ const [armed, setArmed] = React3.useState(false);
1369
+ const [over, setOver] = React3.useState(false);
1370
+ const [landed, setLanded] = React3.useState(0);
1371
+ const input = React3.useRef(null);
1123
1372
  const { style: depthStyle, ...depth } = useDepth({ settle: landed || void 0 });
1124
- React2.useEffect(() => {
1373
+ React3.useEffect(() => {
1125
1374
  let n = 0;
1126
1375
  const hasFiles = (e) => Array.from(e.dataTransfer?.types || []).includes("Files");
1127
1376
  const enter = (e) => {
@@ -1159,7 +1408,7 @@ function DropZone({ onFiles, accept, multiple = true, state, className, children
1159
1408
  setLanded((x) => x + 1);
1160
1409
  };
1161
1410
  const visual = state ?? (over ? "over" : armed ? "armed" : "idle");
1162
- return /* @__PURE__ */ React2.createElement(
1411
+ return /* @__PURE__ */ React3.createElement(
1163
1412
  "div",
1164
1413
  {
1165
1414
  className: cx("alt-drop", className),
@@ -1188,7 +1437,7 @@ function DropZone({ onFiles, accept, multiple = true, state, className, children
1188
1437
  },
1189
1438
  ...rest
1190
1439
  },
1191
- /* @__PURE__ */ React2.createElement("input", { ref: input, type: "file", hidden: true, accept, multiple, onChange: (e) => take(Array.from(e.target.files || [])) }),
1440
+ /* @__PURE__ */ React3.createElement("input", { ref: input, type: "file", hidden: true, accept, multiple, onChange: (e) => take(Array.from(e.target.files || [])) }),
1192
1441
  children
1193
1442
  );
1194
1443
  }
@@ -1199,12 +1448,12 @@ var move = (arr, from, to) => {
1199
1448
  return a;
1200
1449
  };
1201
1450
  function SortableList({ items, getKey, onReorder, renderItem, getLabel = (i) => String(getKey(i)), gap = 8, className, ...rest }) {
1202
- const nodes = React2.useRef(/* @__PURE__ */ new Map());
1203
- const before = React2.useRef(/* @__PURE__ */ new Map());
1204
- const start = React2.useRef(null);
1205
- const [drag, setDrag] = React2.useState(null);
1206
- const [kb, setKb] = React2.useState(null);
1207
- const [msg, setMsg] = React2.useState("");
1451
+ const nodes = React3.useRef(/* @__PURE__ */ new Map());
1452
+ const before = React3.useRef(/* @__PURE__ */ new Map());
1453
+ const start = React3.useRef(null);
1454
+ const [drag, setDrag] = React3.useState(null);
1455
+ const [kb, setKb] = React3.useState(null);
1456
+ const [msg, setMsg] = React3.useState("");
1208
1457
  const snapshot = () => {
1209
1458
  before.current.clear();
1210
1459
  nodes.current.forEach((el, k) => before.current.set(k, el.getBoundingClientRect().top));
@@ -1283,7 +1532,7 @@ function SortableList({ items, getKey, onReorder, renderItem, getLabel = (i) =>
1283
1532
  const s = start.current;
1284
1533
  const h = drag && s ? s.hs[drag.from] + gap : 0;
1285
1534
  const slotTop = drag && s ? drag.to <= drag.from ? s.tops[drag.to] : s.tops[drag.to] + s.hs[drag.to] - s.hs[drag.from] : 0;
1286
- return /* @__PURE__ */ React2.createElement("div", { className: cx("alt-sort", className), style: { gap }, role: "list", "aria-label": rest["aria-label"], "data-dragging": drag ? "" : void 0 }, drag && s && /* @__PURE__ */ React2.createElement("div", { className: "alt-sort-slot", "aria-hidden": "true", style: { top: slotTop, height: s.hs[drag.from] } }), items.map((item, i) => {
1535
+ return /* @__PURE__ */ React3.createElement("div", { className: cx("alt-sort", className), style: { gap }, role: "list", "aria-label": rest["aria-label"], "data-dragging": drag ? "" : void 0 }, drag && s && /* @__PURE__ */ React3.createElement("div", { className: "alt-sort-slot", "aria-hidden": "true", style: { top: slotTop, height: s.hs[drag.from] } }), items.map((item, i) => {
1287
1536
  const key = keys[i];
1288
1537
  const held = drag?.key === key || kb === key;
1289
1538
  let shift = 0;
@@ -1292,7 +1541,7 @@ function SortableList({ items, getKey, onReorder, renderItem, getLabel = (i) =>
1292
1541
  if (drag.to < drag.from && i >= drag.to && i < drag.from) shift = h;
1293
1542
  }
1294
1543
  const transform = drag?.key === key ? `translateY(${drag.dy}px)` : shift ? `translateY(${shift}px)` : void 0;
1295
- return /* @__PURE__ */ React2.createElement(
1544
+ return /* @__PURE__ */ React3.createElement(
1296
1545
  "div",
1297
1546
  {
1298
1547
  key,
@@ -1314,14 +1563,14 @@ function SortableList({ items, getKey, onReorder, renderItem, getLabel = (i) =>
1314
1563
  onPointerCancel: onPointerUp,
1315
1564
  onKeyDown: (e) => onKeyDown(e, key, i)
1316
1565
  },
1317
- /* @__PURE__ */ React2.createElement("span", { className: "alt-sort-grip", "aria-hidden": "true" }, /* @__PURE__ */ React2.createElement("svg", { width: "12", height: "16", viewBox: "0 0 12 16", fill: "currentColor" }, /* @__PURE__ */ React2.createElement("circle", { cx: "3", cy: "3", r: "1.3" }), /* @__PURE__ */ React2.createElement("circle", { cx: "9", cy: "3", r: "1.3" }), /* @__PURE__ */ React2.createElement("circle", { cx: "3", cy: "8", r: "1.3" }), /* @__PURE__ */ React2.createElement("circle", { cx: "9", cy: "8", r: "1.3" }), /* @__PURE__ */ React2.createElement("circle", { cx: "3", cy: "13", r: "1.3" }), /* @__PURE__ */ React2.createElement("circle", { cx: "9", cy: "13", r: "1.3" }))),
1318
- /* @__PURE__ */ React2.createElement("div", { className: "alt-sort-body" }, renderItem(item, { held }))
1566
+ /* @__PURE__ */ React3.createElement("span", { className: "alt-sort-grip", "aria-hidden": "true" }, /* @__PURE__ */ React3.createElement("svg", { width: "12", height: "16", viewBox: "0 0 12 16", fill: "currentColor" }, /* @__PURE__ */ React3.createElement("circle", { cx: "3", cy: "3", r: "1.3" }), /* @__PURE__ */ React3.createElement("circle", { cx: "9", cy: "3", r: "1.3" }), /* @__PURE__ */ React3.createElement("circle", { cx: "3", cy: "8", r: "1.3" }), /* @__PURE__ */ React3.createElement("circle", { cx: "9", cy: "8", r: "1.3" }), /* @__PURE__ */ React3.createElement("circle", { cx: "3", cy: "13", r: "1.3" }), /* @__PURE__ */ React3.createElement("circle", { cx: "9", cy: "13", r: "1.3" }))),
1567
+ /* @__PURE__ */ React3.createElement("div", { className: "alt-sort-body" }, renderItem(item, { held }))
1319
1568
  );
1320
- }), /* @__PURE__ */ React2.createElement("span", { className: "alt-sr", "aria-live": "assertive" }, msg));
1569
+ }), /* @__PURE__ */ React3.createElement("span", { className: "alt-sr", "aria-live": "assertive" }, msg));
1321
1570
  }
1322
1571
 
1323
1572
  // project/components/src/pile.tsx
1324
- var React3 = __toESM(require("react"), 1);
1573
+ var React4 = __toESM(require("react"), 1);
1325
1574
  function Pile({
1326
1575
  count,
1327
1576
  interactive,
@@ -1343,15 +1592,15 @@ function Pile({
1343
1592
  const live = interactive || openable;
1344
1593
  const [isOpen, setOpen] = useControllable(open, defaultOpen, onOpenChange);
1345
1594
  const { mounted, state } = usePresence(openable && isOpen, 260);
1346
- const root = React3.useRef(null);
1347
- const top = React3.useRef(null);
1348
- const id = React3.useId();
1595
+ const root = React4.useRef(null);
1596
+ const top = React4.useRef(null);
1597
+ const id = React4.useId();
1349
1598
  const toggle = () => {
1350
1599
  if (openable) setOpen(!isOpen);
1351
1600
  };
1352
- const close = React3.useCallback(() => setOpen(false), [setOpen]);
1601
+ const close = React4.useCallback(() => setOpen(false), [setOpen]);
1353
1602
  useOutside(root, openable && isOpen, close);
1354
- return /* @__PURE__ */ React3.createElement(
1603
+ return /* @__PURE__ */ React4.createElement(
1355
1604
  "div",
1356
1605
  {
1357
1606
  ref: root,
@@ -1360,8 +1609,8 @@ function Pile({
1360
1609
  "data-open": openable && isOpen ? "" : void 0,
1361
1610
  ...rest
1362
1611
  },
1363
- Array.from({ length: sheets }, (_, i) => /* @__PURE__ */ React3.createElement("span", { key: i, className: "alt-pile-sheet", "aria-hidden": "true", style: { ["--i"]: i + 1 } })),
1364
- /* @__PURE__ */ React3.createElement(
1612
+ Array.from({ length: sheets }, (_, i) => /* @__PURE__ */ React4.createElement("span", { key: i, className: "alt-pile-sheet", "aria-hidden": "true", style: { ["--i"]: i + 1 } })),
1613
+ /* @__PURE__ */ React4.createElement(
1365
1614
  "div",
1366
1615
  {
1367
1616
  ref: top,
@@ -1380,8 +1629,8 @@ function Pile({
1380
1629
  },
1381
1630
  children
1382
1631
  ),
1383
- n > 1 && /* @__PURE__ */ React3.createElement("span", { className: "alt-pile-count", "aria-label": `${n} items` }, n),
1384
- openable && mounted && /* @__PURE__ */ React3.createElement(
1632
+ n > 1 && /* @__PURE__ */ React4.createElement("span", { className: "alt-pile-count", "aria-label": `${n} items` }, n),
1633
+ openable && mounted && /* @__PURE__ */ React4.createElement(
1385
1634
  "div",
1386
1635
  {
1387
1636
  className: "alt-pile-list",
@@ -1395,23 +1644,23 @@ function Pile({
1395
1644
  }
1396
1645
  }
1397
1646
  },
1398
- /* @__PURE__ */ React3.createElement("ul", { className: "alt-pile-list-inner", style: { maxHeight } }, items.map((it, i) => /* @__PURE__ */ React3.createElement("li", { key: getKey ? getKey(it, i) : i }, /* @__PURE__ */ React3.createElement("button", { type: "button", className: "alt-pile-item", style: { ["--i"]: Math.min(i, 10) }, onClick: () => onSelect?.(it, i) }, renderItem(it, { index: i })))))
1647
+ /* @__PURE__ */ React4.createElement("ul", { className: "alt-pile-list-inner", style: { maxHeight } }, items.map((it, i) => /* @__PURE__ */ React4.createElement("li", { key: getKey ? getKey(it, i) : i }, /* @__PURE__ */ React4.createElement("button", { type: "button", className: "alt-pile-item", style: { ["--i"]: Math.min(i, 10) }, onClick: () => onSelect?.(it, i) }, renderItem(it, { index: i })))))
1399
1648
  )
1400
1649
  );
1401
1650
  }
1402
1651
 
1403
1652
  // project/components/src/overlays.tsx
1404
- var React4 = __toESM(require("react"), 1);
1653
+ var React5 = __toESM(require("react"), 1);
1405
1654
  var EXIT_3 = 160;
1406
1655
  var EXIT_4 = 190;
1407
1656
  var EXIT_5 = 220;
1408
1657
  var lastTipClose = 0;
1409
1658
  var openCard = null;
1410
1659
  function Tooltip({ content, side = "top", delay = 450, defaultOpen = false, children }) {
1411
- const [open, setOpen] = React4.useState(defaultOpen);
1412
- const [warm, setWarm] = React4.useState(false);
1413
- const timer = React4.useRef(void 0);
1414
- const id = React4.useId();
1660
+ const [open, setOpen] = React5.useState(defaultOpen);
1661
+ const [warm, setWarm] = React5.useState(false);
1662
+ const timer = React5.useRef(void 0);
1663
+ const id = React5.useId();
1415
1664
  const { mounted, state } = usePresence(open, EXIT_3);
1416
1665
  const show = () => {
1417
1666
  const isWarm = Date.now() - lastTipClose < 400;
@@ -1426,8 +1675,8 @@ function Tooltip({ content, side = "top", delay = 450, defaultOpen = false, chil
1426
1675
  return false;
1427
1676
  });
1428
1677
  };
1429
- React4.useEffect(() => () => window.clearTimeout(timer.current), []);
1430
- return /* @__PURE__ */ React4.createElement(
1678
+ React5.useEffect(() => () => window.clearTimeout(timer.current), []);
1679
+ return /* @__PURE__ */ React5.createElement(
1431
1680
  "span",
1432
1681
  {
1433
1682
  className: "alt-tip-anchor",
@@ -1443,27 +1692,27 @@ function Tooltip({ content, side = "top", delay = 450, defaultOpen = false, chil
1443
1692
  if (e.key === "Escape") hide();
1444
1693
  }
1445
1694
  },
1446
- React4.cloneElement(children, { "aria-describedby": open ? id : void 0 }),
1447
- mounted && /* @__PURE__ */ React4.createElement("span", { role: "tooltip", id, className: "alt-tip", "data-side": side, "data-state": state, "data-warm": warm ? "" : void 0 }, content)
1695
+ React5.cloneElement(children, { "aria-describedby": open ? id : void 0 }),
1696
+ mounted && /* @__PURE__ */ React5.createElement("span", { role: "tooltip", id, className: "alt-tip", "data-side": side, "data-state": state, "data-warm": warm ? "" : void 0 }, content)
1448
1697
  );
1449
1698
  }
1450
1699
  function Popover({ trigger, children, open, defaultOpen = false, onOpenChange, side = "bottom", align = "start", className, ...rest }) {
1451
1700
  const [isOpen, set] = useControllable(open, defaultOpen, onOpenChange);
1452
- const ref = React4.useRef(null);
1453
- const panel = React4.useRef(null);
1454
- const id = React4.useId();
1701
+ const ref = React5.useRef(null);
1702
+ const panel = React5.useRef(null);
1703
+ const id = React5.useId();
1455
1704
  const { mounted, state } = usePresence(isOpen, EXIT_3);
1456
- const close = React4.useCallback(() => set(false), [set]);
1705
+ const close = React5.useCallback(() => set(false), [set]);
1457
1706
  useOutside(ref, isOpen, close);
1458
- React4.useEffect(() => {
1707
+ React5.useEffect(() => {
1459
1708
  if (state !== "open" || !panel.current) return;
1460
1709
  const f = panel.current.querySelector('input, textarea, select, button, [href], [tabindex]:not([tabindex="-1"])');
1461
1710
  (f || panel.current).focus({ preventScroll: true });
1462
1711
  }, [state]);
1463
- return /* @__PURE__ */ React4.createElement("span", { className: "alt-pop-anchor", ref }, React4.cloneElement(trigger, { "aria-expanded": isOpen, "aria-controls": id, "aria-haspopup": "dialog", onClick: (e) => {
1712
+ return /* @__PURE__ */ React5.createElement("span", { className: "alt-pop-anchor", ref }, React5.cloneElement(trigger, { "aria-expanded": isOpen, "aria-controls": id, "aria-haspopup": "dialog", onClick: (e) => {
1464
1713
  trigger.props.onClick?.(e);
1465
1714
  set(!isOpen);
1466
- } }), mounted && /* @__PURE__ */ React4.createElement(
1715
+ } }), mounted && /* @__PURE__ */ React5.createElement(
1467
1716
  "div",
1468
1717
  {
1469
1718
  ref: panel,
@@ -1487,15 +1736,15 @@ function Popover({ trigger, children, open, defaultOpen = false, onOpenChange, s
1487
1736
  ));
1488
1737
  }
1489
1738
  function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaultOpen = false, className }) {
1490
- const [open, setOpen] = React4.useState(defaultOpen);
1491
- const [active, setActive] = React4.useState(-1);
1492
- const [hl, setHl] = React4.useState(null);
1493
- const anchor = React4.useRef(null);
1494
- const menu = React4.useRef(null);
1495
- const refs = React4.useRef([]);
1496
- const id = React4.useId();
1739
+ const [open, setOpen] = React5.useState(defaultOpen);
1740
+ const [active, setActive] = React5.useState(-1);
1741
+ const [hl, setHl] = React5.useState(null);
1742
+ const anchor = React5.useRef(null);
1743
+ const menu = React5.useRef(null);
1744
+ const refs = React5.useRef([]);
1745
+ const id = React5.useId();
1497
1746
  const { mounted, state } = usePresence(open, EXIT_3);
1498
- const close = React4.useCallback(() => {
1747
+ const close = React5.useCallback(() => {
1499
1748
  setOpen(false);
1500
1749
  setActive(-1);
1501
1750
  }, []);
@@ -1505,7 +1754,7 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1505
1754
  const el = active >= 0 ? refs.current[active] : null;
1506
1755
  setHl(el ? { y: el.offsetTop, h: el.offsetHeight } : null);
1507
1756
  }, [active, mounted]);
1508
- React4.useEffect(() => {
1757
+ React5.useEffect(() => {
1509
1758
  if (state === "open") menu.current?.focus({ preventScroll: true });
1510
1759
  }, [state]);
1511
1760
  const choose = (i) => {
@@ -1539,7 +1788,7 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1539
1788
  };
1540
1789
  let n = 0;
1541
1790
  const activeTone = active >= 0 ? items[active].tone : void 0;
1542
- return /* @__PURE__ */ React4.createElement("span", { className: "alt-pop-anchor", ref: anchor }, React4.cloneElement(trigger, {
1791
+ return /* @__PURE__ */ React5.createElement("span", { className: "alt-pop-anchor", ref: anchor }, React5.cloneElement(trigger, {
1543
1792
  "aria-haspopup": "menu",
1544
1793
  "aria-expanded": open,
1545
1794
  "aria-controls": id,
@@ -1554,7 +1803,7 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1554
1803
  setActive(enabled[0]);
1555
1804
  }
1556
1805
  }
1557
- }), mounted && /* @__PURE__ */ React4.createElement(
1806
+ }), mounted && /* @__PURE__ */ React5.createElement(
1558
1807
  "div",
1559
1808
  {
1560
1809
  ref: menu,
@@ -1570,7 +1819,7 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1570
1819
  onKeyDown,
1571
1820
  onPointerLeave: () => setActive(-1)
1572
1821
  },
1573
- /* @__PURE__ */ React4.createElement(
1822
+ /* @__PURE__ */ React5.createElement(
1574
1823
  "span",
1575
1824
  {
1576
1825
  className: "alt-menu-hl",
@@ -1580,10 +1829,10 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1580
1829
  }
1581
1830
  ),
1582
1831
  items.map((it, i) => {
1583
- if (it.type === "separator") return /* @__PURE__ */ React4.createElement("div", { key: i, className: "alt-menu-sep", role: "separator" });
1584
- if (it.type === "label") return /* @__PURE__ */ React4.createElement("div", { key: i, className: "alt-menu-label", style: { ["--i"]: n++ } }, it.label);
1832
+ if (it.type === "separator") return /* @__PURE__ */ React5.createElement("div", { key: i, className: "alt-menu-sep", role: "separator" });
1833
+ if (it.type === "label") return /* @__PURE__ */ React5.createElement("div", { key: i, className: "alt-menu-label", style: { ["--i"]: n++ } }, it.label);
1585
1834
  const item = it;
1586
- return /* @__PURE__ */ React4.createElement(
1835
+ return /* @__PURE__ */ React5.createElement(
1587
1836
  "div",
1588
1837
  {
1589
1838
  key: i,
@@ -1600,9 +1849,9 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1600
1849
  onPointerMove: () => !item.disabled && active !== i && setActive(i),
1601
1850
  onClick: () => choose(i)
1602
1851
  },
1603
- item.icon && /* @__PURE__ */ React4.createElement("span", { className: "alt-menu-icon" }, item.icon),
1604
- /* @__PURE__ */ React4.createElement("span", { className: "alt-menu-text" }, item.label),
1605
- item.shortcut && /* @__PURE__ */ React4.createElement("span", { className: "alt-menu-shortcut" }, item.shortcut)
1852
+ item.icon && /* @__PURE__ */ React5.createElement("span", { className: "alt-menu-icon" }, item.icon),
1853
+ /* @__PURE__ */ React5.createElement("span", { className: "alt-menu-text" }, item.label),
1854
+ item.shortcut && /* @__PURE__ */ React5.createElement("span", { className: "alt-menu-shortcut" }, item.shortcut)
1606
1855
  );
1607
1856
  })
1608
1857
  ));
@@ -1610,10 +1859,10 @@ function DropdownMenu({ trigger, items, align = "start", side = "bottom", defaul
1610
1859
  function HoverCard({ trigger, children, side = "bottom", align = "start", openDelay = 400, closeDelay = 250, open, defaultOpen = false, onOpenChange, className }) {
1611
1860
  const [isOpen, set] = useControllable(open, defaultOpen, onOpenChange);
1612
1861
  const { mounted, state } = usePresence(isOpen, EXIT_3);
1613
- const timer = React4.useRef(void 0);
1614
- const closeMe = React4.useRef(() => set(false));
1862
+ const timer = React5.useRef(void 0);
1863
+ const closeMe = React5.useRef(() => set(false));
1615
1864
  closeMe.current = () => set(false);
1616
- React4.useEffect(() => {
1865
+ React5.useEffect(() => {
1617
1866
  if (!isOpen) return;
1618
1867
  const mine = () => closeMe.current();
1619
1868
  if (openCard && openCard !== mine) {
@@ -1637,8 +1886,8 @@ function HoverCard({ trigger, children, side = "bottom", align = "start", openDe
1637
1886
  if (isOpen) lastTipClose = Date.now();
1638
1887
  }, delay);
1639
1888
  };
1640
- React4.useEffect(() => () => window.clearTimeout(timer.current), []);
1641
- return /* @__PURE__ */ React4.createElement(
1889
+ React5.useEffect(() => () => window.clearTimeout(timer.current), []);
1890
+ return /* @__PURE__ */ React5.createElement(
1642
1891
  "span",
1643
1892
  {
1644
1893
  className: "alt-pop-anchor alt-hovercard-anchor",
@@ -1662,7 +1911,7 @@ function HoverCard({ trigger, children, side = "bottom", align = "start", openDe
1662
1911
  }
1663
1912
  },
1664
1913
  trigger,
1665
- mounted && /* @__PURE__ */ React4.createElement(
1914
+ mounted && /* @__PURE__ */ React5.createElement(
1666
1915
  "div",
1667
1916
  {
1668
1917
  className: cx("alt-pop alt-hovercard", className),
@@ -1677,6 +1926,7 @@ function HoverCard({ trigger, children, side = "bottom", align = "start", openDe
1677
1926
  }
1678
1927
  var summits = 0;
1679
1928
  var summitTaken = () => summits > 0;
1929
+ var MODAL_FOCUS = "[data-autofocus], input, textarea, select";
1680
1930
  function useModal({
1681
1931
  open,
1682
1932
  onDismiss,
@@ -1686,12 +1936,13 @@ function useModal({
1686
1936
  dismissible = true,
1687
1937
  summit = false,
1688
1938
  autoFocus = true,
1689
- focusSelector = "[data-autofocus], input, textarea, select"
1939
+ focusSelector = MODAL_FOCUS,
1940
+ restoreFocus = autoFocus
1690
1941
  }) {
1691
1942
  const ctx = useAltitude();
1692
- const restore = React4.useRef(null);
1943
+ const restore = React5.useRef(null);
1693
1944
  const presence = usePresence(open, exitMs);
1694
- React4.useEffect(() => {
1945
+ React5.useEffect(() => {
1695
1946
  if (!open) return;
1696
1947
  restore.current = document.activeElement;
1697
1948
  const pop = modal ? ctx?.pushLayer() : void 0;
@@ -1702,10 +1953,10 @@ function useModal({
1702
1953
  pop?.();
1703
1954
  if (modal) document.body.style.overflow = prev;
1704
1955
  if (summit) summits--;
1705
- if (autoFocus) restore.current?.focus?.({ preventScroll: true });
1956
+ if (restoreFocus) restore.current?.focus?.({ preventScroll: true });
1706
1957
  };
1707
1958
  }, [open]);
1708
- React4.useEffect(() => {
1959
+ React5.useEffect(() => {
1709
1960
  if (presence.state !== "open" || !autoFocus) return;
1710
1961
  let raf = 0;
1711
1962
  const tryFocus = () => {
@@ -1738,15 +1989,39 @@ function useModal({
1738
1989
  };
1739
1990
  return { ...presence, onKeyDown };
1740
1991
  }
1741
- function Dialog({ open, defaultOpen = false, onOpenChange, trigger, title, description, children, footer, size = "md", dismissible = true, className }) {
1992
+ function Dialog({
1993
+ open,
1994
+ defaultOpen = false,
1995
+ onOpenChange,
1996
+ trigger,
1997
+ title,
1998
+ description,
1999
+ children,
2000
+ footer,
2001
+ size = "md",
2002
+ dismissible = true,
2003
+ initialFocus = "first-field",
2004
+ focusSelector = MODAL_FOCUS,
2005
+ className
2006
+ }) {
1742
2007
  const [isOpen, set] = useControllable(open, defaultOpen, onOpenChange);
1743
- const panel = React4.useRef(null);
1744
- const id = React4.useId();
1745
- const { mounted, state, onKeyDown } = useModal({ open: isOpen, onDismiss: () => set(false), exitMs: EXIT_5, panel, dismissible, summit: true });
1746
- return /* @__PURE__ */ React4.createElement(React4.Fragment, null, trigger && React4.cloneElement(trigger, { "aria-haspopup": "dialog", onClick: (e) => {
2008
+ const panel = React5.useRef(null);
2009
+ const id = React5.useId();
2010
+ const { mounted, state, onKeyDown } = useModal({
2011
+ open: isOpen,
2012
+ onDismiss: () => set(false),
2013
+ exitMs: EXIT_5,
2014
+ panel,
2015
+ dismissible,
2016
+ summit: true,
2017
+ autoFocus: initialFocus !== false,
2018
+ focusSelector: initialFocus === "title" ? ".alt-dialog-title" : focusSelector,
2019
+ restoreFocus: true
2020
+ });
2021
+ return /* @__PURE__ */ React5.createElement(React5.Fragment, null, trigger && React5.cloneElement(trigger, { "aria-haspopup": "dialog", onClick: (e) => {
1747
2022
  trigger.props.onClick?.(e);
1748
2023
  set(true);
1749
- } }), mounted && /* @__PURE__ */ React4.createElement(Layer, null, /* @__PURE__ */ React4.createElement("div", { className: "alt-dialog-root", "data-state": state, onKeyDown }, /* @__PURE__ */ React4.createElement("div", { className: "alt-scrim", onClick: () => dismissible && set(false) }), /* @__PURE__ */ React4.createElement(
2024
+ } }), mounted && /* @__PURE__ */ React5.createElement(Layer, null, /* @__PURE__ */ React5.createElement("div", { className: "alt-dialog-root", "data-state": state, onKeyDown }, /* @__PURE__ */ React5.createElement("div", { className: "alt-scrim", onClick: () => dismissible && set(false) }), /* @__PURE__ */ React5.createElement(
1750
2025
  "div",
1751
2026
  {
1752
2027
  ref: panel,
@@ -1758,10 +2033,10 @@ function Dialog({ open, defaultOpen = false, onOpenChange, trigger, title, descr
1758
2033
  className: cx("alt-dialog", className),
1759
2034
  "data-size": size
1760
2035
  },
1761
- /* @__PURE__ */ React4.createElement("div", { className: "alt-dialog-head" }, /* @__PURE__ */ React4.createElement("h2", { className: "alt-dialog-title", id: `${id}-t` }, title), description && /* @__PURE__ */ React4.createElement("p", { className: "alt-dialog-desc", id: `${id}-d` }, description)),
1762
- children && /* @__PURE__ */ React4.createElement("div", { className: "alt-dialog-body" }, children),
1763
- footer && /* @__PURE__ */ React4.createElement("div", { className: "alt-dialog-footer" }, footer),
1764
- dismissible && /* @__PURE__ */ React4.createElement(Button, { variant: "ghost", size: "sm", square: true, "aria-label": "Close", className: "alt-dialog-close", onClick: () => set(false) }, /* @__PURE__ */ React4.createElement(Icons.X, null))
2036
+ /* @__PURE__ */ React5.createElement("div", { className: "alt-dialog-head" }, /* @__PURE__ */ React5.createElement("h2", { className: "alt-dialog-title", id: `${id}-t`, tabIndex: initialFocus === "title" ? -1 : void 0 }, title), description && /* @__PURE__ */ React5.createElement("p", { className: "alt-dialog-desc", id: `${id}-d` }, description)),
2037
+ children && /* @__PURE__ */ React5.createElement("div", { className: "alt-dialog-body" }, children),
2038
+ footer && /* @__PURE__ */ React5.createElement("div", { className: "alt-dialog-footer" }, footer),
2039
+ dismissible && /* @__PURE__ */ React5.createElement(Button, { variant: "ghost", size: "sm", square: true, "aria-label": "Close", className: "alt-dialog-close", onClick: () => set(false) }, /* @__PURE__ */ React5.createElement(Icons.X, null))
1765
2040
  ))));
1766
2041
  }
1767
2042
  var toasts = [];
@@ -1791,16 +2066,16 @@ var toastIcon = { neutral: Icons.Info, positive: Icons.CircleCheck, caution: Ico
1791
2066
  var STACK = 3;
1792
2067
  var GAP = 8;
1793
2068
  function Toaster({ className }) {
1794
- const [, force] = React4.useReducer((n) => n + 1, 0);
1795
- const [expanded, setExpanded] = React4.useState(false);
1796
- const heights = React4.useRef(/* @__PURE__ */ new Map());
1797
- React4.useEffect(() => {
2069
+ const [, force] = React5.useReducer((n) => n + 1, 0);
2070
+ const [expanded, setExpanded] = React5.useState(false);
2071
+ const heights = React5.useRef(/* @__PURE__ */ new Map());
2072
+ React5.useEffect(() => {
1798
2073
  subs.add(force);
1799
2074
  return () => {
1800
2075
  subs.delete(force);
1801
2076
  };
1802
2077
  }, []);
1803
- React4.useEffect(() => {
2078
+ React5.useEffect(() => {
1804
2079
  if (expanded) return;
1805
2080
  const timers = toasts.filter((t) => !t.leaving && t.duration > 0).map((t) => setTimeout(() => toast.dismiss(t.id), t.duration));
1806
2081
  return () => timers.forEach(clearTimeout);
@@ -1809,7 +2084,7 @@ function Toaster({ className }) {
1809
2084
  const frontH = live[0] ? heights.current.get(live[0].id) || 64 : 64;
1810
2085
  let offset = 0;
1811
2086
  const total = live.slice(0, 5).reduce((a, t) => a + (heights.current.get(t.id) || 64) + GAP, 0);
1812
- return /* @__PURE__ */ React4.createElement(Layer, null, /* @__PURE__ */ React4.createElement(
2087
+ return /* @__PURE__ */ React5.createElement(Layer, null, /* @__PURE__ */ React5.createElement(
1813
2088
  "section",
1814
2089
  {
1815
2090
  "aria-label": "Notifications",
@@ -1851,7 +2126,7 @@ function Toaster({ className }) {
1851
2126
  }
1852
2127
  if (!t.leaving && i >= 0) offset += h + GAP;
1853
2128
  const I = toastIcon[t.tone || "neutral"];
1854
- return /* @__PURE__ */ React4.createElement(
2129
+ return /* @__PURE__ */ React5.createElement(
1855
2130
  "div",
1856
2131
  {
1857
2132
  key: t.id,
@@ -1869,28 +2144,28 @@ function Toaster({ className }) {
1869
2144
  },
1870
2145
  style: { transform: `translateY(${y}) scale(${s})`, opacity: o, boxShadow: sh, zIndex: 100 - Math.max(i, 0), height: behind ? frontH : void 0, pointerEvents: o ? void 0 : "none" }
1871
2146
  },
1872
- /* @__PURE__ */ React4.createElement("span", { className: "alt-toast-icon" }, /* @__PURE__ */ React4.createElement(I, { size: 18 })),
1873
- /* @__PURE__ */ React4.createElement("div", { className: "alt-toast-body" }, /* @__PURE__ */ React4.createElement("p", { className: "alt-toast-title" }, t.title), t.description && /* @__PURE__ */ React4.createElement("p", { className: "alt-toast-desc" }, t.description)),
1874
- t.action && /* @__PURE__ */ React4.createElement(Button, { size: "sm", variant: "secondary", className: "alt-toast-action", onClick: () => {
2147
+ /* @__PURE__ */ React5.createElement("span", { className: "alt-toast-icon" }, /* @__PURE__ */ React5.createElement(I, { size: 18 })),
2148
+ /* @__PURE__ */ React5.createElement("div", { className: "alt-toast-body" }, /* @__PURE__ */ React5.createElement("p", { className: "alt-toast-title" }, t.title), t.description && /* @__PURE__ */ React5.createElement("p", { className: "alt-toast-desc" }, t.description)),
2149
+ t.action && /* @__PURE__ */ React5.createElement(Button, { size: "sm", variant: "secondary", className: "alt-toast-action", onClick: () => {
1875
2150
  t.action.onClick();
1876
2151
  toast.dismiss(t.id);
1877
2152
  } }, t.action.label),
1878
- /* @__PURE__ */ React4.createElement("button", { type: "button", className: "alt-toast-close", "aria-label": "Dismiss", onClick: () => toast.dismiss(t.id) }, /* @__PURE__ */ React4.createElement(Icons.X, { size: 14 }))
2153
+ /* @__PURE__ */ React5.createElement("button", { type: "button", className: "alt-toast-close", "aria-label": "Dismiss", onClick: () => toast.dismiss(t.id) }, /* @__PURE__ */ React5.createElement(Icons.X, { size: 14 }))
1879
2154
  );
1880
2155
  })
1881
2156
  ));
1882
2157
  }
1883
2158
 
1884
2159
  // project/components/src/nav.tsx
1885
- var React5 = __toESM(require("react"), 1);
2160
+ var React6 = __toESM(require("react"), 1);
1886
2161
  function Drilldown({ root, className, ...rest }) {
1887
- const [path, setPath] = React5.useState([root]);
1888
- const [dir, setDir] = React5.useState("down");
1889
- const [out, setOut] = React5.useState(null);
1890
- const view = React5.useRef(null);
2162
+ const [path, setPath] = React6.useState([root]);
2163
+ const [dir, setDir] = React6.useState("down");
2164
+ const [out, setOut] = React6.useState(null);
2165
+ const view = React6.useRef(null);
1891
2166
  const depth = path.length - 1;
1892
2167
  const current = path[depth];
1893
- React5.useEffect(() => {
2168
+ React6.useEffect(() => {
1894
2169
  if (!out) return;
1895
2170
  const t = setTimeout(() => setOut(null), 220);
1896
2171
  return () => clearTimeout(t);
@@ -1906,18 +2181,18 @@ function Drilldown({ root, className, ...rest }) {
1906
2181
  setOut(current);
1907
2182
  setPath(path.slice(0, i + 1));
1908
2183
  };
1909
- React5.useEffect(() => {
2184
+ React6.useEffect(() => {
1910
2185
  view.current?.focus({ preventScroll: true });
1911
2186
  }, [current.id]);
1912
- const render = (node) => node.children?.length ? /* @__PURE__ */ React5.createElement("ul", { className: "alt-drill-list" }, node.children.map((c) => /* @__PURE__ */ React5.createElement("li", { key: c.id }, /* @__PURE__ */ React5.createElement("button", { type: "button", className: "alt-drill-row", onClick: () => go(c) }, /* @__PURE__ */ React5.createElement("span", { className: "alt-drill-row-text" }, /* @__PURE__ */ React5.createElement("span", { className: "alt-drill-row-title" }, c.title), c.description && /* @__PURE__ */ React5.createElement("span", { className: "alt-drill-row-desc" }, c.description)), c.children?.length ? /* @__PURE__ */ React5.createElement("span", { className: "alt-drill-count" }, c.children.length) : null, /* @__PURE__ */ React5.createElement(Icons.ChevronDown, { className: "alt-drill-chev", size: 16 }))))) : /* @__PURE__ */ React5.createElement("div", { className: "alt-drill-leaf" }, node.content);
2187
+ const render = (node) => node.children?.length ? /* @__PURE__ */ React6.createElement("ul", { className: "alt-drill-list" }, node.children.map((c) => /* @__PURE__ */ React6.createElement("li", { key: c.id }, /* @__PURE__ */ React6.createElement("button", { type: "button", className: "alt-drill-row", onClick: () => go(c) }, /* @__PURE__ */ React6.createElement("span", { className: "alt-drill-row-text" }, /* @__PURE__ */ React6.createElement("span", { className: "alt-drill-row-title" }, c.title), c.description && /* @__PURE__ */ React6.createElement("span", { className: "alt-drill-row-desc" }, c.description)), c.children?.length ? /* @__PURE__ */ React6.createElement("span", { className: "alt-drill-count" }, c.children.length) : null, /* @__PURE__ */ React6.createElement(Icons.ChevronDown, { className: "alt-drill-chev", size: 16 }))))) : /* @__PURE__ */ React6.createElement("div", { className: "alt-drill-leaf" }, node.content);
1913
2188
  const sheets = Math.min(depth, 3);
1914
- return /* @__PURE__ */ React5.createElement("div", { className: cx("alt-drill", className), "data-dir": dir, ...rest }, /* @__PURE__ */ React5.createElement("nav", { className: "alt-crumbs", "aria-label": "Location" }, /* @__PURE__ */ React5.createElement("ol", null, path.map((n, i) => /* @__PURE__ */ React5.createElement("li", { key: n.id, "data-d": Math.min(i, 3), style: { ["--d"]: i, zIndex: i + 1 }, "data-current": i === depth ? "" : void 0, "data-new": i === depth && dir === "down" && i > 0 ? "" : void 0 }, /* @__PURE__ */ React5.createElement("button", { type: "button", onClick: () => back(i), "aria-current": i === depth ? "location" : void 0 }, n.title))))), /* @__PURE__ */ React5.createElement("div", { className: "alt-pile alt-drill-pile", "data-sheets": sheets }, Array.from({ length: sheets }, (_, i) => /* @__PURE__ */ React5.createElement("span", { key: i, className: "alt-pile-sheet", "aria-hidden": "true", style: { ["--i"]: i + 1 } })), /* @__PURE__ */ React5.createElement("div", { className: "alt-pile-top alt-drill-stage" }, out && /* @__PURE__ */ React5.createElement("div", { key: "out-" + out.id, className: "alt-drill-view", "data-phase": "out", "aria-hidden": "true" }, render(out)), /* @__PURE__ */ React5.createElement("div", { key: current.id, ref: view, tabIndex: -1, className: "alt-drill-view", "data-phase": "in", "aria-label": typeof current.title === "string" ? current.title : void 0 }, render(current)))));
2189
+ return /* @__PURE__ */ React6.createElement("div", { className: cx("alt-drill", className), "data-dir": dir, ...rest }, /* @__PURE__ */ React6.createElement("nav", { className: "alt-crumbs", "aria-label": "Location" }, /* @__PURE__ */ React6.createElement("ol", null, path.map((n, i) => /* @__PURE__ */ React6.createElement("li", { key: n.id, "data-d": Math.min(i, 3), style: { ["--d"]: i, zIndex: i + 1 }, "data-current": i === depth ? "" : void 0, "data-new": i === depth && dir === "down" && i > 0 ? "" : void 0 }, /* @__PURE__ */ React6.createElement("button", { type: "button", onClick: () => back(i), "aria-current": i === depth ? "location" : void 0 }, n.title))))), /* @__PURE__ */ React6.createElement("div", { className: "alt-pile alt-drill-pile", "data-sheets": sheets }, Array.from({ length: sheets }, (_, i) => /* @__PURE__ */ React6.createElement("span", { key: i, className: "alt-pile-sheet", "aria-hidden": "true", style: { ["--i"]: i + 1 } })), /* @__PURE__ */ React6.createElement("div", { className: "alt-pile-top alt-drill-stage" }, out && /* @__PURE__ */ React6.createElement("div", { key: "out-" + out.id, className: "alt-drill-view", "data-phase": "out", "aria-hidden": "true" }, render(out)), /* @__PURE__ */ React6.createElement("div", { key: current.id, ref: view, tabIndex: -1, className: "alt-drill-view", "data-phase": "in", "aria-label": typeof current.title === "string" ? current.title : void 0 }, render(current)))));
1915
2190
  }
1916
2191
 
1917
2192
  // project/components/src/sheet.tsx
1918
- var React6 = __toESM(require("react"), 1);
2193
+ var React7 = __toESM(require("react"), 1);
1919
2194
  var EXIT_42 = 190;
1920
- var SheetCtx = React6.createContext(null);
2195
+ var SheetCtx = React7.createContext(null);
1921
2196
  function Sheet({
1922
2197
  open,
1923
2198
  defaultOpen = false,
@@ -1933,28 +2208,28 @@ function Sheet({
1933
2208
  ...rest
1934
2209
  }) {
1935
2210
  const [isOpen, set] = useControllable(open, defaultOpen, onOpenChange);
1936
- const panel = React6.useRef(null);
1937
- const scroller = React6.useRef(null);
1938
- const inner = React6.useRef(null);
1939
- const id = React6.useId();
1940
- const [titled, setTitled] = React6.useState(false);
1941
- const [described, setDescribed] = React6.useState(false);
1942
- const [edges, setEdges] = React6.useState({ top: false, bottom: false });
1943
- const [drag, setDrag] = React6.useState(null);
1944
- const pull = React6.useRef(null);
1945
- const [panelEl, setPanelEl] = React6.useState(null);
1946
- const panelRef = React6.useCallback((el) => {
2211
+ const panel = React7.useRef(null);
2212
+ const scroller = React7.useRef(null);
2213
+ const inner = React7.useRef(null);
2214
+ const id = React7.useId();
2215
+ const [titled, setTitled] = React7.useState(false);
2216
+ const [described, setDescribed] = React7.useState(false);
2217
+ const [edges, setEdges] = React7.useState({ top: false, bottom: false });
2218
+ const [drag, setDrag] = React7.useState(null);
2219
+ const pull = React7.useRef(null);
2220
+ const [panelEl, setPanelEl] = React7.useState(null);
2221
+ const panelRef = React7.useCallback((el) => {
1947
2222
  panel.current = el;
1948
2223
  setPanelEl(el);
1949
2224
  }, []);
1950
- const underSummit = React6.useMemo(() => isOpen && summitTaken(), [isOpen]);
1951
- const close = React6.useCallback(() => set(false), [set]);
2225
+ const underSummit = React7.useMemo(() => isOpen && summitTaken(), [isOpen]);
2226
+ const close = React7.useCallback(() => set(false), [set]);
1952
2227
  const { mounted, state, onKeyDown } = useModal({ open: isOpen, onDismiss: close, exitMs: EXIT_42, panel, modal, dismissible, autoFocus: !underSummit });
1953
2228
  useApproach(side === "bottom" && dismissible);
1954
- React6.useEffect(() => {
2229
+ React7.useEffect(() => {
1955
2230
  if (isOpen) setDrag(null);
1956
2231
  }, [isOpen]);
1957
- const measure = React6.useCallback(() => {
2232
+ const measure = React7.useCallback(() => {
1958
2233
  const el = scroller.current;
1959
2234
  if (!el) return;
1960
2235
  const top = el.scrollTop > 1, bottom = el.scrollTop + el.clientHeight < el.scrollHeight - 1;
@@ -1990,17 +2265,17 @@ function Sheet({
1990
2265
  close();
1991
2266
  } else setDrag(null);
1992
2267
  };
1993
- const ctx = React6.useMemo(() => ({ titleId: `${id}-t`, descId: `${id}-d`, setTitled, setDescribed }), [id]);
2268
+ const ctx = React7.useMemo(() => ({ titleId: `${id}-t`, descId: `${id}-d`, setTitled, setDescribed }), [id]);
1994
2269
  const dragging = !!drag && !drag.leaving && !!pull.current;
1995
2270
  const dragStyle = drag ? drag.leaving ? { transform: `translateY(${drag.dy + 24}px)` } : { transform: `translateY(${drag.dy}px)`, transition: dragging ? "none" : void 0 } : void 0;
1996
- return /* @__PURE__ */ React6.createElement(React6.Fragment, null, trigger && React6.cloneElement(trigger, {
2271
+ return /* @__PURE__ */ React7.createElement(React7.Fragment, null, trigger && React7.cloneElement(trigger, {
1997
2272
  "aria-haspopup": "dialog",
1998
2273
  "aria-expanded": isOpen,
1999
2274
  onClick: (e) => {
2000
2275
  trigger.props.onClick?.(e);
2001
2276
  set(modal ? true : !isOpen);
2002
2277
  }
2003
- }), mounted && /* @__PURE__ */ React6.createElement(Layer, null, /* @__PURE__ */ React6.createElement(SheetCtx.Provider, { value: ctx }, /* @__PURE__ */ React6.createElement("div", { className: "alt-sheet-root", "data-state": state, "data-exit": !isOpen ? "" : void 0, "data-modal": modal ? "" : void 0, onKeyDown }, modal && /* @__PURE__ */ React6.createElement("div", { className: "alt-scrim", onClick: () => dismissible && close() }), /* @__PURE__ */ React6.createElement(
2278
+ }), mounted && /* @__PURE__ */ React7.createElement(Layer, null, /* @__PURE__ */ React7.createElement(SheetCtx.Provider, { value: ctx }, /* @__PURE__ */ React7.createElement("div", { className: "alt-sheet-root", "data-state": state, "data-exit": !isOpen ? "" : void 0, "data-modal": modal ? "" : void 0, onKeyDown }, modal && /* @__PURE__ */ React7.createElement("div", { className: "alt-scrim", onClick: () => dismissible && close() }), /* @__PURE__ */ React7.createElement(
2004
2279
  "div",
2005
2280
  {
2006
2281
  ref: panelRef,
@@ -2018,7 +2293,7 @@ function Sheet({
2018
2293
  style: { ...style, ...dragStyle },
2019
2294
  ...rest
2020
2295
  },
2021
- side === "bottom" && dismissible && /* @__PURE__ */ React6.createElement(
2296
+ side === "bottom" && dismissible && /* @__PURE__ */ React7.createElement(
2022
2297
  "span",
2023
2298
  {
2024
2299
  className: "alt-sheet-pull",
@@ -2030,35 +2305,35 @@ function Sheet({
2030
2305
  onPointerCancel: onPullUp
2031
2306
  }
2032
2307
  ),
2033
- /* @__PURE__ */ React6.createElement("div", { className: "alt-sheet-scroll", ref: scroller, onScroll: measure }, /* @__PURE__ */ React6.createElement("div", { className: "alt-sheet-inner", ref: inner }, children)),
2034
- dismissible && /* @__PURE__ */ React6.createElement(Button, { variant: "ghost", size: "sm", square: true, "aria-label": "Close", className: "alt-sheet-close", onClick: close }, /* @__PURE__ */ React6.createElement(Icons.X, null))
2308
+ /* @__PURE__ */ React7.createElement("div", { className: "alt-sheet-scroll", ref: scroller, onScroll: measure }, /* @__PURE__ */ React7.createElement("div", { className: "alt-sheet-inner", ref: inner }, children)),
2309
+ dismissible && /* @__PURE__ */ React7.createElement(Button, { variant: "ghost", size: "sm", square: true, "aria-label": "Close", className: "alt-sheet-close", onClick: close }, /* @__PURE__ */ React7.createElement(Icons.X, null))
2035
2310
  )))));
2036
2311
  }
2037
2312
  function SheetHeader({ className, ...p }) {
2038
- return /* @__PURE__ */ React6.createElement("div", { className: cx("alt-sheet-header", className), ...p });
2313
+ return /* @__PURE__ */ React7.createElement("div", { className: cx("alt-sheet-header", className), ...p });
2039
2314
  }
2040
2315
  function SheetTitle({ className, ...p }) {
2041
- const c = React6.useContext(SheetCtx);
2042
- React6.useEffect(() => {
2316
+ const c = React7.useContext(SheetCtx);
2317
+ React7.useEffect(() => {
2043
2318
  c?.setTitled(true);
2044
2319
  return () => c?.setTitled(false);
2045
2320
  }, [c]);
2046
- return /* @__PURE__ */ React6.createElement("h2", { id: c?.titleId, className: cx("alt-sheet-title", className), ...p });
2321
+ return /* @__PURE__ */ React7.createElement("h2", { id: c?.titleId, className: cx("alt-sheet-title", className), ...p });
2047
2322
  }
2048
2323
  function SheetDescription({ className, ...p }) {
2049
- const c = React6.useContext(SheetCtx);
2050
- React6.useEffect(() => {
2324
+ const c = React7.useContext(SheetCtx);
2325
+ React7.useEffect(() => {
2051
2326
  c?.setDescribed(true);
2052
2327
  return () => c?.setDescribed(false);
2053
2328
  }, [c]);
2054
- return /* @__PURE__ */ React6.createElement("p", { id: c?.descId, className: cx("alt-sheet-desc", className), ...p });
2329
+ return /* @__PURE__ */ React7.createElement("p", { id: c?.descId, className: cx("alt-sheet-desc", className), ...p });
2055
2330
  }
2056
2331
  function SheetFooter({ className, ...p }) {
2057
- return /* @__PURE__ */ React6.createElement("div", { className: cx("alt-sheet-footer", className), ...p });
2332
+ return /* @__PURE__ */ React7.createElement("div", { className: cx("alt-sheet-footer", className), ...p });
2058
2333
  }
2059
2334
 
2060
2335
  // project/components/src/command.tsx
2061
- var React7 = __toESM(require("react"), 1);
2336
+ var React8 = __toESM(require("react"), 1);
2062
2337
  var EXIT_52 = 220;
2063
2338
  function commandScore(text, query) {
2064
2339
  const t = text.toLowerCase(), q = query.toLowerCase().trim();
@@ -2109,18 +2384,18 @@ function matchRanges(label, query) {
2109
2384
  return out;
2110
2385
  }
2111
2386
  function Marked({ text, ranges }) {
2112
- if (!ranges.length) return /* @__PURE__ */ React7.createElement(React7.Fragment, null, text);
2387
+ if (!ranges.length) return /* @__PURE__ */ React8.createElement(React8.Fragment, null, text);
2113
2388
  const parts = [];
2114
2389
  let i = 0;
2115
2390
  ranges.forEach(([a, b], k) => {
2116
2391
  if (a > i) parts.push(text.slice(i, a));
2117
- parts.push(/* @__PURE__ */ React7.createElement("mark", { key: k, className: "alt-cmd-match" }, text.slice(a, b)));
2392
+ parts.push(/* @__PURE__ */ React8.createElement("mark", { key: k, className: "alt-cmd-match" }, text.slice(a, b)));
2118
2393
  i = b;
2119
2394
  });
2120
2395
  if (i < text.length) parts.push(text.slice(i));
2121
- return /* @__PURE__ */ React7.createElement(React7.Fragment, null, parts);
2396
+ return /* @__PURE__ */ React8.createElement(React8.Fragment, null, parts);
2122
2397
  }
2123
- var SearchIcon = () => /* @__PURE__ */ React7.createElement("svg", { width: "18", height: "18", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: 1.75, strokeLinecap: "round", "aria-hidden": "true" }, /* @__PURE__ */ React7.createElement("circle", { cx: "11", cy: "11", r: "7" }), /* @__PURE__ */ React7.createElement("path", { d: "M20 20l-3.5-3.5" }));
2398
+ var SearchIcon = () => /* @__PURE__ */ React8.createElement("svg", { width: "18", height: "18", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: 1.75, strokeLinecap: "round", "aria-hidden": "true" }, /* @__PURE__ */ React8.createElement("circle", { cx: "11", cy: "11", r: "7" }), /* @__PURE__ */ React8.createElement("path", { d: "M20 20l-3.5-3.5" }));
2124
2399
  var ms = (cs, name, fallback) => parseFloat(cs.getPropertyValue(name)) || fallback;
2125
2400
  function CommandPalette({
2126
2401
  items,
@@ -2141,30 +2416,30 @@ function CommandPalette({
2141
2416
  ...rest
2142
2417
  }) {
2143
2418
  const [isOpen, set] = useControllable(open, defaultOpen, onOpenChange);
2144
- const [innerQuery, setInnerQuery] = React7.useState(defaultQuery);
2419
+ const [innerQuery, setInnerQuery] = React8.useState(defaultQuery);
2145
2420
  const query = queryProp ?? innerQuery;
2146
- const [active, setActive] = React7.useState(0);
2147
- const [onset, setOnset] = React7.useState(true);
2148
- const [said, setSaid] = React7.useState("");
2149
- const panel = React7.useRef(null);
2150
- const viewport = React7.useRef(null);
2151
- const list = React7.useRef(null);
2152
- const sizer = React7.useRef(null);
2153
- const rowEls = React7.useRef(/* @__PURE__ */ new Map());
2154
- const prevTops = React7.useRef(null);
2155
- const byKeyboard = React7.useRef(false);
2156
- const caretPlaced = React7.useRef(false);
2157
- const seed = React7.useRef(defaultQuery);
2421
+ const [active, setActive] = React8.useState(0);
2422
+ const [onset, setOnset] = React8.useState(true);
2423
+ const [said, setSaid] = React8.useState("");
2424
+ const panel = React8.useRef(null);
2425
+ const viewport = React8.useRef(null);
2426
+ const list = React8.useRef(null);
2427
+ const sizer = React8.useRef(null);
2428
+ const rowEls = React8.useRef(/* @__PURE__ */ new Map());
2429
+ const prevTops = React8.useRef(null);
2430
+ const byKeyboard = React8.useRef(false);
2431
+ const caretPlaced = React8.useRef(false);
2432
+ const seed = React8.useRef(defaultQuery);
2158
2433
  seed.current = defaultQuery;
2159
- const [panelEl, setPanelEl] = React7.useState(null);
2160
- const panelRef = React7.useCallback((el) => {
2434
+ const [panelEl, setPanelEl] = React8.useState(null);
2435
+ const panelRef = React8.useCallback((el) => {
2161
2436
  panel.current = el;
2162
2437
  setPanelEl(el);
2163
2438
  }, []);
2164
- const id = React7.useId();
2165
- const close = React7.useCallback(() => set(false), [set]);
2439
+ const id = React8.useId();
2440
+ const close = React8.useCallback(() => set(false), [set]);
2166
2441
  const { mounted, state, onKeyDown } = useModal({ open: isOpen, onDismiss: close, exitMs: EXIT_52, panel, summit: true });
2167
- React7.useEffect(() => {
2442
+ React8.useEffect(() => {
2168
2443
  if (!shortcut) return;
2169
2444
  const key = shortcut.toLowerCase();
2170
2445
  const on = (e) => {
@@ -2180,7 +2455,7 @@ function CommandPalette({
2180
2455
  window.addEventListener("keydown", on);
2181
2456
  return () => window.removeEventListener("keydown", on);
2182
2457
  }, [shortcut, isOpen, set]);
2183
- React7.useEffect(() => {
2458
+ React8.useEffect(() => {
2184
2459
  if (isOpen) {
2185
2460
  setInnerQuery(seed.current);
2186
2461
  setActive(0);
@@ -2188,7 +2463,7 @@ function CommandPalette({
2188
2463
  caretPlaced.current = false;
2189
2464
  }
2190
2465
  }, [isOpen]);
2191
- React7.useEffect(() => {
2466
+ React8.useEffect(() => {
2192
2467
  setActive(0);
2193
2468
  }, [query]);
2194
2469
  const q = query.trim();
@@ -2254,14 +2529,14 @@ function CommandPalette({
2254
2529
  ro.disconnect();
2255
2530
  };
2256
2531
  }, [panelEl]);
2257
- const [hl, setHl] = React7.useState(null);
2532
+ const [hl, setHl] = React8.useState(null);
2258
2533
  useIsoLayoutEffect(() => {
2259
2534
  const el = activeRow ? rowEls.current.get(activeRow.key) : null;
2260
2535
  setHl(el ? { y: el.offsetTop, h: el.offsetHeight } : null);
2261
2536
  if (el && byKeyboard.current) el.scrollIntoView({ block: "nearest" });
2262
2537
  byKeyboard.current = false;
2263
2538
  }, [activeRow?.key, rowsKey, panelEl]);
2264
- React7.useEffect(() => {
2539
+ React8.useEffect(() => {
2265
2540
  if (!q) {
2266
2541
  setSaid("");
2267
2542
  return;
@@ -2291,7 +2566,7 @@ function CommandPalette({
2291
2566
  const label = rest["aria-label"] ?? "Command palette";
2292
2567
  const activeIndex = activeRow ? flat.indexOf(activeRow) : -1;
2293
2568
  let n = 0;
2294
- return /* @__PURE__ */ React7.createElement(Layer, null, /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-root", "data-state": state, onKeyDown }, /* @__PURE__ */ React7.createElement("div", { className: "alt-scrim", onClick: close }), /* @__PURE__ */ React7.createElement("div", { ref: panelRef, role: "dialog", "aria-modal": "true", "aria-label": label, tabIndex: -1, className: cx("alt-cmd", className), "data-ephemeral": ephemeral ? "" : void 0 }, /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-head" }, /* @__PURE__ */ React7.createElement(
2569
+ return /* @__PURE__ */ React8.createElement(Layer, null, /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-root", "data-state": state, onKeyDown }, /* @__PURE__ */ React8.createElement("div", { className: "alt-scrim", onClick: close }), /* @__PURE__ */ React8.createElement("div", { ref: panelRef, role: "dialog", "aria-modal": "true", "aria-label": label, tabIndex: -1, className: cx("alt-cmd", className), "data-ephemeral": ephemeral ? "" : void 0 }, /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-head" }, /* @__PURE__ */ React8.createElement(
2295
2570
  Input,
2296
2571
  {
2297
2572
  className: "alt-cmd-field",
@@ -2305,8 +2580,8 @@ function CommandPalette({
2305
2580
  "aria-controls": `${id}-list`,
2306
2581
  "aria-autocomplete": "list",
2307
2582
  "aria-activedescendant": activeIndex >= 0 ? `${id}-o-${activeIndex}` : void 0,
2308
- leading: /* @__PURE__ */ React7.createElement(SearchIcon, null),
2309
- trailing: /* @__PURE__ */ React7.createElement("span", { "aria-hidden": "true" }, /* @__PURE__ */ React7.createElement(Kbd, null, "esc")),
2583
+ leading: /* @__PURE__ */ React8.createElement(SearchIcon, null),
2584
+ trailing: /* @__PURE__ */ React8.createElement("span", { "aria-hidden": "true" }, /* @__PURE__ */ React8.createElement(Kbd, null, "esc")),
2310
2585
  onChange: (e) => {
2311
2586
  setInnerQuery(e.target.value);
2312
2587
  setActive(0);
@@ -2321,7 +2596,7 @@ function CommandPalette({
2321
2596
  },
2322
2597
  onKeyDown: onInputKeyDown
2323
2598
  }
2324
- )), /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-viewport", ref: viewport }, /* @__PURE__ */ React7.createElement("div", { ref: sizer }, /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-list", ref: list, role: "listbox", id: `${id}-list`, "aria-label": "Results" }, /* @__PURE__ */ React7.createElement(
2599
+ )), /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-viewport", ref: viewport }, /* @__PURE__ */ React8.createElement("div", { ref: sizer }, /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-list", ref: list, role: "listbox", id: `${id}-list`, "aria-label": "Results" }, /* @__PURE__ */ React8.createElement(
2325
2600
  "span",
2326
2601
  {
2327
2602
  className: "alt-cmd-hl",
@@ -2332,10 +2607,10 @@ function CommandPalette({
2332
2607
  ), view.map((v) => {
2333
2608
  const labelId = `${id}-g-${v.gi}`;
2334
2609
  const groupPredicted = !!v.g.predicted || v.rows.every((r) => r.item.predicted);
2335
- return /* @__PURE__ */ React7.createElement("div", { key: v.gk, role: "group", "aria-labelledby": v.g.label ? labelId : void 0, className: "alt-cmd-group" }, v.g.label && /* @__PURE__ */ React7.createElement("div", { id: labelId, role: "presentation", className: "alt-cmd-label", "data-flip": "g:" + v.gk, "data-predicted": groupPredicted ? "" : void 0 }, v.g.label), v.rows.map(() => {
2610
+ return /* @__PURE__ */ React8.createElement("div", { key: v.gk, role: "group", "aria-labelledby": v.g.label ? labelId : void 0, className: "alt-cmd-group" }, v.g.label && /* @__PURE__ */ React8.createElement("div", { id: labelId, role: "presentation", className: "alt-cmd-label", "data-flip": "g:" + v.gk, "data-predicted": groupPredicted ? "" : void 0 }, v.g.label), v.rows.map(() => {
2336
2611
  const i = n++, r = flat[i], item = r.item;
2337
2612
  const on = r === activeRow;
2338
- return /* @__PURE__ */ React7.createElement(
2613
+ return /* @__PURE__ */ React8.createElement(
2339
2614
  "div",
2340
2615
  {
2341
2616
  key: r.key,
@@ -2356,16 +2631,16 @@ function CommandPalette({
2356
2631
  },
2357
2632
  onClick: () => choose(r)
2358
2633
  },
2359
- item.icon && /* @__PURE__ */ React7.createElement("span", { className: "alt-cmd-icon", "aria-hidden": "true" }, item.icon),
2360
- /* @__PURE__ */ React7.createElement("span", { className: "alt-cmd-text" }, /* @__PURE__ */ React7.createElement("span", { className: "alt-cmd-title" }, /* @__PURE__ */ React7.createElement(Marked, { text: item.label, ranges: matchRanges(item.label, q) })), item.description && /* @__PURE__ */ React7.createElement("span", { className: "alt-cmd-desc" }, item.description)),
2361
- item.shortcut && /* @__PURE__ */ React7.createElement("span", { className: "alt-cmd-keys" }, item.shortcut.map((k, j) => /* @__PURE__ */ React7.createElement(Kbd, { key: j }, k)))
2634
+ item.icon && /* @__PURE__ */ React8.createElement("span", { className: "alt-cmd-icon", "aria-hidden": "true" }, item.icon),
2635
+ /* @__PURE__ */ React8.createElement("span", { className: "alt-cmd-text" }, /* @__PURE__ */ React8.createElement("span", { className: "alt-cmd-title" }, /* @__PURE__ */ React8.createElement(Marked, { text: item.label, ranges: matchRanges(item.label, q) })), item.description && /* @__PURE__ */ React8.createElement("span", { className: "alt-cmd-desc" }, item.description)),
2636
+ item.shortcut && /* @__PURE__ */ React8.createElement("span", { className: "alt-cmd-keys" }, item.shortcut.map((k, j) => /* @__PURE__ */ React8.createElement(Kbd, { key: j }, k)))
2362
2637
  );
2363
2638
  }));
2364
- })), q && !flat.length && /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-empty" }, typeof empty === "function" ? empty(q) : empty ?? /* @__PURE__ */ React7.createElement(React7.Fragment, null, /* @__PURE__ */ React7.createElement("b", null, "No results for \u201C", q, "\u201D"), "Try another word, or check the spelling.")))), hints && /* @__PURE__ */ React7.createElement("div", { className: "alt-cmd-foot", "aria-hidden": "true" }, /* @__PURE__ */ React7.createElement("span", null, /* @__PURE__ */ React7.createElement(Kbd, null, "\u2191"), /* @__PURE__ */ React7.createElement(Kbd, null, "\u2193"), "Move"), /* @__PURE__ */ React7.createElement("span", null, /* @__PURE__ */ React7.createElement(Kbd, null, "\u21B5"), "Choose"), /* @__PURE__ */ React7.createElement("span", null, /* @__PURE__ */ React7.createElement(Kbd, null, "esc"), "Close")), /* @__PURE__ */ React7.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said))));
2639
+ })), q && !flat.length && /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-empty" }, typeof empty === "function" ? empty(q) : empty ?? /* @__PURE__ */ React8.createElement(React8.Fragment, null, /* @__PURE__ */ React8.createElement("b", null, "No results for \u201C", q, "\u201D"), "Try another word, or check the spelling.")))), hints && /* @__PURE__ */ React8.createElement("div", { className: "alt-cmd-foot", "aria-hidden": "true" }, /* @__PURE__ */ React8.createElement("span", null, /* @__PURE__ */ React8.createElement(Kbd, null, "\u2191"), /* @__PURE__ */ React8.createElement(Kbd, null, "\u2193"), "Move"), /* @__PURE__ */ React8.createElement("span", null, /* @__PURE__ */ React8.createElement(Kbd, null, "\u21B5"), "Choose"), /* @__PURE__ */ React8.createElement("span", null, /* @__PURE__ */ React8.createElement(Kbd, null, "esc"), "Close")), /* @__PURE__ */ React8.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said))));
2365
2640
  }
2366
2641
 
2367
2642
  // project/components/src/select.tsx
2368
- var React8 = __toESM(require("react"), 1);
2643
+ var React9 = __toESM(require("react"), 1);
2369
2644
  var EXIT_32 = 160;
2370
2645
  function SelectItem(_) {
2371
2646
  return null;
@@ -2374,17 +2649,17 @@ var textOf = (o) => o.textValue ?? (typeof o.label === "string" || typeof o.labe
2374
2649
  function collect(items, children) {
2375
2650
  if (items) return items;
2376
2651
  const out = [];
2377
- React8.Children.forEach(children, (c) => {
2378
- if (!React8.isValidElement(c) || c.type !== SelectItem) return;
2652
+ React9.Children.forEach(children, (c) => {
2653
+ if (!React9.isValidElement(c) || c.type !== SelectItem) return;
2379
2654
  const p = c.props;
2380
2655
  out.push({ value: p.value, label: p.children, textValue: p.textValue, description: p.description, icon: p.icon, disabled: p.disabled });
2381
2656
  });
2382
2657
  return out;
2383
2658
  }
2384
- var Tick = () => /* @__PURE__ */ React8.createElement("svg", { className: "alt-select-tick", viewBox: "0 0 16 16", width: "15", height: "15", fill: "none", stroke: "currentColor", strokeWidth: "2.25", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React8.createElement("path", { d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }));
2385
- var Chevron = () => /* @__PURE__ */ React8.createElement(Icons.ChevronDown, { className: "alt-select-chevron", size: 16 });
2659
+ var Tick = () => /* @__PURE__ */ React9.createElement("svg", { className: "alt-select-tick", viewBox: "0 0 16 16", width: "15", height: "15", fill: "none", stroke: "currentColor", strokeWidth: "2.25", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React9.createElement("path", { d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }));
2660
+ var Chevron = () => /* @__PURE__ */ React9.createElement(Icons.ChevronDown, { className: "alt-select-chevron", size: 16 });
2386
2661
  function useSide(open, anchor, list) {
2387
- const [side, setSide] = React8.useState("bottom");
2662
+ const [side, setSide] = React9.useState("bottom");
2388
2663
  useIsoLayoutEffect(() => {
2389
2664
  if (!open || !anchor.current || !list.current) return;
2390
2665
  const a = anchor.current.getBoundingClientRect(), need = list.current.offsetHeight + 12;
@@ -2402,9 +2677,9 @@ function useSide(open, anchor, list) {
2402
2677
  return side;
2403
2678
  }
2404
2679
  function useGlow(value) {
2405
- const [glow, setGlow] = React8.useState(void 0);
2406
- const first = React8.useRef(true);
2407
- React8.useEffect(() => {
2680
+ const [glow, setGlow] = React9.useState(void 0);
2681
+ const first = React9.useRef(true);
2682
+ React9.useEffect(() => {
2408
2683
  if (first.current) {
2409
2684
  first.current = false;
2410
2685
  return;
@@ -2414,8 +2689,8 @@ function useGlow(value) {
2414
2689
  return glow;
2415
2690
  }
2416
2691
  function useLabelId(controlId, fallback) {
2417
- const [labelId, setLabelId] = React8.useState(void 0);
2418
- React8.useEffect(() => {
2692
+ const [labelId, setLabelId] = React9.useState(void 0);
2693
+ React9.useEffect(() => {
2419
2694
  const label = document.querySelector(`label[for="${CSS.escape(controlId)}"]`);
2420
2695
  if (!label) {
2421
2696
  setLabelId(void 0);
@@ -2427,8 +2702,8 @@ function useLabelId(controlId, fallback) {
2427
2702
  return labelId;
2428
2703
  }
2429
2704
  function OptionList({ id, options, active, value, state, side, query, empty, listRef, labelledBy, label, focusable, onActive, onChoose, onKeyDown }) {
2430
- const rows = React8.useRef([]);
2431
- const [hl, setHl] = React8.useState(null);
2705
+ const rows = React9.useRef([]);
2706
+ const [hl, setHl] = React9.useState(null);
2432
2707
  useIsoLayoutEffect(() => {
2433
2708
  const el = active >= 0 ? rows.current[active] : null;
2434
2709
  setHl(el ? { y: el.offsetTop, h: el.offsetHeight } : null);
@@ -2443,9 +2718,9 @@ function OptionList({ id, options, active, value, state, side, query, empty, lis
2443
2718
  if (!query || typeof o.label !== "string") return o.label;
2444
2719
  const i = t.toLowerCase().indexOf(query.toLowerCase());
2445
2720
  if (i < 0) return o.label;
2446
- return /* @__PURE__ */ React8.createElement(React8.Fragment, null, t.slice(0, i), /* @__PURE__ */ React8.createElement("mark", { className: "alt-cmd-match" }, t.slice(i, i + query.length)), t.slice(i + query.length));
2721
+ return /* @__PURE__ */ React9.createElement(React9.Fragment, null, t.slice(0, i), /* @__PURE__ */ React9.createElement("mark", { className: "alt-cmd-match" }, t.slice(i, i + query.length)), t.slice(i + query.length));
2447
2722
  };
2448
- return /* @__PURE__ */ React8.createElement(
2723
+ return /* @__PURE__ */ React9.createElement(
2449
2724
  "div",
2450
2725
  {
2451
2726
  ref: listRef,
@@ -2461,8 +2736,8 @@ function OptionList({ id, options, active, value, state, side, query, empty, lis
2461
2736
  onKeyDown,
2462
2737
  onMouseDown: (e) => e.preventDefault()
2463
2738
  },
2464
- /* @__PURE__ */ React8.createElement("span", { className: "alt-menu-hl", "aria-hidden": "true", style: hl ? { transform: `translateY(${hl.y}px)`, height: hl.h, opacity: 1 } : { opacity: 0 } }),
2465
- options.map((o, i) => /* @__PURE__ */ React8.createElement(
2739
+ /* @__PURE__ */ React9.createElement("span", { className: "alt-menu-hl", "aria-hidden": "true", style: hl ? { transform: `translateY(${hl.y}px)`, height: hl.h, opacity: 1 } : { opacity: 0 } }),
2740
+ options.map((o, i) => /* @__PURE__ */ React9.createElement(
2466
2741
  "div",
2467
2742
  {
2468
2743
  key: o.value,
@@ -2481,11 +2756,11 @@ function OptionList({ id, options, active, value, state, side, query, empty, lis
2481
2756
  },
2482
2757
  onClick: () => onChoose(i)
2483
2758
  },
2484
- o.icon && /* @__PURE__ */ React8.createElement("span", { className: "alt-menu-icon" }, o.icon),
2485
- /* @__PURE__ */ React8.createElement("span", { className: "alt-menu-text" }, marks(o), o.description && /* @__PURE__ */ React8.createElement("span", { className: "alt-select-desc" }, o.description)),
2486
- o.value === value && /* @__PURE__ */ React8.createElement(Tick, null)
2759
+ o.icon && /* @__PURE__ */ React9.createElement("span", { className: "alt-menu-icon" }, o.icon),
2760
+ /* @__PURE__ */ React9.createElement("span", { className: "alt-menu-text" }, marks(o), o.description && /* @__PURE__ */ React9.createElement("span", { className: "alt-select-desc" }, o.description)),
2761
+ o.value === value && /* @__PURE__ */ React9.createElement(Tick, null)
2487
2762
  )),
2488
- !options.length && /* @__PURE__ */ React8.createElement("div", { className: "alt-select-empty" }, empty)
2763
+ !options.length && /* @__PURE__ */ React9.createElement("div", { className: "alt-select-empty" }, empty)
2489
2764
  );
2490
2765
  }
2491
2766
  function Select({
@@ -2507,16 +2782,16 @@ function Select({
2507
2782
  }) {
2508
2783
  const options = collect(items, children);
2509
2784
  const [v, set] = useControllable(value, defaultValue, onValueChange);
2510
- const [open, setOpen] = React8.useState(defaultOpen);
2511
- const [active, setActive] = React8.useState(() => defaultOpen ? options.findIndex((o) => o.value === (value ?? defaultValue)) : -1);
2512
- const auto = React8.useId();
2785
+ const [open, setOpen] = React9.useState(defaultOpen);
2786
+ const [active, setActive] = React9.useState(() => defaultOpen ? options.findIndex((o) => o.value === (value ?? defaultValue)) : -1);
2787
+ const auto = React9.useId();
2513
2788
  const triggerId = id ?? auto + "-trigger";
2514
2789
  const listId = auto + "-list";
2515
- const root = React8.useRef(null);
2516
- const field = React8.useRef(null);
2517
- const trigger = React8.useRef(null);
2518
- const list = React8.useRef(null);
2519
- const typed = React8.useRef({ text: "", at: 0 });
2790
+ const root = React9.useRef(null);
2791
+ const field = React9.useRef(null);
2792
+ const trigger = React9.useRef(null);
2793
+ const list = React9.useRef(null);
2794
+ const typed = React9.useRef({ text: "", at: 0 });
2520
2795
  const { mounted, state } = usePresence(open, EXIT_32);
2521
2796
  const side = useSide(mounted, field, list);
2522
2797
  const glow = useGlow(v);
@@ -2525,12 +2800,12 @@ function Select({
2525
2800
  useKeyFocus();
2526
2801
  const chosen = options.find((o) => o.value === v);
2527
2802
  const enabled = options.map((o, i) => o.disabled ? -1 : i).filter((i) => i >= 0);
2528
- const close = React8.useCallback((refocus = true) => {
2803
+ const close = React9.useCallback((refocus = true) => {
2529
2804
  setOpen(false);
2530
2805
  if (refocus) trigger.current?.focus({ preventScroll: true });
2531
2806
  }, []);
2532
2807
  useOutside(root, open, () => close(false));
2533
- React8.useEffect(() => {
2808
+ React9.useEffect(() => {
2534
2809
  if (state === "open") list.current?.focus({ preventScroll: true });
2535
2810
  }, [state]);
2536
2811
  const openAt = (i) => {
@@ -2602,7 +2877,7 @@ function Select({
2602
2877
  }
2603
2878
  }
2604
2879
  };
2605
- return /* @__PURE__ */ React8.createElement("div", { ref: root, className: cx("alt-select", className), "data-open": open ? "" : void 0 }, /* @__PURE__ */ React8.createElement(
2880
+ return /* @__PURE__ */ React9.createElement("div", { ref: root, className: cx("alt-select", className), "data-open": open ? "" : void 0 }, /* @__PURE__ */ React9.createElement(
2606
2881
  "div",
2607
2882
  {
2608
2883
  ref: field,
@@ -2613,7 +2888,7 @@ function Select({
2613
2888
  "data-invalid": invalid ? "" : void 0,
2614
2889
  "data-disabled": disabled ? "" : void 0
2615
2890
  },
2616
- /* @__PURE__ */ React8.createElement(
2891
+ /* @__PURE__ */ React9.createElement(
2617
2892
  "button",
2618
2893
  {
2619
2894
  ref: trigger,
@@ -2630,10 +2905,10 @@ function Select({
2630
2905
  onClick: () => open ? close() : openAt(current()),
2631
2906
  onKeyDown: onTriggerKey
2632
2907
  },
2633
- /* @__PURE__ */ React8.createElement("span", { className: "alt-select-value", "data-placeholder": chosen ? void 0 : "", "data-glow": glow }, chosen ? /* @__PURE__ */ React8.createElement(React8.Fragment, null, chosen.icon && /* @__PURE__ */ React8.createElement("span", { className: "alt-select-icon" }, chosen.icon), chosen.label) : placeholder),
2634
- /* @__PURE__ */ React8.createElement(Chevron, null)
2908
+ /* @__PURE__ */ React9.createElement("span", { className: "alt-select-value", "data-placeholder": chosen ? void 0 : "", "data-glow": glow }, chosen ? /* @__PURE__ */ React9.createElement(React9.Fragment, null, chosen.icon && /* @__PURE__ */ React9.createElement("span", { className: "alt-select-icon" }, chosen.icon), chosen.label) : placeholder),
2909
+ /* @__PURE__ */ React9.createElement(Chevron, null)
2635
2910
  )
2636
- ), name && /* @__PURE__ */ React8.createElement("input", { type: "hidden", name, value: v }), mounted && /* @__PURE__ */ React8.createElement(
2911
+ ), name && /* @__PURE__ */ React9.createElement("input", { type: "hidden", name, value: v }), mounted && /* @__PURE__ */ React9.createElement(
2637
2912
  OptionList,
2638
2913
  {
2639
2914
  id: listId,
@@ -2672,24 +2947,24 @@ function Combobox({
2672
2947
  }) {
2673
2948
  const [v, set] = useControllable(value, defaultValue, onValueChange);
2674
2949
  const chosen = items.find((o) => o.value === v);
2675
- const [text, setText] = React8.useState(chosen ? textOf(chosen) : "");
2676
- const [typing, setTyping] = React8.useState(false);
2677
- const [open, setOpen] = React8.useState(defaultOpen);
2678
- const [active, setActive] = React8.useState(() => defaultOpen ? items.findIndex((o) => o.value === (value ?? defaultValue)) : -1);
2679
- const auto = React8.useId();
2950
+ const [text, setText] = React9.useState(chosen ? textOf(chosen) : "");
2951
+ const [typing, setTyping] = React9.useState(false);
2952
+ const [open, setOpen] = React9.useState(defaultOpen);
2953
+ const [active, setActive] = React9.useState(() => defaultOpen ? items.findIndex((o) => o.value === (value ?? defaultValue)) : -1);
2954
+ const auto = React9.useId();
2680
2955
  const inputId = id ?? auto + "-input";
2681
2956
  const listId = auto + "-list";
2682
- const root = React8.useRef(null);
2683
- const field = React8.useRef(null);
2684
- const input = React8.useRef(null);
2685
- const list = React8.useRef(null);
2957
+ const root = React9.useRef(null);
2958
+ const field = React9.useRef(null);
2959
+ const input = React9.useRef(null);
2960
+ const list = React9.useRef(null);
2686
2961
  const { mounted, state } = usePresence(open, EXIT_32);
2687
2962
  const side = useSide(mounted, field, list);
2688
2963
  const glow = useGlow(v);
2689
2964
  const labelId = useLabelId(inputId, auto + "-label");
2690
2965
  useApproach();
2691
2966
  useKeyFocus();
2692
- React8.useEffect(() => {
2967
+ React9.useEffect(() => {
2693
2968
  if (!typing) setText(chosen ? textOf(chosen) : "");
2694
2969
  }, [v]);
2695
2970
  const q = typing ? text.trim() : "";
@@ -2756,7 +3031,7 @@ function Combobox({
2756
3031
  if (!root.current?.contains(e.relatedTarget)) commit();
2757
3032
  };
2758
3033
  const filled = !!chosen && !typing;
2759
- return /* @__PURE__ */ React8.createElement("div", { ref: root, className: cx("alt-select alt-combobox", className), "data-open": open ? "" : void 0 }, /* @__PURE__ */ React8.createElement(
3034
+ return /* @__PURE__ */ React9.createElement("div", { ref: root, className: cx("alt-select alt-combobox", className), "data-open": open ? "" : void 0 }, /* @__PURE__ */ React9.createElement(
2760
3035
  "div",
2761
3036
  {
2762
3037
  ref: field,
@@ -2767,7 +3042,7 @@ function Combobox({
2767
3042
  "data-invalid": invalid ? "" : void 0,
2768
3043
  "data-disabled": disabled ? "" : void 0
2769
3044
  },
2770
- /* @__PURE__ */ React8.createElement(
3045
+ /* @__PURE__ */ React9.createElement(
2771
3046
  "input",
2772
3047
  {
2773
3048
  ref: input,
@@ -2797,7 +3072,7 @@ function Combobox({
2797
3072
  }
2798
3073
  }
2799
3074
  ),
2800
- /* @__PURE__ */ React8.createElement(
3075
+ /* @__PURE__ */ React9.createElement(
2801
3076
  "button",
2802
3077
  {
2803
3078
  type: "button",
@@ -2818,9 +3093,9 @@ function Combobox({
2818
3093
  input.current?.focus();
2819
3094
  }
2820
3095
  },
2821
- /* @__PURE__ */ React8.createElement(Chevron, null)
3096
+ /* @__PURE__ */ React9.createElement(Chevron, null)
2822
3097
  )
2823
- ), name && /* @__PURE__ */ React8.createElement("input", { type: "hidden", name, value: v }), mounted && /* @__PURE__ */ React8.createElement(
3098
+ ), name && /* @__PURE__ */ React9.createElement("input", { type: "hidden", name, value: v }), mounted && /* @__PURE__ */ React9.createElement(
2824
3099
  OptionList,
2825
3100
  {
2826
3101
  id: listId,
@@ -2842,30 +3117,30 @@ function Combobox({
2842
3117
  }
2843
3118
 
2844
3119
  // project/components/src/stepper.tsx
2845
- var React9 = __toESM(require("react"), 1);
2846
- var Tick2 = () => /* @__PURE__ */ React9.createElement("svg", { viewBox: "0 0 16 16", width: "13", height: "13", fill: "none", stroke: "currentColor", strokeWidth: "2.4", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React9.createElement("path", { d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }));
3120
+ var React10 = __toESM(require("react"), 1);
3121
+ var Tick2 = () => /* @__PURE__ */ React10.createElement("svg", { viewBox: "0 0 16 16", width: "13", height: "13", fill: "none", stroke: "currentColor", strokeWidth: "2.4", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React10.createElement("path", { d: "M3.5 8.5l3 3 6-6.5", pathLength: 16 }));
2847
3122
  var word = { done: "completed", current: "current", upcoming: "not started" };
2848
3123
  function Stepper({ steps, current, onStepChange, orientation = "horizontal", className, ...rest }) {
2849
- const [seen, setSeen] = React9.useState(current);
2850
- const [motion, setMotion] = React9.useState(null);
2851
- const [said, setSaid] = React9.useState("");
3124
+ const [seen, setSeen] = React10.useState(current);
3125
+ const [motion, setMotion] = React10.useState(null);
3126
+ const [said, setSaid] = React10.useState("");
2852
3127
  if (seen !== current) {
2853
3128
  setSeen(current);
2854
3129
  setMotion({ pressed: seen, risen: current, stamp: current > seen ? seen : -1, delay: (current > seen ? 150 : 60) + riseDelay(), key: (motion?.key ?? 0) + 1 });
2855
3130
  }
2856
- React9.useEffect(() => {
3131
+ React10.useEffect(() => {
2857
3132
  if (!motion) return;
2858
3133
  const t = steps[current];
2859
3134
  setSaid(t ? `Step ${current + 1} of ${steps.length}: ${typeof t.title === "string" ? t.title : ""}` : "All steps complete");
2860
3135
  const done = setTimeout(() => setMotion(null), 900);
2861
3136
  return () => clearTimeout(done);
2862
3137
  }, [motion?.key]);
2863
- return /* @__PURE__ */ React9.createElement(React9.Fragment, null, /* @__PURE__ */ React9.createElement("ol", { className: cx("alt-stepper", className), "data-orientation": orientation, "aria-label": rest["aria-label"] ?? "Progress", ...rest }, steps.map((s, i) => {
3138
+ return /* @__PURE__ */ React10.createElement(React10.Fragment, null, /* @__PURE__ */ React10.createElement("ol", { className: cx("alt-stepper", className), "data-orientation": orientation, "aria-label": rest["aria-label"] ?? "Progress", ...rest }, steps.map((s, i) => {
2864
3139
  const state = i < current ? "done" : i === current ? "current" : "upcoming";
2865
3140
  const back = state === "done" && !!onStepChange;
2866
3141
  const rising = motion && motion.risen === i;
2867
3142
  const stamped = motion && motion.stamp === i;
2868
- return /* @__PURE__ */ React9.createElement("li", { key: s.id ?? i, className: "alt-step-item", "data-state": state, "aria-current": state === "current" ? "step" : void 0 }, /* @__PURE__ */ React9.createElement(
3143
+ return /* @__PURE__ */ React10.createElement("li", { key: s.id ?? i, className: "alt-step-item", "data-state": state, "aria-current": state === "current" ? "step" : void 0 }, /* @__PURE__ */ React10.createElement(
2869
3144
  "div",
2870
3145
  {
2871
3146
  className: "alt-step",
@@ -2884,14 +3159,14 @@ function Stepper({ steps, current, onStepChange, orientation = "horizontal", cla
2884
3159
  } : {},
2885
3160
  style: rising ? { ["--alt-rise-delay"]: motion.delay + "ms" } : void 0
2886
3161
  },
2887
- /* @__PURE__ */ React9.createElement("span", { className: "alt-step-mark", "data-stamp": stamped ? motion.key % 2 ? "a" : "b" : void 0 }, state === "done" ? /* @__PURE__ */ React9.createElement(Tick2, null) : i + 1),
2888
- /* @__PURE__ */ React9.createElement("span", { className: "alt-step-text" }, /* @__PURE__ */ React9.createElement("span", { className: "alt-sr" }, "Step ", i + 1, " of ", steps.length, ", ", word[state], ": "), /* @__PURE__ */ React9.createElement("span", { className: "alt-step-title" }, s.title), s.description && /* @__PURE__ */ React9.createElement("span", { className: "alt-step-desc" }, s.description))
2889
- ), i < steps.length - 1 && /* @__PURE__ */ React9.createElement("span", { className: "alt-step-line", "aria-hidden": "true", "data-done": i < current ? "" : void 0 }));
2890
- })), /* @__PURE__ */ React9.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said));
3162
+ /* @__PURE__ */ React10.createElement("span", { className: "alt-step-mark", "data-stamp": stamped ? motion.key % 2 ? "a" : "b" : void 0 }, state === "done" ? /* @__PURE__ */ React10.createElement(Tick2, null) : i + 1),
3163
+ /* @__PURE__ */ React10.createElement("span", { className: "alt-step-text" }, /* @__PURE__ */ React10.createElement("span", { className: "alt-sr" }, "Step ", i + 1, " of ", steps.length, ", ", word[state], ": "), /* @__PURE__ */ React10.createElement("span", { className: "alt-step-title" }, s.title), s.description && /* @__PURE__ */ React10.createElement("span", { className: "alt-step-desc" }, s.description))
3164
+ ), i < steps.length - 1 && /* @__PURE__ */ React10.createElement("span", { className: "alt-step-line", "aria-hidden": "true", "data-done": i < current ? "" : void 0 }));
3165
+ })), /* @__PURE__ */ React10.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said));
2891
3166
  }
2892
3167
 
2893
3168
  // project/components/src/empty.tsx
2894
- var React10 = __toESM(require("react"), 1);
3169
+ var React11 = __toESM(require("react"), 1);
2895
3170
  function EmptyState({
2896
3171
  icon: icon2,
2897
3172
  title,
@@ -2905,11 +3180,11 @@ function EmptyState({
2905
3180
  children,
2906
3181
  ...rest
2907
3182
  }) {
2908
- const id = React10.useId();
3183
+ const id = React11.useId();
2909
3184
  const H = `h${headingLevel}`;
2910
3185
  const words = typeof announce === "string" ? announce : announce && typeof title === "string" ? title : "";
2911
- const [said, setSaid] = React10.useState("");
2912
- React10.useEffect(() => {
3186
+ const [said, setSaid] = React11.useState("");
3187
+ React11.useEffect(() => {
2913
3188
  if (!words) {
2914
3189
  setSaid("");
2915
3190
  return;
@@ -2917,7 +3192,7 @@ function EmptyState({
2917
3192
  const t = setTimeout(() => setSaid(words), 100);
2918
3193
  return () => clearTimeout(t);
2919
3194
  }, [words]);
2920
- return /* @__PURE__ */ React10.createElement(
3195
+ return /* @__PURE__ */ React11.createElement(
2921
3196
  "section",
2922
3197
  {
2923
3198
  className: cx("alt-empty", className),
@@ -2926,17 +3201,17 @@ function EmptyState({
2926
3201
  "aria-describedby": description ? `${id}-d` : void 0,
2927
3202
  ...rest
2928
3203
  },
2929
- icon2 && /* @__PURE__ */ React10.createElement("span", { className: "alt-empty-icon", "aria-hidden": "true" }, icon2),
2930
- /* @__PURE__ */ React10.createElement(H, { id: `${id}-t`, className: "alt-empty-title" }, title),
2931
- description && /* @__PURE__ */ React10.createElement("p", { id: `${id}-d`, className: "alt-empty-desc" }, description),
3204
+ icon2 && /* @__PURE__ */ React11.createElement("span", { className: "alt-empty-icon", "aria-hidden": "true" }, icon2),
3205
+ /* @__PURE__ */ React11.createElement(H, { id: `${id}-t`, className: "alt-empty-title" }, title),
3206
+ description && /* @__PURE__ */ React11.createElement("p", { id: `${id}-d`, className: "alt-empty-desc" }, description),
2932
3207
  children,
2933
- (action || secondary) && /* @__PURE__ */ React10.createElement("div", { className: "alt-empty-actions" }, action, secondary),
2934
- announce && /* @__PURE__ */ React10.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said)
3208
+ (action || secondary) && /* @__PURE__ */ React11.createElement("div", { className: "alt-empty-actions" }, action, secondary),
3209
+ announce && /* @__PURE__ */ React11.createElement("span", { className: "alt-sr", "aria-live": "polite" }, said)
2935
3210
  );
2936
3211
  }
2937
3212
 
2938
3213
  // project/components/src/collections.tsx
2939
- var React11 = __toESM(require("react"), 1);
3214
+ var React12 = __toESM(require("react"), 1);
2940
3215
  var dropSnapshots = /* @__PURE__ */ new WeakMap();
2941
3216
  var ms2 = (cs, name, fallback) => parseFloat(cs.getPropertyValue(name)) || fallback;
2942
3217
  function pagePlace(el) {
@@ -2958,7 +3233,7 @@ function placeIn(el, host) {
2958
3233
  return { x: a.x - b.x, y: a.y - b.y };
2959
3234
  }
2960
3235
  function useCarry(host, selector, attr, durToken = "--dur-travel-3") {
2961
- const prev = React11.useRef(null);
3236
+ const prev = React12.useRef(null);
2962
3237
  useIsoLayoutEffect(() => {
2963
3238
  const root = host.current;
2964
3239
  if (!root) return;
@@ -2987,12 +3262,12 @@ var moveItem = (arr, from, to) => {
2987
3262
  a.splice(to, 0, x);
2988
3263
  return a;
2989
3264
  };
2990
- var Table = React11.forwardRef(function Table2({ maxHeight, underlay, className, children, ...rest }, ref) {
2991
- const wrap = React11.useRef(null);
2992
- const table = React11.useRef(null);
2993
- React11.useImperativeHandle(ref, () => table.current);
2994
- const [edges, setEdges] = React11.useState({ top: false, bottom: false });
2995
- const measure = React11.useCallback(() => {
3265
+ var Table = React12.forwardRef(function Table2({ maxHeight, underlay, className, children, ...rest }, ref) {
3266
+ const wrap = React12.useRef(null);
3267
+ const table = React12.useRef(null);
3268
+ React12.useImperativeHandle(ref, () => table.current);
3269
+ const [edges, setEdges] = React12.useState({ top: false, bottom: false });
3270
+ const measure = React12.useCallback(() => {
2996
3271
  const el = wrap.current;
2997
3272
  if (!el) return;
2998
3273
  const top = el.scrollTop > 1, bottom = el.scrollTop + el.clientHeight < el.scrollHeight - 1;
@@ -3013,7 +3288,7 @@ var Table = React11.forwardRef(function Table2({ maxHeight, underlay, className,
3013
3288
  }, [measure]);
3014
3289
  useCarry(table, "tbody > tr[data-row]", "data-row");
3015
3290
  const scrolls = maxHeight !== void 0;
3016
- return /* @__PURE__ */ React11.createElement(
3291
+ return /* @__PURE__ */ React12.createElement(
3017
3292
  "div",
3018
3293
  {
3019
3294
  ref: wrap,
@@ -3025,27 +3300,27 @@ var Table = React11.forwardRef(function Table2({ maxHeight, underlay, className,
3025
3300
  ...scrolls ? { tabIndex: 0, role: "region", "aria-label": rest["aria-label"] } : {}
3026
3301
  },
3027
3302
  underlay,
3028
- /* @__PURE__ */ React11.createElement("table", { ref: table, className: cx("alt-table", className), ...rest }, children)
3303
+ /* @__PURE__ */ React12.createElement("table", { ref: table, className: cx("alt-table", className), ...rest }, children)
3029
3304
  );
3030
3305
  });
3031
- var TableHeader = ({ className, ...p }) => /* @__PURE__ */ React11.createElement("thead", { className: cx("alt-table-head", className), ...p });
3032
- var TableBody = React11.forwardRef(function TableBody2({ className, ...p }, ref) {
3033
- return /* @__PURE__ */ React11.createElement("tbody", { ref, className: cx("alt-table-body", className), ...p });
3306
+ var TableHeader = ({ className, ...p }) => /* @__PURE__ */ React12.createElement("thead", { className: cx("alt-table-head", className), ...p });
3307
+ var TableBody = React12.forwardRef(function TableBody2({ className, ...p }, ref) {
3308
+ return /* @__PURE__ */ React12.createElement("tbody", { ref, className: cx("alt-table-body", className), ...p });
3034
3309
  });
3035
- var TableFooter = ({ className, ...p }) => /* @__PURE__ */ React11.createElement("tfoot", { className: cx("alt-table-foot", className), ...p });
3036
- var TableCaption = ({ className, ...p }) => /* @__PURE__ */ React11.createElement("caption", { className: cx("alt-table-caption", className), ...p });
3037
- var TableRow = React11.forwardRef(function TableRow2({ rowId, selected, interactive, relevance, settle, held, className, style, ...rest }, ref) {
3038
- const [glow, setGlow] = React11.useState(void 0);
3039
- const [delay, setDelay] = React11.useState(0);
3040
- const first = React11.useRef(true);
3041
- React11.useEffect(() => {
3310
+ var TableFooter = ({ className, ...p }) => /* @__PURE__ */ React12.createElement("tfoot", { className: cx("alt-table-foot", className), ...p });
3311
+ var TableCaption = ({ className, ...p }) => /* @__PURE__ */ React12.createElement("caption", { className: cx("alt-table-caption", className), ...p });
3312
+ var TableRow = React12.forwardRef(function TableRow2({ rowId, selected, interactive, relevance, settle, held, className, style, ...rest }, ref) {
3313
+ const [glow, setGlow] = React12.useState(void 0);
3314
+ const [delay, setDelay] = React12.useState(0);
3315
+ const first = React12.useRef(true);
3316
+ React12.useEffect(() => {
3042
3317
  const wasFirst = first.current;
3043
3318
  first.current = false;
3044
3319
  if (settle === void 0 || settle === null || settle === false || wasFirst && settle !== true) return;
3045
3320
  setDelay(riseDelay());
3046
3321
  setGlow((g) => g === "a" ? "b" : "a");
3047
3322
  }, [settle]);
3048
- return /* @__PURE__ */ React11.createElement(
3323
+ return /* @__PURE__ */ React12.createElement(
3049
3324
  "tr",
3050
3325
  {
3051
3326
  ref,
@@ -3061,15 +3336,28 @@ var TableRow = React11.forwardRef(function TableRow2({ rowId, selected, interact
3061
3336
  }
3062
3337
  );
3063
3338
  });
3064
- var SortIcon = () => /* @__PURE__ */ React11.createElement("svg", { className: "alt-table-sort-icon", width: "14", height: "14", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: 1.75, strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React11.createElement("path", { d: "M6 15l6-6 6 6" }));
3339
+ var SortIcon = () => /* @__PURE__ */ React12.createElement("svg", { className: "alt-table-sort-icon", width: "14", height: "14", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: 1.75, strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true" }, /* @__PURE__ */ React12.createElement("path", { d: "M6 15l6-6 6 6" }));
3065
3340
  function TableHead({ align, sort, onSort, className, children, ...rest }) {
3066
- return /* @__PURE__ */ React11.createElement("th", { scope: "col", className: cx("alt-th", className), "data-align": align, "aria-sort": onSort ? sort ?? "none" : void 0, ...rest }, onSort ? /* @__PURE__ */ React11.createElement("button", { type: "button", className: "alt-table-sort", "data-sort": sort ?? "none", onClick: onSort }, children, /* @__PURE__ */ React11.createElement(SortIcon, null)) : children);
3341
+ return /* @__PURE__ */ React12.createElement("th", { scope: "col", className: cx("alt-th", className), "data-align": align, "aria-sort": onSort ? sort ?? "none" : void 0, ...rest }, onSort ? /* @__PURE__ */ React12.createElement("button", { type: "button", className: "alt-table-sort", "data-sort": sort ?? "none", onClick: onSort }, children, /* @__PURE__ */ React12.createElement(SortIcon, null)) : children);
3067
3342
  }
3068
3343
  function TableCell({ align, className, ...rest }) {
3069
- return /* @__PURE__ */ React11.createElement("td", { className: cx("alt-td", className), "data-align": align, ...rest });
3070
- }
3071
- var GripIcon = () => /* @__PURE__ */ React11.createElement("svg", { width: "12", height: "16", viewBox: "0 0 12 16", fill: "currentColor", "aria-hidden": "true" }, /* @__PURE__ */ React11.createElement("circle", { cx: "3", cy: "3", r: "1.3" }), /* @__PURE__ */ React11.createElement("circle", { cx: "9", cy: "3", r: "1.3" }), /* @__PURE__ */ React11.createElement("circle", { cx: "3", cy: "8", r: "1.3" }), /* @__PURE__ */ React11.createElement("circle", { cx: "9", cy: "8", r: "1.3" }), /* @__PURE__ */ React11.createElement("circle", { cx: "3", cy: "13", r: "1.3" }), /* @__PURE__ */ React11.createElement("circle", { cx: "9", cy: "13", r: "1.3" }));
3072
- function DataTable({
3344
+ return /* @__PURE__ */ React12.createElement("td", { className: cx("alt-td", className), "data-align": align, ...rest });
3345
+ }
3346
+ var GripIcon = () => /* @__PURE__ */ React12.createElement("svg", { width: "12", height: "16", viewBox: "0 0 12 16", fill: "currentColor", "aria-hidden": "true" }, /* @__PURE__ */ React12.createElement("circle", { cx: "3", cy: "3", r: "1.3" }), /* @__PURE__ */ React12.createElement("circle", { cx: "9", cy: "3", r: "1.3" }), /* @__PURE__ */ React12.createElement("circle", { cx: "3", cy: "8", r: "1.3" }), /* @__PURE__ */ React12.createElement("circle", { cx: "9", cy: "8", r: "1.3" }), /* @__PURE__ */ React12.createElement("circle", { cx: "3", cy: "13", r: "1.3" }), /* @__PURE__ */ React12.createElement("circle", { cx: "9", cy: "13", r: "1.3" }));
3347
+ function DataTable({ skeleton, ...props }) {
3348
+ const missing = skeleton !== false && props.rows === void 0;
3349
+ useReportWaiting(missing || skeleton !== false && isPromise(props.rows));
3350
+ const arrival = useArrival(missing);
3351
+ if (!useHasWaited(missing || isPromise(props.rows))) return /* @__PURE__ */ React12.createElement(DataTableFace, { ...props, rows: props.rows ?? [] });
3352
+ const { lines = 5 } = hint(skeleton);
3353
+ const { columns, selectable, toolbar, maxHeight, className } = props;
3354
+ return /* @__PURE__ */ React12.createElement(Await, { shape: "none", enabled: skeleton !== false, imprint: /* @__PURE__ */ React12.createElement("div", { className: cx("alt-data-table", className) }, (selectable || toolbar) && /* @__PURE__ */ React12.createElement("div", { className: "alt-table-tools" }, toolbar && /* @__PURE__ */ React12.createElement("div", { className: "alt-table-tools-end" }, toolbar)), /* @__PURE__ */ React12.createElement(Table, { maxHeight, "aria-label": props["aria-label"] }, /* @__PURE__ */ React12.createElement(TableHeader, null, /* @__PURE__ */ React12.createElement(TableRow, null, selectable && /* @__PURE__ */ React12.createElement(TableHead, { className: "alt-th-check" }, /* @__PURE__ */ React12.createElement("span", { className: "alt-skeleton alt-check-imprint" })), columns.map((c) => /* @__PURE__ */ React12.createElement(TableHead, { key: c.key, align: c.align, style: { width: c.width } }, c.header)))), /* @__PURE__ */ React12.createElement(TableBody, null, Array.from({ length: lines }, (_, i) => /* @__PURE__ */ React12.createElement(TableRow, { key: i }, selectable && /* @__PURE__ */ React12.createElement(TableCell, { className: "alt-td-check" }, /* @__PURE__ */ React12.createElement("span", { className: "alt-skeleton alt-check-imprint" })), columns.map((c, ci) => /* @__PURE__ */ React12.createElement(TableCell, { key: c.key, align: c.align }, /* @__PURE__ */ React12.createElement("span", { className: "alt-skeleton alt-cell-imprint", "data-shape": "text", style: { width: CELL_WIDTHS[(i + ci) % CELL_WIDTHS.length], ["--i"]: i } })))))))) }, /* @__PURE__ */ React12.createElement(Arrive, { when: arrival }, /* @__PURE__ */ React12.createElement(DataTableLanded, { ...props })));
3355
+ }
3356
+ var CELL_WIDTHS = ["72%", "54%", "86%", "63%", "78%"];
3357
+ function DataTableLanded(props) {
3358
+ return /* @__PURE__ */ React12.createElement(DataTableFace, { ...props, rows: readPromised(props.rows) ?? [] });
3359
+ }
3360
+ function DataTableFace({
3073
3361
  columns,
3074
3362
  rows,
3075
3363
  getRowId,
@@ -3093,11 +3381,11 @@ function DataTable({
3093
3381
  }) {
3094
3382
  const [sel, setSel] = useControllable(selected, defaultSelected, onSelectedChange);
3095
3383
  const [srt, setSrt] = useControllable(sort, defaultSort, onSortChange);
3096
- const [said, setSaid] = React11.useState("");
3097
- const table = React11.useRef(null);
3098
- const body = React11.useRef(null);
3384
+ const [said, setSaid] = React12.useState("");
3385
+ const table = React12.useRef(null);
3386
+ const body = React12.useRef(null);
3099
3387
  const name = (r) => getRowLabel?.(r) ?? getRowId(r);
3100
- const view = React11.useMemo(() => {
3388
+ const view = React12.useMemo(() => {
3101
3389
  const col = srt && columns.find((c) => c.key === srt.key);
3102
3390
  if (!srt || !col?.sortValue) return rows;
3103
3391
  const d = srt.direction === "descending" ? -1 : 1;
@@ -3114,9 +3402,9 @@ function DataTable({
3114
3402
  setSaid(next ? `Sorted by ${typeof c.header === "string" ? c.header : c.key}, ${next.direction}.` : "Sort cleared.");
3115
3403
  };
3116
3404
  const toggle = (id, on) => setSel(on ? [...sel.filter((x) => x !== id), id] : sel.filter((x) => x !== id));
3117
- const start = React11.useRef(null);
3118
- const [drag, setDrag] = React11.useState(null);
3119
- const [held, setHeld] = React11.useState(null);
3405
+ const start = React12.useRef(null);
3406
+ const [drag, setDrag] = React12.useState(null);
3407
+ const [held, setHeld] = React12.useState(null);
3120
3408
  const rowEls = () => Array.from(body.current?.querySelectorAll("tr[data-row]") ?? []);
3121
3409
  const snapshot = (at) => {
3122
3410
  if (!table.current) return;
@@ -3186,24 +3474,24 @@ function DataTable({
3186
3474
  setSaid(`Move cancelled; ${name(view[index])} is back at position ${held.origin + 1}.`);
3187
3475
  }
3188
3476
  };
3189
- React11.useEffect(() => {
3477
+ React12.useEffect(() => {
3190
3478
  if (!movable) setHeld(null);
3191
3479
  }, [movable]);
3192
3480
  const s = start.current;
3193
3481
  const h = drag && s ? s.hs[drag.from] : 0;
3194
3482
  const slotTop = drag && s ? drag.to <= drag.from ? s.tops[drag.to] : s.tops[drag.to] + s.hs[drag.to] - s.hs[drag.from] : 0;
3195
3483
  const span = columns.length + (selectable ? 1 : 0) + (movable ? 1 : 0);
3196
- return /* @__PURE__ */ React11.createElement("div", { className: cx("alt-data-table", className) }, (selectable || toolbar) && /* @__PURE__ */ React11.createElement("div", { className: "alt-table-tools" }, sel.length > 0 && /* @__PURE__ */ React11.createElement("div", { className: "alt-table-selection" }, /* @__PURE__ */ React11.createElement(Badge, { variant: "count", tone: "accent", "aria-hidden": "true" }, sel.length), /* @__PURE__ */ React11.createElement("span", null, "selected"), actions?.(sel), /* @__PURE__ */ React11.createElement(Button, { size: "sm", variant: "ghost", onClick: () => setSel([]) }, "Clear")), toolbar && /* @__PURE__ */ React11.createElement("div", { className: "alt-table-tools-end" }, toolbar)), /* @__PURE__ */ React11.createElement(
3484
+ return /* @__PURE__ */ React12.createElement("div", { className: cx("alt-data-table", className) }, (selectable || toolbar) && /* @__PURE__ */ React12.createElement("div", { className: "alt-table-tools" }, sel.length > 0 && /* @__PURE__ */ React12.createElement("div", { className: "alt-table-selection" }, /* @__PURE__ */ React12.createElement(Badge, { variant: "count", tone: "accent", "aria-hidden": "true" }, sel.length), /* @__PURE__ */ React12.createElement("span", null, "selected"), actions?.(sel), /* @__PURE__ */ React12.createElement(Button, { size: "sm", variant: "ghost", onClick: () => setSel([]) }, "Clear")), toolbar && /* @__PURE__ */ React12.createElement("div", { className: "alt-table-tools-end" }, toolbar)), /* @__PURE__ */ React12.createElement(
3197
3485
  Table,
3198
3486
  {
3199
3487
  ref: table,
3200
3488
  maxHeight,
3201
3489
  "aria-label": rest["aria-label"],
3202
3490
  "data-dragging": drag ? "" : void 0,
3203
- underlay: drag && s ? /* @__PURE__ */ React11.createElement("span", { className: "alt-table-slot", "aria-hidden": "true", style: { top: slotTop + (table.current?.offsetTop ?? 0), height: h } }) : null
3491
+ underlay: drag && s ? /* @__PURE__ */ React12.createElement("span", { className: "alt-table-slot", "aria-hidden": "true", style: { top: slotTop + (table.current?.offsetTop ?? 0), height: h } }) : null
3204
3492
  },
3205
- /* @__PURE__ */ React11.createElement(TableHeader, null, /* @__PURE__ */ React11.createElement(TableRow, null, movable && /* @__PURE__ */ React11.createElement(TableHead, { className: "alt-th-grip" }, /* @__PURE__ */ React11.createElement("span", { className: "alt-sr" }, "Move")), selectable && /* @__PURE__ */ React11.createElement(TableHead, { className: "alt-th-check" }, /* @__PURE__ */ React11.createElement(Checkbox, { "aria-label": "Select all rows", checked: all, indeterminate: some, onCheckedChange: (on) => setSel(on ? Array.from(/* @__PURE__ */ new Set([...sel, ...ids])) : sel.filter((x) => !ids.includes(x))) })), columns.map((c) => /* @__PURE__ */ React11.createElement(TableHead, { key: c.key, align: c.align, style: { width: c.width }, sort: srt?.key === c.key ? srt.direction : "none", onSort: c.sortValue ? () => cycle(c) : void 0 }, c.header)))),
3206
- /* @__PURE__ */ React11.createElement(TableBody, { ref: body }, !view.length && /* @__PURE__ */ React11.createElement("tr", null, /* @__PURE__ */ React11.createElement("td", { className: "alt-td alt-table-empty", colSpan: span }, empty)), view.map((r, i) => {
3493
+ /* @__PURE__ */ React12.createElement(TableHeader, null, /* @__PURE__ */ React12.createElement(TableRow, null, movable && /* @__PURE__ */ React12.createElement(TableHead, { className: "alt-th-grip" }, /* @__PURE__ */ React12.createElement("span", { className: "alt-sr" }, "Move")), selectable && /* @__PURE__ */ React12.createElement(TableHead, { className: "alt-th-check" }, /* @__PURE__ */ React12.createElement(Checkbox, { "aria-label": "Select all rows", checked: all, indeterminate: some, onCheckedChange: (on) => setSel(on ? Array.from(/* @__PURE__ */ new Set([...sel, ...ids])) : sel.filter((x) => !ids.includes(x))) })), columns.map((c) => /* @__PURE__ */ React12.createElement(TableHead, { key: c.key, align: c.align, style: { width: c.width }, sort: srt?.key === c.key ? srt.direction : "none", onSort: c.sortValue ? () => cycle(c) : void 0 }, c.header)))),
3494
+ /* @__PURE__ */ React12.createElement(TableBody, { ref: body }, !view.length && /* @__PURE__ */ React12.createElement("tr", null, /* @__PURE__ */ React12.createElement("td", { className: "alt-td alt-table-empty", colSpan: span }, empty)), view.map((r, i) => {
3207
3495
  const id = ids[i];
3208
3496
  let shift = 0;
3209
3497
  if (drag && id !== drag.id && h) {
@@ -3211,7 +3499,7 @@ function DataTable({
3211
3499
  if (drag.to < drag.from && i >= drag.to && i < drag.from) shift = h;
3212
3500
  }
3213
3501
  const following = drag?.id === id;
3214
- return /* @__PURE__ */ React11.createElement(
3502
+ return /* @__PURE__ */ React12.createElement(
3215
3503
  TableRow,
3216
3504
  {
3217
3505
  key: id,
@@ -3226,7 +3514,7 @@ function DataTable({
3226
3514
  if (!e.target.closest("button, a, input, label, select, textarea")) onRowClick(r);
3227
3515
  } : void 0
3228
3516
  },
3229
- movable && /* @__PURE__ */ React11.createElement(TableCell, { className: "alt-td-grip" }, /* @__PURE__ */ React11.createElement(
3517
+ movable && /* @__PURE__ */ React12.createElement(TableCell, { className: "alt-td-grip" }, /* @__PURE__ */ React12.createElement(
3230
3518
  "button",
3231
3519
  {
3232
3520
  type: "button",
@@ -3242,18 +3530,18 @@ function DataTable({
3242
3530
  if (held?.id === id && !drag) setTimeout(() => setHeld((x) => x?.id === id && document.activeElement?.closest(`tr[data-row="${CSS.escape(id)}"]`) === null ? null : x), 0);
3243
3531
  }
3244
3532
  },
3245
- /* @__PURE__ */ React11.createElement(GripIcon, null)
3533
+ /* @__PURE__ */ React12.createElement(GripIcon, null)
3246
3534
  )),
3247
- selectable && /* @__PURE__ */ React11.createElement(TableCell, { className: "alt-td-check" }, /* @__PURE__ */ React11.createElement(Checkbox, { "aria-label": `Select ${name(r)}`, checked: chosen.has(id), onCheckedChange: (on) => toggle(id, on) })),
3535
+ selectable && /* @__PURE__ */ React12.createElement(TableCell, { className: "alt-td-check" }, /* @__PURE__ */ React12.createElement(Checkbox, { "aria-label": `Select ${name(r)}`, checked: chosen.has(id), onCheckedChange: (on) => toggle(id, on) })),
3248
3536
  columns.map((c, ci) => {
3249
3537
  const content = c.cell ? c.cell(r) : String(r[c.key] ?? "");
3250
- return /* @__PURE__ */ React11.createElement(TableCell, { key: c.key, align: c.align }, onRowClick && ci === 0 ? /* @__PURE__ */ React11.createElement("button", { type: "button", className: "alt-table-rowbtn", onClick: () => onRowClick(r) }, content) : content);
3538
+ return /* @__PURE__ */ React12.createElement(TableCell, { key: c.key, align: c.align }, onRowClick && ci === 0 ? /* @__PURE__ */ React12.createElement("button", { type: "button", className: "alt-table-rowbtn", onClick: () => onRowClick(r) }, content) : content);
3251
3539
  })
3252
3540
  );
3253
3541
  }))
3254
- ), /* @__PURE__ */ React11.createElement("span", { className: "alt-sr", "aria-live": "polite" }, selectable && sel.length ? `${sel.length} selected. ` : "", said));
3542
+ ), /* @__PURE__ */ React12.createElement("span", { className: "alt-sr", "aria-live": "polite" }, selectable && sel.length ? `${sel.length} selected. ` : "", said));
3255
3543
  }
3256
- var BoardCtx = React11.createContext(null);
3544
+ var BoardCtx = React12.createContext(null);
3257
3545
  function readBoard(root) {
3258
3546
  return Array.from(root.querySelectorAll("[data-board-col]")).map((col) => {
3259
3547
  const list = col.querySelector(".alt-board-list");
@@ -3300,18 +3588,18 @@ function plan(cols, id, cx2, cy, h) {
3300
3588
  }
3301
3589
  return { to: { column: tc.id, index }, shifts, slotTop, gap: tc.gap };
3302
3590
  }
3303
- var Board = React11.forwardRef(function Board2({ onMove, className, children, ...rest }, ref) {
3304
- const root = React11.useRef(null);
3305
- React11.useImperativeHandle(ref, () => root.current);
3306
- const hintId = React11.useId();
3307
- const [carry, setCarry] = React11.useState(null);
3308
- const [kb, setKb] = React11.useState(null);
3309
- const [landing, setLanding] = React11.useState(null);
3310
- const [said, setSaid] = React11.useState("");
3311
- const start = React11.useRef(null);
3312
- const dragged = React11.useRef(false);
3591
+ var Board = React12.forwardRef(function Board2({ onMove, className, children, ...rest }, ref) {
3592
+ const root = React12.useRef(null);
3593
+ React12.useImperativeHandle(ref, () => root.current);
3594
+ const hintId = React12.useId();
3595
+ const [carry, setCarry] = React12.useState(null);
3596
+ const [kb, setKb] = React12.useState(null);
3597
+ const [landing, setLanding] = React12.useState(null);
3598
+ const [said, setSaid] = React12.useState("");
3599
+ const start = React12.useRef(null);
3600
+ const dragged = React12.useRef(false);
3313
3601
  useCarry(root, "[data-board-card]", "data-board-card");
3314
- React11.useEffect(() => {
3602
+ React12.useEffect(() => {
3315
3603
  if (!landing) return;
3316
3604
  const t = setTimeout(() => setLanding(null), 450);
3317
3605
  return () => clearTimeout(t);
@@ -3440,17 +3728,17 @@ var Board = React11.forwardRef(function Board2({ onMove, className, children, ..
3440
3728
  return d;
3441
3729
  };
3442
3730
  const ctx = { carry, kb, landing, hintId, onPointerDown, onPointerMove, onPointerUp, onKeyDown, onBlur, swallowClick };
3443
- return /* @__PURE__ */ React11.createElement(BoardCtx.Provider, { value: ctx }, /* @__PURE__ */ React11.createElement("div", { ref: root, role: "group", "aria-label": rest["aria-label"] ?? "Board", className: cx("alt-board", className), "data-carrying": carry || kb ? "" : void 0, ...rest }, children, /* @__PURE__ */ React11.createElement("span", { id: hintId, className: "alt-sr" }, "Press Space to pick up. While holding a card, use the arrow keys to move it, Space to drop it, Escape to cancel."), /* @__PURE__ */ React11.createElement("span", { className: "alt-sr", "aria-live": "assertive" }, said)));
3731
+ return /* @__PURE__ */ React12.createElement(BoardCtx.Provider, { value: ctx }, /* @__PURE__ */ React12.createElement("div", { ref: root, role: "group", "aria-label": rest["aria-label"] ?? "Board", className: cx("alt-board", className), "data-carrying": carry || kb ? "" : void 0, ...rest }, children, /* @__PURE__ */ React12.createElement("span", { id: hintId, className: "alt-sr" }, "Press Space to pick up. While holding a card, use the arrow keys to move it, Space to drop it, Escape to cancel."), /* @__PURE__ */ React12.createElement("span", { className: "alt-sr", "aria-live": "assertive" }, said)));
3444
3732
  });
3445
3733
  function BoardColumn({ id, title, collapsed, defaultCollapsed = false, onCollapsedChange, collapsible, className, children, ...rest }) {
3446
- const ctx = React11.useContext(BoardCtx);
3734
+ const ctx = React12.useContext(BoardCtx);
3447
3735
  const [isCollapsed, setCollapsed] = useControllable(collapsed, defaultCollapsed, onCollapsedChange);
3448
- const count = React11.Children.toArray(children).filter(React11.isValidElement).length;
3736
+ const count = React12.Children.toArray(children).filter(React12.isValidElement).length;
3449
3737
  const label = typeof title === "string" ? title : id;
3450
3738
  const carry = ctx?.carry;
3451
3739
  const over = carry ? carry.to.column === id : ctx?.kb?.at.column === id;
3452
3740
  const receiving = !!carry && carry.to.column === id && carry.from.column !== id && !isCollapsed;
3453
- return /* @__PURE__ */ React11.createElement(
3741
+ return /* @__PURE__ */ React12.createElement(
3454
3742
  "section",
3455
3743
  {
3456
3744
  className: cx("alt-board-col", className),
@@ -3461,7 +3749,7 @@ function BoardColumn({ id, title, collapsed, defaultCollapsed = false, onCollaps
3461
3749
  "data-over": over ? "" : void 0,
3462
3750
  ...rest
3463
3751
  },
3464
- /* @__PURE__ */ React11.createElement("header", { className: "alt-board-head" }, /* @__PURE__ */ React11.createElement("h3", { className: "alt-board-title" }, title), /* @__PURE__ */ React11.createElement("span", { className: "alt-board-count", "aria-label": `${count} ${count === 1 ? "card" : "cards"}` }, count), collapsible && /* @__PURE__ */ React11.createElement(
3752
+ /* @__PURE__ */ React12.createElement("header", { className: "alt-board-head" }, /* @__PURE__ */ React12.createElement("h3", { className: "alt-board-title" }, title), /* @__PURE__ */ React12.createElement("span", { className: "alt-board-count", "aria-label": `${count} ${count === 1 ? "card" : "cards"}` }, count), collapsible && /* @__PURE__ */ React12.createElement(
3465
3753
  Button,
3466
3754
  {
3467
3755
  variant: "ghost",
@@ -3473,20 +3761,20 @@ function BoardColumn({ id, title, collapsed, defaultCollapsed = false, onCollaps
3473
3761
  "data-collapsed": isCollapsed ? "" : void 0,
3474
3762
  onClick: () => setCollapsed(!isCollapsed)
3475
3763
  },
3476
- /* @__PURE__ */ React11.createElement(Icons.ChevronDown, null)
3764
+ /* @__PURE__ */ React12.createElement(Icons.ChevronDown, null)
3477
3765
  )),
3478
- isCollapsed ? /* @__PURE__ */ React11.createElement(Pile, { count: Math.max(count, 1), className: "alt-board-pile" }, /* @__PURE__ */ React11.createElement("div", { className: "alt-board-pile-face" }, /* @__PURE__ */ React11.createElement("b", null, title), /* @__PURE__ */ React11.createElement("span", null, count ? `${count} ${count === 1 ? "card" : "cards"}` : "No cards"))) : /* @__PURE__ */ React11.createElement("div", { className: "alt-board-list", style: receiving ? { paddingBottom: carry.h + carry.gap } : void 0 }, carry && carry.to.column === id && /* @__PURE__ */ React11.createElement("span", { className: "alt-board-slot", "aria-hidden": "true", style: { top: carry.slotTop, height: carry.h } }), children, !count && !carry && /* @__PURE__ */ React11.createElement("div", { className: "alt-board-empty" }, "No cards"))
3766
+ isCollapsed ? /* @__PURE__ */ React12.createElement(Pile, { count: Math.max(count, 1), className: "alt-board-pile" }, /* @__PURE__ */ React12.createElement("div", { className: "alt-board-pile-face" }, /* @__PURE__ */ React12.createElement("b", null, title), /* @__PURE__ */ React12.createElement("span", null, count ? `${count} ${count === 1 ? "card" : "cards"}` : "No cards"))) : /* @__PURE__ */ React12.createElement("div", { className: "alt-board-list", style: receiving ? { paddingBottom: carry.h + carry.gap } : void 0 }, carry && carry.to.column === id && /* @__PURE__ */ React12.createElement("span", { className: "alt-board-slot", "aria-hidden": "true", style: { top: carry.slotTop, height: carry.h } }), children, !count && !carry && /* @__PURE__ */ React12.createElement("div", { className: "alt-board-empty" }, "No cards"))
3479
3767
  );
3480
3768
  }
3481
- var BoardCard = React11.forwardRef(function BoardCard2({ id, label, heldBy, settle, className, style, onClickCapture, children, ...rest }, ref) {
3482
- const ctx = React11.useContext(BoardCtx);
3769
+ var BoardCard = React12.forwardRef(function BoardCard2({ id, label, heldBy, settle, className, style, onClickCapture, children, ...rest }, ref) {
3770
+ const ctx = React12.useContext(BoardCtx);
3483
3771
  const depth = useDepth({ heldBy, settle });
3484
3772
  const carry = ctx?.carry;
3485
3773
  const following = carry?.id === id;
3486
3774
  const carried = following || ctx?.kb?.id === id;
3487
3775
  const shift = carry?.shifts[id];
3488
3776
  const transform = following ? `translate(${carry.dx}px, ${carry.dy}px)` : shift ? `translateY(${shift}px)` : void 0;
3489
- return /* @__PURE__ */ React11.createElement(
3777
+ return /* @__PURE__ */ React12.createElement(
3490
3778
  "div",
3491
3779
  {
3492
3780
  ref,