@vllnt/ui 0.2.1-canary.0aaaad2 → 0.2.1-canary.0cc4e50

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.
Files changed (112) hide show
  1. package/CHANGELOG.md +3 -0
  2. package/dist/components/activity-heatmap/activity-heatmap.js +2 -1
  3. package/dist/components/activity-log/activity-log.js +1 -1
  4. package/dist/components/ai-artifact/ai-artifact.js +8 -8
  5. package/dist/components/ai-chat-input/ai-chat-input.js +1 -1
  6. package/dist/components/ai-message-bubble/ai-message-bubble.js +1 -1
  7. package/dist/components/ai-sidebar/ai-sidebar.js +4 -4
  8. package/dist/components/ai-tool-call-display/ai-tool-call-display.js +1 -1
  9. package/dist/components/animated-text/animated-text.js +6 -3
  10. package/dist/components/annotation/annotation.js +1 -1
  11. package/dist/components/auto-reload/auto-reload.js +1 -1
  12. package/dist/components/avatar-group/avatar-group.js +1 -1
  13. package/dist/components/blog-card/blog-card.js +4 -2
  14. package/dist/components/bottom-activity-strip/bottom-activity-strip.js +2 -2
  15. package/dist/components/candlestick-chart/candlestick-chart.js +2 -1
  16. package/dist/components/canvas-shell/canvas-foundation-demo.js +1 -1
  17. package/dist/components/carousel/carousel.js +14 -6
  18. package/dist/components/category-filter/category-filter.js +1 -1
  19. package/dist/components/chat-dock-section/chat-dock-section.js +1 -1
  20. package/dist/components/checklist/checklist.js +35 -7
  21. package/dist/components/checklist/index.js +8 -2
  22. package/dist/components/chronological-timeline/chronological-timeline.js +2 -2
  23. package/dist/components/code-playground/code-playground.js +3 -2
  24. package/dist/components/combobox/combobox.js +1 -6
  25. package/dist/components/comment-pin/comment-pin.js +2 -2
  26. package/dist/components/comparison/comparison.js +2 -1
  27. package/dist/components/completion-dialog/completion-dialog.js +19 -11
  28. package/dist/components/connector-edge/connector-edge.js +1 -1
  29. package/dist/components/content-intro/content-intro.js +18 -15
  30. package/dist/components/conversation-thread/conversation-thread.js +4 -4
  31. package/dist/components/countdown-timer/countdown-timer.js +1 -1
  32. package/dist/components/data-table/data-table.js +1 -1
  33. package/dist/components/date-picker/date-picker.js +1 -6
  34. package/dist/components/exercise/exercise.js +11 -3
  35. package/dist/components/faq/faq.js +6 -2
  36. package/dist/components/file-upload/file-upload.js +1 -6
  37. package/dist/components/filter-bar/filter-bar.js +7 -7
  38. package/dist/components/flashcard/flashcard.js +1 -1
  39. package/dist/components/floating-toolbar/floating-toolbar.js +2 -2
  40. package/dist/components/form/form.js +1 -1
  41. package/dist/components/gantt-chart/gantt-chart.js +8 -7
  42. package/dist/components/globe-3d/globe-3d.js +16 -4
  43. package/dist/components/horizontal-scroll-row/horizontal-scroll-row.js +2 -1
  44. package/dist/components/inline-input/inline-input.js +1 -1
  45. package/dist/components/interactive-timeline/interactive-timeline.js +8 -5
  46. package/dist/components/jarvis-dock/jarvis-dock.js +2 -2
  47. package/dist/components/key-concept/key-concept.js +2 -1
  48. package/dist/components/keyboard-shortcuts-help/keyboard-shortcuts-help.js +2 -1
  49. package/dist/components/knowledge-check/knowledge-check.js +2 -2
  50. package/dist/components/lang-provider/lang-provider.js +3 -3
  51. package/dist/components/learning-objectives/learning-objectives.js +2 -1
  52. package/dist/components/live-feed/live-feed.js +2 -2
  53. package/dist/components/map-2d/map-2d.js +1 -1
  54. package/dist/components/map-timeline/map-timeline.js +5 -5
  55. package/dist/components/market-treemap/market-treemap.js +2 -2
  56. package/dist/components/mdx-content/mdx-content.js +17 -8
  57. package/dist/components/metric-gauge/metric-gauge.js +1 -1
  58. package/dist/components/model-selector/model-selector.js +1 -1
  59. package/dist/components/multi-select/multi-select.js +1 -1
  60. package/dist/components/navbar-saas/navbar-saas.js +5 -5
  61. package/dist/components/number-input/number-input.js +1 -1
  62. package/dist/components/number-ticker/number-ticker.js +1 -1
  63. package/dist/components/object-card/object-card.js +1 -1
  64. package/dist/components/order-book/order-book.js +2 -2
  65. package/dist/components/overview-board/overview-board.js +1 -1
  66. package/dist/components/policy-delivery-panel/policy-delivery-panel.js +2 -2
  67. package/dist/components/profile-section/profile-section.js +2 -1
  68. package/dist/components/progress-card/progress-card.js +1 -1
  69. package/dist/components/progress-tracker/progress-tracker.js +17 -9
  70. package/dist/components/prompt-templates/prompt-templates.js +2 -2
  71. package/dist/components/quiz/quiz.js +3 -2
  72. package/dist/components/relationship-inspector/relationship-inspector.js +2 -2
  73. package/dist/components/routing-assignment-panel/routing-assignment-panel.js +2 -2
  74. package/dist/components/run-timeline/run-timeline.js +2 -2
  75. package/dist/components/scope-selector/scope-selector.js +1 -1
  76. package/dist/components/search-dialog/search-dialog.js +484 -51
  77. package/dist/components/share-dialog/share-dialog.js +2 -2
  78. package/dist/components/share-section/share-section.js +2 -1
  79. package/dist/components/sidebar/sidebar.js +30 -25
  80. package/dist/components/sidebar-toggle/sidebar-toggle.js +1 -1
  81. package/dist/components/slideshow/slideshow.js +3 -2
  82. package/dist/components/social-fab/social-fab.js +10 -10
  83. package/dist/components/spinner/spinner.js +1 -1
  84. package/dist/components/spinner/unicode-spinner.js +4 -2
  85. package/dist/components/stat-card/stat-card.js +2 -2
  86. package/dist/components/status-board/status-board.js +13 -6
  87. package/dist/components/step-by-step/step-by-step.js +2 -1
  88. package/dist/components/table-of-contents/table-of-contents.js +5 -2
  89. package/dist/components/table-of-contents-panel/table-of-contents-panel.js +3 -1
  90. package/dist/components/tabs/tabs.js +26 -8
  91. package/dist/components/tags-input/tags-input.js +11 -3
  92. package/dist/components/terminal/terminal.js +11 -3
  93. package/dist/components/theme-toggle/theme-toggle.js +2 -2
  94. package/dist/components/thinking-block/thinking-block.js +2 -2
  95. package/dist/components/ticker-tape/ticker-tape.js +1 -1
  96. package/dist/components/timeline-scrubber/timeline-scrubber.js +2 -2
  97. package/dist/components/tldr-section/tldr-section.js +9 -7
  98. package/dist/components/tour/tour.js +1 -1
  99. package/dist/components/transaction-list/transaction-list.js +2 -2
  100. package/dist/components/tutorial-card/tutorial-card.js +1 -1
  101. package/dist/components/tutorial-complete/tutorial-complete.js +8 -6
  102. package/dist/components/tutorial-filters/tutorial-filters.js +2 -2
  103. package/dist/components/tutorial-intro-content/tutorial-intro-content.js +5 -5
  104. package/dist/components/tutorial-mdx/tutorial-mdx.js +6 -6
  105. package/dist/components/usage-breakdown/usage-breakdown.js +1 -1
  106. package/dist/components/viewport-bookmarks/viewport-bookmarks.js +2 -2
  107. package/dist/components/watchlist/watchlist.js +2 -1
  108. package/dist/components/world-breadcrumbs/world-breadcrumbs.js +2 -2
  109. package/dist/components/world-clock-bar/world-clock-bar.js +5 -4
  110. package/dist/components/zoom-hud/zoom-hud.js +1 -1
  111. package/dist/index.d.ts +113 -29
  112. package/package.json +3 -3
@@ -2,6 +2,7 @@ import { jsx } from "react/jsx-runtime";
2
2
  import { evaluate } from "@mdx-js/mdx";
3
3
  import * as runtime from "react/jsx-runtime";
4
4
  import ReactMarkdown from "react-markdown";
5
+ import remarkGfm from "remark-gfm";
5
6
  import { CodeBlock } from "../code-block/code-block";
6
7
  const MDXComponents = {
7
8
  a: ({ children, href, ...props }) => /* @__PURE__ */ jsx(
@@ -16,7 +17,7 @@ const MDXComponents = {
16
17
  blockquote: ({ children, ...props }) => /* @__PURE__ */ jsx(
17
18
  "blockquote",
18
19
  {
19
- className: "border-l-4 border-primary pl-4 italic text-muted-foreground my-6 py-2 text-sm",
20
+ className: "border-l border-primary pl-4 italic text-muted-foreground my-6 py-2 text-sm",
20
21
  ...props,
21
22
  children
22
23
  }
@@ -37,9 +38,9 @@ const MDXComponents = {
37
38
  );
38
39
  },
39
40
  em: ({ children, ...props }) => /* @__PURE__ */ jsx("em", { className: "italic", ...props, children }),
40
- h1: ({ children, ...props }) => /* @__PURE__ */ jsx("h1", { className: "text-2xl font-bold mt-8 mb-4", ...props, children }),
41
- h2: ({ children, ...props }) => /* @__PURE__ */ jsx("h2", { className: "text-xl font-bold mt-6 mb-3", ...props, children }),
42
- h3: ({ children, ...props }) => /* @__PURE__ */ jsx("h3", { className: "text-lg font-bold mt-4 mb-2", ...props, children }),
41
+ h1: ({ children, ...props }) => /* @__PURE__ */ jsx("h1", { className: "text-2xl font-semibold mt-8 mb-4", ...props, children }),
42
+ h2: ({ children, ...props }) => /* @__PURE__ */ jsx("h2", { className: "text-xl font-semibold mt-6 mb-3", ...props, children }),
43
+ h3: ({ children, ...props }) => /* @__PURE__ */ jsx("h3", { className: "text-lg font-semibold mt-4 mb-2", ...props, children }),
43
44
  hr: ({ ...props }) => /* @__PURE__ */ jsx("hr", { className: "my-8 border-border", ...props }),
44
45
  li: ({ children, ...props }) => /* @__PURE__ */ jsx(
45
46
  "li",
@@ -89,14 +90,15 @@ const proseClasses = [
89
90
  "prose-strong:font-semibold prose-em:italic",
90
91
  "prose-a:text-primary prose-a:underline prose-a:underline-offset-4 hover:prose-a:text-primary/80",
91
92
  "prose-code:bg-muted prose-code:px-1 prose-code:py-0.5 prose-code:rounded prose-code:text-sm prose-code:font-mono",
92
- "prose-pre:my-6 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:bg-black prose-pre:py-4 prose-pre:font-mono prose-pre:text-sm prose-pre:text-white prose-pre:shadow-lg dark:prose-pre:bg-zinc-900",
93
- "prose-blockquote:border-l-4 prose-blockquote:border-primary prose-blockquote:pl-4 prose-blockquote:italic prose-blockquote:text-muted-foreground prose-blockquote:my-6 prose-blockquote:py-2",
93
+ "prose-pre:my-6 prose-pre:overflow-x-auto prose-pre:rounded-lg prose-pre:border prose-pre:bg-zinc-950 prose-pre:py-4 prose-pre:font-mono prose-pre:text-sm prose-pre:text-white prose-pre:shadow-lg dark:prose-pre:bg-zinc-900",
94
+ "prose-blockquote:border-l prose-blockquote:border-primary prose-blockquote:pl-4 prose-blockquote:italic prose-blockquote:text-muted-foreground prose-blockquote:my-6 prose-blockquote:py-2",
94
95
  "prose-hr:my-8 prose-hr:border-border",
95
96
  "prose-table:w-full prose-table:border-collapse prose-table:border prose-table:border-border",
96
97
  "prose-th:border prose-th:border-border prose-th:bg-muted prose-th:p-2 prose-th:text-left prose-th:font-medium",
97
98
  "prose-td:border prose-td:border-border prose-td:p-2",
98
99
  "prose-img:rounded-lg prose-img:border prose-img:border-border prose-img:shadow-lg"
99
100
  ].join(" ");
101
+ const markdownPlugins = [remarkGfm];
100
102
  function removeImportStatements(content, componentNames) {
101
103
  let processed = content.replaceAll(/^import\s+.*CodeBlock.*from.*$/gm, "");
102
104
  componentNames.forEach((name) => {
@@ -143,9 +145,16 @@ async function MDXContent({
143
145
  if (Component) {
144
146
  return /* @__PURE__ */ jsx("div", { className: proseClasses, children: /* @__PURE__ */ jsx(Component, { components: allComponents }) });
145
147
  }
146
- return /* @__PURE__ */ jsx("div", { className: proseClasses, children: /* @__PURE__ */ jsx(ReactMarkdown, { components: allComponents, children: content }) });
148
+ return /* @__PURE__ */ jsx("div", { className: proseClasses, children: /* @__PURE__ */ jsx(
149
+ ReactMarkdown,
150
+ {
151
+ components: allComponents,
152
+ remarkPlugins: markdownPlugins,
153
+ children: content
154
+ }
155
+ ) });
147
156
  }
148
- return /* @__PURE__ */ jsx("div", { className: proseClasses, children: /* @__PURE__ */ jsx(ReactMarkdown, { components: allComponents, children: content }) });
157
+ return /* @__PURE__ */ jsx("div", { className: proseClasses, children: /* @__PURE__ */ jsx(ReactMarkdown, { components: allComponents, remarkPlugins: markdownPlugins, children: content }) });
149
158
  }
150
159
  export {
151
160
  MDXContent
@@ -1,7 +1,7 @@
1
1
  import { Fragment, jsx, jsxs } from "react/jsx-runtime";
2
2
  import * as React from "react";
3
3
  import { cn } from "../../lib/utils";
4
- import { Badge } from "../badge";
4
+ import { Badge } from "../badge/badge";
5
5
  import {
6
6
  Card,
7
7
  CardContent,
@@ -3,7 +3,7 @@ import { jsx, jsxs } from "react/jsx-runtime";
3
3
  import { useMemo, useRef, useState } from "react";
4
4
  import { ArrowUpDown, Filter } from "lucide-react";
5
5
  import { cn } from "../../lib/utils";
6
- import { Badge } from "../badge";
6
+ import { Badge } from "../badge/badge";
7
7
  import { Button } from "../button";
8
8
  import {
9
9
  Command,
@@ -3,7 +3,7 @@ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
3
3
  import * as React from "react";
4
4
  import { Check, ChevronDown } from "lucide-react";
5
5
  import { cn } from "../../lib/utils";
6
- import { Badge } from "../badge";
6
+ import { Badge } from "../badge/badge";
7
7
  import { Button } from "../button";
8
8
  import {
9
9
  Command,
@@ -4,10 +4,9 @@ import { Menu, X } from "lucide-react";
4
4
  import Link from "next/link";
5
5
  import { usePathname } from "next/navigation";
6
6
  import { cn } from "../../lib/utils";
7
- import { Button } from "../button";
7
+ import { Button } from "../button/button";
8
8
  import { useSidebar } from "../sidebar-provider";
9
9
  import { ThemeToggle } from "../theme-toggle";
10
- import { useMobile } from "./use-mobile";
11
10
  const EMPTY_NAV_ITEMS = [];
12
11
  function NavbarSaas({
13
12
  brand,
@@ -17,13 +16,14 @@ function NavbarSaas({
17
16
  }) {
18
17
  const pathname = usePathname();
19
18
  const { open, setOpen } = useSidebar();
20
- const isMobile = useMobile();
21
19
  return /* @__PURE__ */ jsx("header", { className: "sticky top-0 z-50 w-full border-b bg-background/95 backdrop-blur supports-[backdrop-filter]:bg-background/60 shrink-0", children: /* @__PURE__ */ jsx("div", { className: "w-full", children: /* @__PURE__ */ jsxs("div", { className: "mx-auto flex h-16 items-center justify-between px-4", children: [
22
20
  /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-4", children: [
23
- showMobileMenu && isMobile ? /* @__PURE__ */ jsx(
21
+ showMobileMenu ? /* @__PURE__ */ jsx(
24
22
  Button,
25
23
  {
26
- className: "lg:hidden",
24
+ "aria-expanded": open,
25
+ "aria-label": "Toggle sidebar",
26
+ "data-testid": "navbar-saas-mobile-trigger",
27
27
  onClick: () => {
28
28
  setOpen(!open);
29
29
  },
@@ -3,7 +3,7 @@ import { jsx, jsxs } from "react/jsx-runtime";
3
3
  import * as React from "react";
4
4
  import { Minus, Plus } from "lucide-react";
5
5
  import { cn } from "../../lib/utils";
6
- import { Button } from "../button";
6
+ import { Button } from "../button/button";
7
7
  function getNumericBound(bound) {
8
8
  if (bound === void 0) {
9
9
  return;
@@ -7,7 +7,7 @@ function getNumberTickerFormatter(locale, formatOptions) {
7
7
  const key = `${locale ?? ""}|${formatOptions ? JSON.stringify(formatOptions) : ""}`;
8
8
  let formatter = NUMBER_FORMATTER_CACHE.get(key);
9
9
  if (!formatter) {
10
- formatter = new Intl.NumberFormat(locale, formatOptions);
10
+ formatter = Intl.NumberFormat(locale, formatOptions);
11
11
  NUMBER_FORMATTER_CACHE.set(key, formatter);
12
12
  }
13
13
  return formatter;
@@ -1,7 +1,7 @@
1
1
  import { jsx, jsxs } from "react/jsx-runtime";
2
2
  import { forwardRef } from "react";
3
3
  import { cn } from "../../lib/utils";
4
- import { Badge } from "../badge";
4
+ import { Badge } from "../badge/badge";
5
5
  import { Button } from "../button";
6
6
  const stateClasses = {
7
7
  blocked: "border-amber-500/30 bg-amber-500/10 text-amber-700 dark:text-amber-300",
@@ -68,7 +68,7 @@ function BookSide({
68
68
  ] });
69
69
  }
70
70
  const OrderBook = React.forwardRef(
71
- ({ asks, bids, className, precision = 2, ...props }, reference) => {
71
+ ({ as: Heading = "h2", asks, bids, className, precision = 2, ...props }, reference) => {
72
72
  if (asks.length === 0 && bids.length === 0) {
73
73
  return null;
74
74
  }
@@ -90,7 +90,7 @@ const OrderBook = React.forwardRef(
90
90
  /* @__PURE__ */ jsxs("div", { className: "mb-4 flex flex-wrap items-start justify-between gap-3", children: [
91
91
  /* @__PURE__ */ jsxs("div", { children: [
92
92
  /* @__PURE__ */ jsx("p", { className: "text-xs font-medium uppercase tracking-[0.28em] text-muted-foreground", children: "Level II" }),
93
- /* @__PURE__ */ jsx("h2", { className: "text-lg font-semibold text-foreground", children: "Order book" })
93
+ /* @__PURE__ */ jsx(Heading, { className: "text-lg font-semibold text-foreground", children: "Order book" })
94
94
  ] }),
95
95
  /* @__PURE__ */ jsxs("div", { className: "rounded-full border border-border bg-background/70 px-3 py-1 text-sm text-muted-foreground tabular-nums", children: [
96
96
  "Spread ",
@@ -2,7 +2,7 @@ import { jsx, jsxs } from "react/jsx-runtime";
2
2
  import { forwardRef } from "react";
3
3
  import { AlertCircle, ArrowRight, Inbox, ListTodo, Siren } from "lucide-react";
4
4
  import { cn } from "../../lib/utils";
5
- import { Button } from "../button";
5
+ import { Button } from "../button/button";
6
6
  const toneClassNames = {
7
7
  danger: "border-red-500/30 bg-red-500/8",
8
8
  default: "border-border/70 bg-background/80",
@@ -40,7 +40,7 @@ const RowBody = (props) => {
40
40
  const Row = (props) => {
41
41
  const { policy } = props;
42
42
  if (policy.onToggle) {
43
- const handleClick = () => {
43
+ const handleTogglePolicy = () => {
44
44
  policy.onToggle?.();
45
45
  };
46
46
  return /* @__PURE__ */ jsx(
@@ -49,7 +49,7 @@ const Row = (props) => {
49
49
  className: "flex w-full items-center gap-2 rounded-md border border-transparent px-2 py-1.5 text-left transition-colors hover:border-border hover:bg-muted/40 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
50
50
  "data-policy-row": policy.id,
51
51
  "data-policy-status": policy.status,
52
- onClick: handleClick,
52
+ onClick: handleTogglePolicy,
53
53
  type: "button",
54
54
  children: /* @__PURE__ */ jsx(RowBody, { policy })
55
55
  }
@@ -3,6 +3,7 @@ import Image from "next/image";
3
3
  import Link from "next/link";
4
4
  import { Button } from "../button/button";
5
5
  function ProfileSection({
6
+ as: Heading = "h3",
6
7
  compact = false,
7
8
  dict,
8
9
  imageAlt,
@@ -25,7 +26,7 @@ function ProfileSection({
25
26
  }
26
27
  ) }) : null,
27
28
  /* @__PURE__ */ jsxs("div", { className: "space-y-2", children: [
28
- /* @__PURE__ */ jsx("h3", { className: `font-semibold ${compact ? "text-lg" : "text-xl"}`, children: dict.profile.name }),
29
+ /* @__PURE__ */ jsx(Heading, { className: `font-semibold ${compact ? "text-lg" : "text-xl"}`, children: dict.profile.name }),
29
30
  /* @__PURE__ */ jsx("p", { className: "text-sm text-muted-foreground", children: compact ? dict.profile.tagline : `> ${dict.profile.tagline}` })
30
31
  ] }),
31
32
  showSocialLinks ? /* @__PURE__ */ jsx("div", { className: "flex flex-wrap justify-center items-center gap-2", children: socialLinks?.map((link) => /* @__PURE__ */ jsx(
@@ -2,7 +2,7 @@
2
2
  import { jsx, jsxs } from "react/jsx-runtime";
3
3
  import { memo, useEffect, useState } from "react";
4
4
  import { useMounted } from "../../lib/use-mounted";
5
- import { Badge } from "../badge";
5
+ import { Badge } from "../badge/badge";
6
6
  import {
7
7
  Card,
8
8
  CardContent,
@@ -2,7 +2,7 @@
2
2
  import { jsx, jsxs } from "react/jsx-runtime";
3
3
  import * as React from "react";
4
4
  import { cn } from "../../lib/utils";
5
- import { Badge } from "../badge";
5
+ import { Badge } from "../badge/badge";
6
6
  import {
7
7
  Card,
8
8
  CardContent,
@@ -10,7 +10,10 @@ import {
10
10
  CardHeader,
11
11
  CardTitle
12
12
  } from "../card";
13
- import { CHECKLIST_PROGRESS_EVENT } from "../checklist";
13
+ import {
14
+ CHECKLIST_PROGRESS_EVENT,
15
+ parseChecklistStorageValue
16
+ } from "../checklist";
14
17
  import { ProgressBar } from "../progress-bar";
15
18
  const ProgressTrackerContext = React.createContext(null);
16
19
  function clampPercentage(value) {
@@ -41,15 +44,13 @@ function readPersistedChecklistItems(persistKey) {
41
44
  try {
42
45
  const saved = localStorage.getItem(`checklist:${persistKey}`);
43
46
  if (!saved) return [];
44
- const parsed = JSON.parse(saved);
45
- return Array.isArray(parsed) ? parsed.filter((item) => typeof item === "string") : [];
47
+ return parseChecklistStorageValue(saved);
46
48
  } catch {
47
49
  return [];
48
50
  }
49
51
  }
50
52
  function areStringArraysEqual(left, right) {
51
- if (left.length !== right.length) return false;
52
- return left.every((value, index) => value === right[index]);
53
+ return left.length === right.length && left.every((value, index) => value === right[index]);
53
54
  }
54
55
  function getChecklistPersistKey(event) {
55
56
  if (!(event instanceof CustomEvent)) return null;
@@ -79,14 +80,16 @@ function useChecklistProgress(checklistItems = [], persistKey) {
79
80
  const [persistedIds, setPersistedIds] = React.useState(
80
81
  () => readPersistedChecklistItems(persistKey)
81
82
  );
83
+ const [trackedPersistKey, setTrackedPersistKey] = React.useState(persistKey);
82
84
  const setPersistedIdsIfChanged = React.useCallback((nextIds) => {
83
85
  setPersistedIds(
84
86
  (currentIds) => areStringArraysEqual(currentIds, nextIds) ? currentIds : nextIds
85
87
  );
86
88
  }, []);
87
- React.useEffect(() => {
89
+ if (trackedPersistKey !== persistKey) {
90
+ setTrackedPersistKey(persistKey);
88
91
  setPersistedIdsIfChanged(readPersistedChecklistItems(persistKey));
89
- }, [persistKey, setPersistedIdsIfChanged]);
92
+ }
90
93
  React.useEffect(() => {
91
94
  if (!persistKey || typeof window === "undefined") return;
92
95
  const sync = (event) => {
@@ -162,7 +165,12 @@ function ProgressTrackerOverview({
162
165
  }) {
163
166
  const { modules, overallProgress, streak, title } = useProgressTrackerContext();
164
167
  const trackedPersistKeys = React.useMemo(
165
- () => modules.map((module) => module.persistKey).filter(Boolean),
168
+ () => modules.reduce((keys, module) => {
169
+ if (module.persistKey) {
170
+ keys.push(module.persistKey);
171
+ }
172
+ return keys;
173
+ }, []),
166
174
  [modules]
167
175
  );
168
176
  const [, forceChecklistRefresh] = React.useState(0);
@@ -243,7 +243,7 @@ function VariableField({
243
243
  onValueChange,
244
244
  value
245
245
  }) {
246
- const handleChange = useCallback(
246
+ const handleVariableValueChange = useCallback(
247
247
  (event) => {
248
248
  onValueChange(name, event.target.value);
249
249
  },
@@ -255,7 +255,7 @@ function VariableField({
255
255
  Input,
256
256
  {
257
257
  id: fieldId,
258
- onChange: handleChange,
258
+ onChange: handleVariableValueChange,
259
259
  placeholder: `Value for ${name}`,
260
260
  value
261
261
  }
@@ -118,6 +118,7 @@ function QuizResult({
118
118
  );
119
119
  }
120
120
  function Quiz({
121
+ as: Heading = "h4",
121
122
  className,
122
123
  explanation,
123
124
  hint,
@@ -159,7 +160,7 @@ function Quiz({
159
160
  )
160
161
  }
161
162
  ),
162
- /* @__PURE__ */ jsx("h4", { className: "font-semibold text-foreground", children: question })
163
+ /* @__PURE__ */ jsx(Heading, { className: "font-semibold text-foreground", children: question })
163
164
  ] }),
164
165
  /* @__PURE__ */ jsx("div", { className: "space-y-2 mb-4", children: options.map((opt, index) => /* @__PURE__ */ jsx(
165
166
  QuizOptionButton,
@@ -172,7 +173,7 @@ function Quiz({
172
173
  selectedIndex,
173
174
  submitted
174
175
  },
175
- typeof opt === "string" ? opt : `quiz-option-${String(opt)}`
176
+ `quiz-option-${index}-${opt.label}`
176
177
  )) }),
177
178
  hint && !submitted ? /* @__PURE__ */ jsx(
178
179
  QuizHint,
@@ -28,7 +28,7 @@ const RowBody = (props) => {
28
28
  const Row = (props) => {
29
29
  const { edge } = props;
30
30
  if (edge.onActivate) {
31
- const handleClick = () => {
31
+ const handleActivateRelationship = () => {
32
32
  edge.onActivate?.();
33
33
  };
34
34
  return /* @__PURE__ */ jsx(
@@ -37,7 +37,7 @@ const Row = (props) => {
37
37
  className: "flex w-full items-center gap-2 rounded-md border border-transparent px-2 py-1.5 text-left transition-colors hover:border-border hover:bg-muted/40 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
38
38
  "data-relationship-direction": edge.direction,
39
39
  "data-relationship-row": true,
40
- onClick: handleClick,
40
+ onClick: handleActivateRelationship,
41
41
  type: "button",
42
42
  children: /* @__PURE__ */ jsx(RowBody, { edge })
43
43
  }
@@ -63,7 +63,7 @@ const RowBody = (props) => {
63
63
  const Row = (props) => {
64
64
  const { assignment } = props;
65
65
  if (assignment.onActivate) {
66
- const handleClick = () => {
66
+ const handleActivateAssignment = () => {
67
67
  assignment.onActivate?.();
68
68
  };
69
69
  return /* @__PURE__ */ jsx(
@@ -72,7 +72,7 @@ const Row = (props) => {
72
72
  className: "flex w-full items-center gap-2 rounded-md border border-transparent px-2 py-1.5 text-left transition-colors hover:border-border hover:bg-muted/40 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring",
73
73
  "data-routing-assignment": assignment.id,
74
74
  "data-routing-role": assignment.role,
75
- onClick: handleClick,
75
+ onClick: handleActivateAssignment,
76
76
  type: "button",
77
77
  children: /* @__PURE__ */ jsx(RowBody, { assignment })
78
78
  }
@@ -63,7 +63,7 @@ const PhaseBar = (props) => {
63
63
  };
64
64
  const ariaLabel = `${STATE_LABEL[state]} ${phase.start} \u2192 ${phase.end}`;
65
65
  if (phase.onActivate) {
66
- const handleClick = () => {
66
+ const handleActivatePhase = () => {
67
67
  phase.onActivate?.();
68
68
  };
69
69
  return /* @__PURE__ */ jsx(
@@ -76,7 +76,7 @@ const PhaseBar = (props) => {
76
76
  ),
77
77
  "data-run-phase": phase.id,
78
78
  "data-run-phase-state": state,
79
- onClick: handleClick,
79
+ onClick: handleActivatePhase,
80
80
  style: sharedStyle,
81
81
  type: "button",
82
82
  children: phase.label
@@ -3,7 +3,7 @@ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
3
3
  import { forwardRef, useMemo, useState } from "react";
4
4
  import { Check, ChevronRight, Search } from "lucide-react";
5
5
  import { cn } from "../../lib/utils";
6
- import { Badge } from "../badge";
6
+ import { Badge } from "../badge/badge";
7
7
  import { Button } from "../button";
8
8
  import { Input } from "../input";
9
9
  import { Popover, PopoverContent, PopoverTrigger } from "../popover";