@lssm/example.learning-journey-ui-gamified 0.0.0-canary-20251217073102 → 0.0.0-canary-20251217083314

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 (126) hide show
  1. package/.turbo/turbo-build$colon$bundle.log +395 -14
  2. package/CHANGELOG.md +9 -9
  3. package/dist/GamifiedMiniApp.d.ts +16 -0
  4. package/dist/GamifiedMiniApp.js +64 -0
  5. package/dist/components/DayCalendar.d.ts +15 -0
  6. package/dist/components/DayCalendar.js +32 -0
  7. package/dist/components/FlashCard.d.ts +18 -0
  8. package/dist/components/FlashCard.js +79 -0
  9. package/dist/components/MasteryRing.d.ts +17 -0
  10. package/dist/components/MasteryRing.js +81 -0
  11. package/dist/components/index.d.ts +4 -0
  12. package/dist/components/index.js +5 -0
  13. package/dist/docs/index.d.ts +1 -0
  14. package/dist/docs/index.js +1 -0
  15. package/dist/docs/learning-journey-ui-gamified.docblock.d.ts +1 -0
  16. package/dist/docs/learning-journey-ui-gamified.docblock.js +20 -0
  17. package/dist/{index.d.mts → example.d.ts} +1 -18
  18. package/dist/example.js +34 -0
  19. package/dist/examples/learning-journey-ui-shared/dist/components/BadgeDisplay.js +44 -0
  20. package/dist/examples/learning-journey-ui-shared/dist/components/StreakCounter.js +45 -0
  21. package/dist/examples/learning-journey-ui-shared/dist/components/ViewTabs.js +48 -0
  22. package/dist/examples/learning-journey-ui-shared/dist/components/XpBar.js +46 -0
  23. package/dist/examples/learning-journey-ui-shared/dist/components/index.js +4 -0
  24. package/dist/examples/learning-journey-ui-shared/dist/docs/index.js +1 -0
  25. package/dist/examples/learning-journey-ui-shared/dist/docs/learning-journey-ui-shared.docblock.js +20 -0
  26. package/dist/examples/learning-journey-ui-shared/dist/hooks/index.js +1 -0
  27. package/dist/examples/learning-journey-ui-shared/dist/hooks/useLearningProgress.js +73 -0
  28. package/dist/examples/learning-journey-ui-shared/dist/index.js +8 -0
  29. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/PUBLISHING.docblock.js +15 -0
  30. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/accessibility_wcag_compliance_specs.docblock.js +15 -0
  31. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/index.js +28 -0
  32. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/presentations.js +71 -0
  33. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/registry.js +44 -0
  34. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/PHASE_1_QUICKSTART.docblock.js +15 -0
  35. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/PHASE_2_AI_NATIVE_OPERATIONS.docblock.js +15 -0
  36. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/PHASE_3_AUTO_EVOLUTION.docblock.js +15 -0
  37. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/PHASE_4_PERSONALIZATION_ENGINE.docblock.js +15 -0
  38. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/PHASE_5_ZERO_TOUCH_OPERATIONS.docblock.js +15 -0
  39. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/auth/better-auth-nextjs.docblock.js +79 -0
  40. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/contracts/openapi-export.docblock.js +56 -0
  41. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/lifecycle-stage-system.docblock.js +15 -0
  42. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/llm/llm-integration.docblock.js +356 -0
  43. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/mcp-endpoints.docblock.js +36 -0
  44. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/presentation-runtime.docblock.js +15 -0
  45. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/schema/README.docblock.js +19 -0
  46. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/learning-events.docblock.js +47 -0
  47. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/learning-journeys.docblock.js +78 -0
  48. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/platform-admin-panel.docblock.js +83 -0
  49. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/project-access-teams.docblock.js +44 -0
  50. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/project-routing.docblock.js +66 -0
  51. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/sandbox-unlogged.docblock.js +39 -0
  52. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/team-invitations.docblock.js +68 -0
  53. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/workspace-ops.docblock.js +46 -0
  54. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/studio/workspaces.docblock.js +61 -0
  55. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/telemetry-ingest.docblock.js +154 -0
  56. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/templates/runtime.docblock.js +19 -0
  57. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/vscode-extension.docblock.js +100 -0
  58. package/dist/examples/learning-journey-ui-shared/dist/libs/contracts/dist/docs/tech/workflows/overview.docblock.js +19 -0
  59. package/dist/examples/learning-journey-ui-shared/dist/libs/design-system/dist/_virtual/rolldown_runtime.js +5 -0
  60. package/dist/examples/learning-journey-ui-shared/dist/libs/design-system/dist/components/atoms/Button.js +33 -0
  61. package/dist/examples/learning-journey-ui-shared/dist/libs/design-system/dist/ui-kit-web/dist/ui/button.js +55 -0
  62. package/dist/examples/learning-journey-ui-shared/dist/libs/design-system/dist/ui-kit-web/dist/ui-kit-core/dist/utils.js +13 -0
  63. package/dist/examples/learning-journey-ui-shared/dist/libs/ui-kit-web/dist/ui/progress.js +23 -0
  64. package/dist/examples/learning-journey-ui-shared/dist/libs/ui-kit-web/dist/ui/utils.js +10 -0
  65. package/dist/examples/learning-journey-ui-shared/dist/libs/ui-kit-web/dist/ui-kit-core/dist/utils.js +10 -0
  66. package/dist/index.d.ts +12 -0
  67. package/dist/index.js +14 -0
  68. package/dist/libs/contracts/dist/docs/PUBLISHING.docblock.js +16 -0
  69. package/dist/libs/contracts/dist/docs/accessibility_wcag_compliance_specs.docblock.js +16 -0
  70. package/dist/libs/contracts/dist/docs/index.js +29 -0
  71. package/dist/libs/contracts/dist/docs/presentations.js +71 -0
  72. package/dist/libs/contracts/dist/docs/registry.js +44 -0
  73. package/dist/libs/contracts/dist/docs/tech/PHASE_1_QUICKSTART.docblock.js +16 -0
  74. package/dist/libs/contracts/dist/docs/tech/PHASE_2_AI_NATIVE_OPERATIONS.docblock.js +16 -0
  75. package/dist/libs/contracts/dist/docs/tech/PHASE_3_AUTO_EVOLUTION.docblock.js +16 -0
  76. package/dist/libs/contracts/dist/docs/tech/PHASE_4_PERSONALIZATION_ENGINE.docblock.js +16 -0
  77. package/dist/libs/contracts/dist/docs/tech/PHASE_5_ZERO_TOUCH_OPERATIONS.docblock.js +16 -0
  78. package/dist/libs/contracts/dist/docs/tech/auth/better-auth-nextjs.docblock.js +80 -0
  79. package/dist/libs/contracts/dist/docs/tech/contracts/openapi-export.docblock.js +57 -0
  80. package/dist/libs/contracts/dist/docs/tech/lifecycle-stage-system.docblock.js +16 -0
  81. package/dist/libs/contracts/dist/docs/tech/llm/llm-integration.docblock.js +357 -0
  82. package/dist/libs/contracts/dist/docs/tech/mcp-endpoints.docblock.js +37 -0
  83. package/dist/libs/contracts/dist/docs/tech/presentation-runtime.docblock.js +16 -0
  84. package/dist/libs/contracts/dist/docs/tech/schema/README.docblock.js +20 -0
  85. package/dist/libs/contracts/dist/docs/tech/studio/learning-events.docblock.js +48 -0
  86. package/dist/libs/contracts/dist/docs/tech/studio/learning-journeys.docblock.js +79 -0
  87. package/dist/libs/contracts/dist/docs/tech/studio/platform-admin-panel.docblock.js +84 -0
  88. package/dist/libs/contracts/dist/docs/tech/studio/project-access-teams.docblock.js +45 -0
  89. package/dist/libs/contracts/dist/docs/tech/studio/project-routing.docblock.js +67 -0
  90. package/dist/libs/contracts/dist/docs/tech/studio/sandbox-unlogged.docblock.js +40 -0
  91. package/dist/libs/contracts/dist/docs/tech/studio/team-invitations.docblock.js +69 -0
  92. package/dist/libs/contracts/dist/docs/tech/studio/workspace-ops.docblock.js +47 -0
  93. package/dist/libs/contracts/dist/docs/tech/studio/workspaces.docblock.js +62 -0
  94. package/dist/libs/contracts/dist/docs/tech/telemetry-ingest.docblock.js +155 -0
  95. package/dist/libs/contracts/dist/docs/tech/templates/runtime.docblock.js +20 -0
  96. package/dist/libs/contracts/dist/docs/tech/vscode-extension.docblock.js +101 -0
  97. package/dist/libs/contracts/dist/docs/tech/workflows/overview.docblock.js +20 -0
  98. package/dist/libs/design-system/dist/_virtual/rolldown_runtime.js +5 -0
  99. package/dist/libs/design-system/dist/components/atoms/Button.js +33 -0
  100. package/dist/libs/design-system/dist/ui-kit-web/dist/ui/button.js +55 -0
  101. package/dist/libs/design-system/dist/ui-kit-web/dist/ui-kit-core/dist/utils.js +13 -0
  102. package/dist/libs/ui-kit-web/dist/ui/card.js +36 -0
  103. package/dist/libs/ui-kit-web/dist/ui/utils.js +10 -0
  104. package/dist/libs/ui-kit-web/dist/ui-kit-core/dist/utils.js +10 -0
  105. package/dist/views/Overview.d.ts +14 -0
  106. package/dist/views/Overview.js +163 -0
  107. package/dist/views/Progress.d.ts +10 -0
  108. package/dist/views/Progress.js +144 -0
  109. package/dist/views/Steps.d.ts +11 -0
  110. package/dist/views/Steps.js +55 -0
  111. package/dist/views/Timeline.d.ts +10 -0
  112. package/dist/views/Timeline.js +132 -0
  113. package/dist/views/index.d.ts +5 -0
  114. package/dist/views/index.js +6 -0
  115. package/package.json +25 -16
  116. package/tsdown.config.js +14 -10
  117. package/dist/DayCalendar-Cha869Bi.mjs +0 -178
  118. package/dist/components/index.d.mts +0 -2
  119. package/dist/components/index.mjs +0 -4
  120. package/dist/components-kh0CpIG2.mjs +0 -1
  121. package/dist/index-C7CBKOil.d.mts +0 -44
  122. package/dist/index-DiAD2ivN.d.mts +0 -33
  123. package/dist/index.mjs +0 -110
  124. package/dist/views/index.d.mts +0 -2
  125. package/dist/views/index.mjs +0 -4
  126. package/dist/views-B-DapxWu.mjs +0 -467
@@ -0,0 +1,32 @@
1
+ 'use client';
2
+
3
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
4
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
5
+
6
+ //#region src/components/DayCalendar.tsx
7
+ function DayCalendar({ totalDays, currentDay, completedDays }) {
8
+ return /* @__PURE__ */ jsx("div", {
9
+ className: "grid grid-cols-7 gap-2",
10
+ children: Array.from({ length: totalDays }, (_, i) => i + 1).map((day) => {
11
+ const isCompleted = completedDays.includes(day);
12
+ const isCurrent = day === currentDay;
13
+ const isLocked = day > currentDay;
14
+ return /* @__PURE__ */ jsx("div", {
15
+ className: cn("flex h-12 w-12 flex-col items-center justify-center rounded-lg border text-sm font-medium transition-all", isCompleted && "border-green-500 bg-green-500/10 text-green-500", isCurrent && !isCompleted && "border-violet-500 bg-violet-500/10 text-violet-500 ring-2 ring-violet-500/50", isLocked && "border-muted bg-muted/50 text-muted-foreground", !isCompleted && !isCurrent && !isLocked && "border-border bg-card"),
16
+ children: isCompleted ? /* @__PURE__ */ jsx("span", {
17
+ className: "text-lg",
18
+ children: "✓"
19
+ }) : isLocked ? /* @__PURE__ */ jsx("span", {
20
+ className: "text-lg",
21
+ children: "🔒"
22
+ }) : /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx("span", {
23
+ className: "text-muted-foreground text-xs",
24
+ children: "Day"
25
+ }), /* @__PURE__ */ jsx("span", { children: day })] })
26
+ }, day);
27
+ })
28
+ });
29
+ }
30
+
31
+ //#endregion
32
+ export { DayCalendar };
@@ -0,0 +1,18 @@
1
+ import * as react_jsx_runtime1 from "react/jsx-runtime";
2
+ import { LearningJourneyStepSpec } from "@lssm/module.learning-journey/track-spec";
3
+
4
+ //#region src/components/FlashCard.d.ts
5
+ interface FlashCardProps {
6
+ step: LearningJourneyStepSpec;
7
+ isCompleted: boolean;
8
+ isCurrent: boolean;
9
+ onComplete?: () => void;
10
+ }
11
+ declare function FlashCard({
12
+ step,
13
+ isCompleted,
14
+ isCurrent,
15
+ onComplete
16
+ }: FlashCardProps): react_jsx_runtime1.JSX.Element;
17
+ //#endregion
18
+ export { FlashCard };
@@ -0,0 +1,79 @@
1
+ 'use client';
2
+
3
+ import { Card, CardContent } from "../libs/ui-kit-web/dist/ui/card.js";
4
+ import { Button$1 } from "../libs/design-system/dist/components/atoms/Button.js";
5
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
6
+ import { useState } from "react";
7
+ import { jsx, jsxs } from "react/jsx-runtime";
8
+
9
+ //#region src/components/FlashCard.tsx
10
+ function FlashCard({ step, isCompleted, isCurrent, onComplete }) {
11
+ const [isFlipped, setIsFlipped] = useState(false);
12
+ return /* @__PURE__ */ jsx(Card, {
13
+ className: cn("relative cursor-pointer overflow-hidden transition-all duration-300", isCurrent && "ring-primary ring-2", isCompleted && "opacity-60"),
14
+ onClick: () => !isCompleted && setIsFlipped(!isFlipped),
15
+ children: /* @__PURE__ */ jsxs(CardContent, {
16
+ className: "p-6",
17
+ children: [/* @__PURE__ */ jsxs("div", {
18
+ className: cn("space-y-4 transition-opacity duration-200", isFlipped ? "opacity-0" : "opacity-100"),
19
+ children: [
20
+ /* @__PURE__ */ jsxs("div", {
21
+ className: "flex items-start justify-between",
22
+ children: [/* @__PURE__ */ jsxs("div", {
23
+ className: "flex-1",
24
+ children: [/* @__PURE__ */ jsx("h3", {
25
+ className: "text-lg font-semibold",
26
+ children: step.title
27
+ }), step.description && /* @__PURE__ */ jsx("p", {
28
+ className: "text-muted-foreground mt-1 text-sm",
29
+ children: step.description
30
+ })]
31
+ }), step.xpReward && /* @__PURE__ */ jsxs("span", {
32
+ className: "rounded-full bg-green-500/10 px-2 py-1 text-xs font-semibold text-green-500",
33
+ children: [
34
+ "+",
35
+ step.xpReward,
36
+ " XP"
37
+ ]
38
+ })]
39
+ }),
40
+ isCompleted && /* @__PURE__ */ jsxs("div", {
41
+ className: "flex items-center gap-2 text-green-500",
42
+ children: [/* @__PURE__ */ jsx("span", { children: "✓" }), /* @__PURE__ */ jsx("span", {
43
+ className: "text-sm font-medium",
44
+ children: "Completed"
45
+ })]
46
+ }),
47
+ isCurrent && !isCompleted && /* @__PURE__ */ jsx("p", {
48
+ className: "text-muted-foreground text-xs",
49
+ children: "Tap to reveal action"
50
+ })
51
+ ]
52
+ }), isFlipped && !isCompleted && /* @__PURE__ */ jsxs("div", {
53
+ className: "absolute inset-0 flex flex-col items-center justify-center gap-4 bg-gradient-to-br from-violet-500/10 to-violet-600/10 p-6",
54
+ children: [/* @__PURE__ */ jsx("p", {
55
+ className: "text-center text-sm",
56
+ children: step.instructions ?? "Complete this step to earn XP"
57
+ }), /* @__PURE__ */ jsxs("div", {
58
+ className: "flex gap-2",
59
+ children: [/* @__PURE__ */ jsx(Button$1, {
60
+ variant: "outline",
61
+ size: "sm",
62
+ onClick: () => setIsFlipped(false),
63
+ children: "Back"
64
+ }), /* @__PURE__ */ jsx(Button$1, {
65
+ size: "sm",
66
+ onClick: (e) => {
67
+ e.stopPropagation();
68
+ onComplete?.();
69
+ },
70
+ children: "Mark Complete"
71
+ })]
72
+ })]
73
+ })]
74
+ })
75
+ });
76
+ }
77
+
78
+ //#endregion
79
+ export { FlashCard };
@@ -0,0 +1,17 @@
1
+ import * as react_jsx_runtime4 from "react/jsx-runtime";
2
+
3
+ //#region src/components/MasteryRing.d.ts
4
+ interface MasteryRingProps {
5
+ label: string;
6
+ percentage: number;
7
+ size?: 'sm' | 'md' | 'lg';
8
+ color?: 'green' | 'blue' | 'violet' | 'orange';
9
+ }
10
+ declare function MasteryRing({
11
+ label,
12
+ percentage,
13
+ size,
14
+ color
15
+ }: MasteryRingProps): react_jsx_runtime4.JSX.Element;
16
+ //#endregion
17
+ export { MasteryRing };
@@ -0,0 +1,81 @@
1
+ 'use client';
2
+
3
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+
6
+ //#region src/components/MasteryRing.tsx
7
+ const sizeStyles = {
8
+ sm: {
9
+ container: "h-16 w-16",
10
+ text: "text-xs",
11
+ ring: 48,
12
+ stroke: 4
13
+ },
14
+ md: {
15
+ container: "h-24 w-24",
16
+ text: "text-sm",
17
+ ring: 72,
18
+ stroke: 6
19
+ },
20
+ lg: {
21
+ container: "h-32 w-32",
22
+ text: "text-base",
23
+ ring: 96,
24
+ stroke: 8
25
+ }
26
+ };
27
+ const colorStyles = {
28
+ green: "stroke-green-500",
29
+ blue: "stroke-blue-500",
30
+ violet: "stroke-violet-500",
31
+ orange: "stroke-orange-500"
32
+ };
33
+ function MasteryRing({ label, percentage, size = "md", color = "violet" }) {
34
+ const styles = sizeStyles[size];
35
+ const radius = (styles.ring - styles.stroke) / 2;
36
+ const circumference = 2 * Math.PI * radius;
37
+ const strokeDashoffset = circumference - percentage / 100 * circumference;
38
+ return /* @__PURE__ */ jsxs("div", {
39
+ className: cn("relative flex flex-col items-center gap-1", styles.container),
40
+ children: [
41
+ /* @__PURE__ */ jsxs("svg", {
42
+ className: "absolute -rotate-90",
43
+ width: styles.ring,
44
+ height: styles.ring,
45
+ viewBox: `0 0 ${styles.ring} ${styles.ring}`,
46
+ children: [/* @__PURE__ */ jsx("circle", {
47
+ cx: styles.ring / 2,
48
+ cy: styles.ring / 2,
49
+ r: radius,
50
+ fill: "none",
51
+ strokeWidth: styles.stroke,
52
+ className: "stroke-muted"
53
+ }), /* @__PURE__ */ jsx("circle", {
54
+ cx: styles.ring / 2,
55
+ cy: styles.ring / 2,
56
+ r: radius,
57
+ fill: "none",
58
+ strokeWidth: styles.stroke,
59
+ strokeLinecap: "round",
60
+ strokeDasharray: circumference,
61
+ strokeDashoffset,
62
+ className: cn("transition-all duration-500", colorStyles[color])
63
+ })]
64
+ }),
65
+ /* @__PURE__ */ jsx("div", {
66
+ className: "flex h-full flex-col items-center justify-center",
67
+ children: /* @__PURE__ */ jsxs("span", {
68
+ className: cn("font-bold", styles.text),
69
+ children: [Math.round(percentage), "%"]
70
+ })
71
+ }),
72
+ /* @__PURE__ */ jsx("span", {
73
+ className: cn("text-muted-foreground mt-1 truncate", styles.text),
74
+ children: label
75
+ })
76
+ ]
77
+ });
78
+ }
79
+
80
+ //#endregion
81
+ export { MasteryRing };
@@ -0,0 +1,4 @@
1
+ import { DayCalendar } from "./DayCalendar.js";
2
+ import { FlashCard } from "./FlashCard.js";
3
+ import { MasteryRing } from "./MasteryRing.js";
4
+ export { DayCalendar, FlashCard, MasteryRing };
@@ -0,0 +1,5 @@
1
+ import { FlashCard } from "./FlashCard.js";
2
+ import { MasteryRing } from "./MasteryRing.js";
3
+ import { DayCalendar } from "./DayCalendar.js";
4
+
5
+ export { DayCalendar, FlashCard, MasteryRing };
@@ -0,0 +1 @@
1
+ export { };
@@ -0,0 +1 @@
1
+ import "./learning-journey-ui-gamified.docblock.js";
@@ -0,0 +1 @@
1
+ export { };
@@ -0,0 +1,20 @@
1
+ import { registerDocBlocks } from "../libs/contracts/dist/docs/registry.js";
2
+ import "../libs/contracts/dist/docs/index.js";
3
+
4
+ //#region src/docs/learning-journey-ui-gamified.docblock.ts
5
+ registerDocBlocks([{
6
+ id: "docs.examples.learning-journey-ui-gamified",
7
+ title: "Learning Journey UI — Gamified",
8
+ summary: "UI mini-app components for gamified learning: flashcards, mastery, streak/calendar.",
9
+ kind: "reference",
10
+ visibility: "public",
11
+ route: "/docs/examples/learning-journey-ui-gamified",
12
+ tags: [
13
+ "learning",
14
+ "ui",
15
+ "gamified"
16
+ ],
17
+ body: `## Includes\n- Gamified mini-app shell\n- Views: overview, steps, progress, timeline\n- Components: flash card, mastery ring, day calendar\n\n## Notes\n- Compose with design system components.\n- Respect prefers-reduced-motion; keep tap targets large.`
18
+ }]);
19
+
20
+ //#endregion
@@ -1,20 +1,3 @@
1
- import { n as MasteryRing, r as FlashCard, t as DayCalendar } from "./index-C7CBKOil.mjs";
2
- import { i as Overview, n as Progress, r as Steps, t as Timeline } from "./index-DiAD2ivN.mjs";
3
- import { LearningMiniAppProps } from "@lssm/example.learning-journey-ui-shared";
4
- import * as react_jsx_runtime2 from "react/jsx-runtime";
5
-
6
- //#region src/GamifiedMiniApp.d.ts
7
- type GamifiedMiniAppProps = Omit<LearningMiniAppProps, 'progress'> & {
8
- progress?: LearningMiniAppProps['progress'];
9
- };
10
- declare function GamifiedMiniApp({
11
- track,
12
- progress: externalProgress,
13
- onStepComplete: externalOnStepComplete,
14
- onViewChange,
15
- initialView
16
- }: GamifiedMiniAppProps): react_jsx_runtime2.JSX.Element;
17
- //#endregion
18
1
  //#region src/example.d.ts
19
2
  declare const example: {
20
3
  readonly id: "learning-journey-ui-gamified";
@@ -46,4 +29,4 @@ declare const example: {
46
29
  };
47
30
  };
48
31
  //#endregion
49
- export { DayCalendar, FlashCard, GamifiedMiniApp, MasteryRing, Overview, Progress, Steps, Timeline, example };
32
+ export { example as default };
@@ -0,0 +1,34 @@
1
+ //#region src/example.ts
2
+ const example = {
3
+ id: "learning-journey-ui-gamified",
4
+ title: "Learning Journey UI — Gamified",
5
+ summary: "UI mini-app for gamified learning: flashcards, mastery ring, calendar.",
6
+ tags: [
7
+ "learning",
8
+ "ui",
9
+ "gamified"
10
+ ],
11
+ kind: "ui",
12
+ visibility: "public",
13
+ docs: { rootDocId: "docs.examples.learning-journey-ui-gamified" },
14
+ entrypoints: {
15
+ packageName: "@lssm/example.learning-journey-ui-gamified",
16
+ docs: "./docs"
17
+ },
18
+ surfaces: {
19
+ templates: true,
20
+ sandbox: {
21
+ enabled: true,
22
+ modes: ["playground", "markdown"]
23
+ },
24
+ studio: {
25
+ enabled: true,
26
+ installable: true
27
+ },
28
+ mcp: { enabled: true }
29
+ }
30
+ };
31
+ var example_default = example;
32
+
33
+ //#endregion
34
+ export { example_default as default };
@@ -0,0 +1,44 @@
1
+ 'use client';
2
+
3
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+
6
+ //#region ../learning-journey-ui-shared/dist/components/BadgeDisplay.js
7
+ const BADGE_ICONS = {
8
+ studio_first_30m: "🎯",
9
+ platform_tour: "🗺️",
10
+ crm_first_win: "🏆",
11
+ drill_master: "🧠",
12
+ coach_listener: "👂",
13
+ quest_complete: "⭐",
14
+ streak_7: "🔥",
15
+ streak_30: "💎",
16
+ default: "🏅"
17
+ };
18
+ const sizeStyles = {
19
+ sm: "h-6 w-6 text-sm",
20
+ md: "h-8 w-8 text-base",
21
+ lg: "h-10 w-10 text-lg"
22
+ };
23
+ function BadgeDisplay({ badges, maxVisible = 5, size = "md" }) {
24
+ const visibleBadges = badges.slice(0, maxVisible);
25
+ const hiddenCount = badges.length - maxVisible;
26
+ if (badges.length === 0) return /* @__PURE__ */ jsx("div", {
27
+ className: "text-muted-foreground text-sm",
28
+ children: "No badges earned yet"
29
+ });
30
+ return /* @__PURE__ */ jsxs("div", {
31
+ className: "flex items-center gap-1",
32
+ children: [visibleBadges.map((badge) => /* @__PURE__ */ jsx("div", {
33
+ className: cn("flex items-center justify-center rounded-full bg-gradient-to-br from-amber-400/20 to-amber-600/20", sizeStyles[size]),
34
+ title: badge.replace(/_/g, " "),
35
+ children: BADGE_ICONS[badge] ?? BADGE_ICONS.default
36
+ }, badge)), hiddenCount > 0 && /* @__PURE__ */ jsxs("div", {
37
+ className: cn("text-muted-foreground bg-muted flex items-center justify-center rounded-full", sizeStyles[size], "text-xs font-medium"),
38
+ children: ["+", hiddenCount]
39
+ })]
40
+ });
41
+ }
42
+
43
+ //#endregion
44
+ export { BadgeDisplay };
@@ -0,0 +1,45 @@
1
+ 'use client';
2
+
3
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+
6
+ //#region ../learning-journey-ui-shared/dist/components/StreakCounter.js
7
+ const sizeStyles = {
8
+ sm: {
9
+ container: "gap-1 px-2 py-1",
10
+ icon: "text-base",
11
+ text: "text-xs"
12
+ },
13
+ md: {
14
+ container: "gap-1.5 px-3 py-1.5",
15
+ icon: "text-lg",
16
+ text: "text-sm"
17
+ },
18
+ lg: {
19
+ container: "gap-2 px-4 py-2",
20
+ icon: "text-xl",
21
+ text: "text-base"
22
+ }
23
+ };
24
+ function StreakCounter({ days, isActive = true, size = "md" }) {
25
+ const styles = sizeStyles[size];
26
+ return /* @__PURE__ */ jsxs("div", {
27
+ className: cn("inline-flex items-center rounded-full font-semibold", styles.container, isActive ? "bg-orange-500/10 text-orange-500" : "bg-muted text-muted-foreground"),
28
+ children: [/* @__PURE__ */ jsx("span", {
29
+ className: styles.icon,
30
+ role: "img",
31
+ "aria-label": "streak",
32
+ children: "🔥"
33
+ }), /* @__PURE__ */ jsxs("span", {
34
+ className: styles.text,
35
+ children: [
36
+ days,
37
+ " ",
38
+ days === 1 ? "day" : "days"
39
+ ]
40
+ })]
41
+ });
42
+ }
43
+
44
+ //#endregion
45
+ export { StreakCounter };
@@ -0,0 +1,48 @@
1
+ 'use client';
2
+
3
+ import { Button$1 } from "../libs/design-system/dist/components/atoms/Button.js";
4
+ import { jsx, jsxs } from "react/jsx-runtime";
5
+
6
+ //#region ../learning-journey-ui-shared/dist/components/ViewTabs.js
7
+ const VIEW_LABELS = {
8
+ overview: {
9
+ label: "Overview",
10
+ icon: "📊"
11
+ },
12
+ steps: {
13
+ label: "Steps",
14
+ icon: "📝"
15
+ },
16
+ progress: {
17
+ label: "Progress",
18
+ icon: "📈"
19
+ },
20
+ timeline: {
21
+ label: "Timeline",
22
+ icon: "📅"
23
+ }
24
+ };
25
+ const DEFAULT_VIEWS = [
26
+ "overview",
27
+ "steps",
28
+ "progress",
29
+ "timeline"
30
+ ];
31
+ function ViewTabs({ currentView, onViewChange, availableViews = DEFAULT_VIEWS }) {
32
+ return /* @__PURE__ */ jsx("div", {
33
+ className: "flex flex-wrap gap-2",
34
+ children: availableViews.map((view) => {
35
+ const { label, icon } = VIEW_LABELS[view];
36
+ return /* @__PURE__ */ jsxs(Button$1, {
37
+ variant: currentView === view ? "default" : "outline",
38
+ size: "sm",
39
+ onClick: () => onViewChange(view),
40
+ className: "gap-1.5",
41
+ children: [/* @__PURE__ */ jsx("span", { children: icon }), /* @__PURE__ */ jsx("span", { children: label })]
42
+ }, view);
43
+ })
44
+ });
45
+ }
46
+
47
+ //#endregion
48
+ export { ViewTabs };
@@ -0,0 +1,46 @@
1
+ 'use client';
2
+
3
+ import { Progress } from "../libs/ui-kit-web/dist/ui/progress.js";
4
+ import { cn } from "../libs/ui-kit-web/dist/ui/utils.js";
5
+ import { jsx, jsxs } from "react/jsx-runtime";
6
+
7
+ //#region ../learning-journey-ui-shared/dist/components/XpBar.js
8
+ const sizeStyles = {
9
+ sm: "h-2",
10
+ md: "h-3",
11
+ lg: "h-4"
12
+ };
13
+ const labelSizeStyles = {
14
+ sm: "text-xs",
15
+ md: "text-sm",
16
+ lg: "text-base"
17
+ };
18
+ function XpBar({ current, max, level, showLabel = true, size = "md" }) {
19
+ const percentage = max > 0 ? Math.min(current / max * 100, 100) : 0;
20
+ return /* @__PURE__ */ jsxs("div", {
21
+ className: "w-full space-y-1",
22
+ children: [showLabel && /* @__PURE__ */ jsxs("div", {
23
+ className: cn("flex items-center justify-between", labelSizeStyles[size]),
24
+ children: [/* @__PURE__ */ jsxs("span", {
25
+ className: "text-muted-foreground font-medium",
26
+ children: [level !== void 0 && /* @__PURE__ */ jsxs("span", {
27
+ className: "text-primary mr-1",
28
+ children: ["Lvl ", level]
29
+ }), "XP"]
30
+ }), /* @__PURE__ */ jsxs("span", {
31
+ className: "font-semibold",
32
+ children: [
33
+ current.toLocaleString(),
34
+ " / ",
35
+ max.toLocaleString()
36
+ ]
37
+ })]
38
+ }), /* @__PURE__ */ jsx(Progress, {
39
+ value: percentage,
40
+ className: cn("bg-muted", sizeStyles[size])
41
+ })]
42
+ });
43
+ }
44
+
45
+ //#endregion
46
+ export { XpBar };
@@ -0,0 +1,4 @@
1
+ import { XpBar } from "./XpBar.js";
2
+ import { StreakCounter } from "./StreakCounter.js";
3
+ import { BadgeDisplay } from "./BadgeDisplay.js";
4
+ import { ViewTabs } from "./ViewTabs.js";
@@ -0,0 +1 @@
1
+ import "./learning-journey-ui-shared.docblock.js";
@@ -0,0 +1,20 @@
1
+ import { registerDocBlocks } from "../libs/contracts/dist/docs/registry.js";
2
+ import "../libs/contracts/dist/docs/index.js";
3
+
4
+ //#region ../learning-journey-ui-shared/dist/docs/learning-journey-ui-shared.docblock.js
5
+ registerDocBlocks([{
6
+ id: "docs.examples.learning-journey-ui-shared",
7
+ title: "Learning Journey UI — Shared",
8
+ summary: "Shared UI components and hooks for learning journey mini-apps.",
9
+ kind: "reference",
10
+ visibility: "public",
11
+ route: "/docs/examples/learning-journey-ui-shared",
12
+ tags: [
13
+ "learning",
14
+ "ui",
15
+ "shared"
16
+ ],
17
+ body: `## Includes\n- Hooks: useLearningProgress\n- Components: XpBar, StreakCounter, BadgeDisplay, ViewTabs\n\n## Notes\n- Keep components accessible (labels, focus, contrast).\n- Prefer design-system tokens and components.`
18
+ }]);
19
+
20
+ //#endregion
@@ -0,0 +1 @@
1
+ import { useLearningProgress } from "./useLearningProgress.js";
@@ -0,0 +1,73 @@
1
+ 'use client';
2
+
3
+ import { useCallback, useMemo, useState } from "react";
4
+
5
+ //#region ../learning-journey-ui-shared/dist/hooks/useLearningProgress.js
6
+ /** Default progress state for a new track */
7
+ function createDefaultProgress(trackId) {
8
+ return {
9
+ trackId,
10
+ completedStepIds: [],
11
+ currentStepId: null,
12
+ xpEarned: 0,
13
+ streakDays: 0,
14
+ lastActivityDate: null,
15
+ badges: []
16
+ };
17
+ }
18
+ /** Hook for managing learning progress state */
19
+ function useLearningProgress(track) {
20
+ const [progress, setProgress] = useState(() => createDefaultProgress(track.id));
21
+ const completeStep = useCallback((stepId) => {
22
+ const step = track.steps.find((s) => s.id === stepId);
23
+ if (!step || progress.completedStepIds.includes(stepId)) return;
24
+ setProgress((prev) => {
25
+ const newCompletedIds = [...prev.completedStepIds, stepId];
26
+ const xpReward = step.xpReward ?? 0;
27
+ const nextStep = track.steps.find((s) => !newCompletedIds.includes(s.id));
28
+ const isTrackComplete = newCompletedIds.length === track.steps.length;
29
+ const completionBonus = isTrackComplete ? track.completionRewards?.xpBonus ?? 0 : 0;
30
+ return {
31
+ ...prev,
32
+ completedStepIds: newCompletedIds,
33
+ currentStepId: nextStep?.id ?? null,
34
+ xpEarned: prev.xpEarned + xpReward + completionBonus,
35
+ lastActivityDate: (/* @__PURE__ */ new Date()).toISOString(),
36
+ badges: isTrackComplete && track.completionRewards?.badgeKey ? [...prev.badges, track.completionRewards.badgeKey] : prev.badges
37
+ };
38
+ });
39
+ }, [track, progress.completedStepIds]);
40
+ const resetProgress = useCallback(() => {
41
+ setProgress(createDefaultProgress(track.id));
42
+ }, [track.id]);
43
+ const incrementStreak = useCallback(() => {
44
+ setProgress((prev) => ({
45
+ ...prev,
46
+ streakDays: prev.streakDays + 1,
47
+ lastActivityDate: (/* @__PURE__ */ new Date()).toISOString()
48
+ }));
49
+ }, []);
50
+ return {
51
+ progress,
52
+ stats: useMemo(() => {
53
+ const totalSteps = track.steps.length;
54
+ const completedSteps = progress.completedStepIds.length;
55
+ const percentComplete = totalSteps > 0 ? Math.round(completedSteps / totalSteps * 100) : 0;
56
+ const totalXp = track.totalXp ?? track.steps.reduce((sum, s) => sum + (s.xpReward ?? 0), 0) + (track.completionRewards?.xpBonus ?? 0);
57
+ return {
58
+ totalSteps,
59
+ completedSteps,
60
+ remainingSteps: totalSteps - completedSteps,
61
+ percentComplete,
62
+ totalXp,
63
+ isComplete: completedSteps === totalSteps
64
+ };
65
+ }, [track, progress.completedStepIds]),
66
+ completeStep,
67
+ resetProgress,
68
+ incrementStreak
69
+ };
70
+ }
71
+
72
+ //#endregion
73
+ export { useLearningProgress };
@@ -0,0 +1,8 @@
1
+ import { useLearningProgress } from "./hooks/useLearningProgress.js";
2
+ import "./hooks/index.js";
3
+ import { XpBar } from "./components/XpBar.js";
4
+ import { StreakCounter } from "./components/StreakCounter.js";
5
+ import { BadgeDisplay } from "./components/BadgeDisplay.js";
6
+ import { ViewTabs } from "./components/ViewTabs.js";
7
+ import "./components/index.js";
8
+ import "./docs/index.js";
@@ -0,0 +1,15 @@
1
+ import { registerDocBlocks } from "./registry.js";
2
+
3
+ //#region ../learning-journey-ui-shared/dist/libs/contracts/dist/docs/PUBLISHING.docblock.js
4
+ registerDocBlocks([{
5
+ id: "docs.PUBLISHING",
6
+ title: "Publishing ContractSpec Libraries",
7
+ summary: "This guide describes how we release the ContractSpec libraries to npm. We use a dual-track release system: **Stable** (manual) and **Canary** (automatic).",
8
+ kind: "reference",
9
+ visibility: "public",
10
+ route: "/docs/PUBLISHING",
11
+ tags: ["PUBLISHING"],
12
+ body: "# Publishing ContractSpec Libraries\n\nThis guide describes how we release the ContractSpec libraries to npm. We use a dual-track release system: **Stable** (manual) and **Canary** (automatic).\n\n## Release Tracks\n\n| Track | Branch | npm Tag | Frequency | Versioning | Use Case |\n|-------|--------|---------|-----------|------------|----------|\n| **Stable** | `release` | `latest` | Manual | SemVer (e.g., `1.7.4`) | Production, external users |\n| **Canary** | `main` | `canary` | Every Push | Snapshot (e.g., `1.7.4-canary...`) | Dev, internal testing |\n\n## Prerequisites\n\n- ✅ `NPM_TOKEN` secret is configured in GitHub (owner or automation token with _publish_ scope).\n- ✅ `GITHUB_TOKEN` (built-in) has permissions to create PRs (enabled by default in new repos).\n- ✅ For stable releases: `release` branch exists and is protected.\n\n## Canary Workflow (Automatic)\n\nEvery commit pushed to `main` triggers the `.github/workflows/publish-canary.yml` workflow.\n\n1. **Trigger**: Push to `main`.\n2. **Versioning**: Runs `changeset version --snapshot canary` to generate a temporary snapshot version.\n3. **Publish**: Packages are published to npm with the `canary` tag using `changeset publish --tag canary`.\n\n### Consuming Canary Builds\n\nTo install the latest bleeding-edge version:\n\n```bash\nnpm install @lssm/lib.contracts@canary\n# or\nbun add @lssm/lib.contracts@canary\n```\n\n## Stable Release Workflow (Manual)\n\nStable releases are managed via the `release` branch using the standard [Changesets Action](https://github.com/changesets/action).\n\n1. **Develop on `main`**: Create features and fixes.\n2. **Add Changesets**: Run `bun changeset` to document changes and impact (major/minor/patch).\n3. **Merge to `release`**: When ready to ship, open a PR from `main` to `release` or merge manually.\n4. **\"Version Packages\" PR**:\n - The GitHub Action detects new changesets and automatically creates a Pull Request titled **\"Version Packages\"**.\n - This PR contains the version bumps and updated `CHANGELOG.md` files.\n5. **Merge & Publish**:\n - Review and merge the \"Version Packages\" PR.\n - The Action runs again, detects the versions have been bumped, builds the libraries, and publishes them to npm with the `latest` tag.\n\n### Publishing Steps\n\n1. Ensure all changesets are present on `main`.\n2. Merge `main` into `release`:\n ```bash\n git checkout release\n git pull origin release\n git merge main\n git push origin release\n ```\n3. Go to GitHub Pull Requests. You will see a **\"Version Packages\"** PR created by the bot.\n4. Merge that PR.\n5. The release is now live on npm!\n\n## Manual Verification (Optional)\n\nBefore publishing a new version you can run:\n\n```bash\nbun run build:not-apps\nnpx npm-packlist --json packages/libs/contracts\n```\n\n## Rollback\n\nIf a publish fails mid-way, re-run the workflow once the issue is fixed. Already published packages are skipped automatically. Use `npm deprecate <package>@<version>` if we need to warn consumers about a broken release.\n"
13
+ }]);
14
+
15
+ //#endregion