@contractspec/example.learning-journey-ui-gamified 3.7.6 → 3.7.10

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 (57) hide show
  1. package/.turbo/turbo-build.log +5 -5
  2. package/AGENTS.md +50 -25
  3. package/CHANGELOG.md +32 -0
  4. package/README.md +63 -20
  5. package/dist/GamifiedMiniApp.js +246 -246
  6. package/dist/browser/GamifiedMiniApp.js +246 -246
  7. package/dist/browser/components/DayCalendar.js +1 -1
  8. package/dist/browser/components/FlashCard.js +6 -6
  9. package/dist/browser/components/MasteryRing.js +1 -1
  10. package/dist/browser/components/index.js +100 -100
  11. package/dist/browser/index.js +247 -246
  12. package/dist/browser/views/Overview.js +16 -16
  13. package/dist/browser/views/Progress.js +7 -7
  14. package/dist/browser/views/Steps.js +8 -8
  15. package/dist/browser/views/Timeline.js +8 -8
  16. package/dist/browser/views/index.js +242 -242
  17. package/dist/components/DayCalendar.js +1 -1
  18. package/dist/components/FlashCard.js +6 -6
  19. package/dist/components/MasteryRing.js +1 -1
  20. package/dist/components/index.d.ts +1 -1
  21. package/dist/components/index.js +100 -100
  22. package/dist/index.d.ts +3 -3
  23. package/dist/index.js +247 -246
  24. package/dist/node/GamifiedMiniApp.js +246 -246
  25. package/dist/node/components/DayCalendar.js +1 -1
  26. package/dist/node/components/FlashCard.js +6 -6
  27. package/dist/node/components/MasteryRing.js +1 -1
  28. package/dist/node/components/index.js +100 -100
  29. package/dist/node/index.js +247 -246
  30. package/dist/node/views/Overview.js +16 -16
  31. package/dist/node/views/Progress.js +7 -7
  32. package/dist/node/views/Steps.js +8 -8
  33. package/dist/node/views/Timeline.js +8 -8
  34. package/dist/node/views/index.js +242 -242
  35. package/dist/views/Overview.js +16 -16
  36. package/dist/views/Progress.js +7 -7
  37. package/dist/views/Steps.js +8 -8
  38. package/dist/views/Timeline.js +8 -8
  39. package/dist/views/index.d.ts +1 -1
  40. package/dist/views/index.js +242 -242
  41. package/package.json +12 -12
  42. package/src/GamifiedMiniApp.tsx +70 -70
  43. package/src/components/DayCalendar.tsx +41 -41
  44. package/src/components/FlashCard.tsx +83 -83
  45. package/src/components/MasteryRing.tsx +64 -64
  46. package/src/components/index.ts +1 -1
  47. package/src/docs/learning-journey-ui-gamified.docblock.ts +11 -11
  48. package/src/example.ts +25 -25
  49. package/src/index.ts +5 -6
  50. package/src/learning-journey-ui-gamified.feature.ts +12 -12
  51. package/src/views/Overview.tsx +145 -145
  52. package/src/views/Progress.tsx +167 -167
  53. package/src/views/Steps.tsx +40 -40
  54. package/src/views/Timeline.tsx +177 -177
  55. package/src/views/index.ts +1 -1
  56. package/tsconfig.json +7 -8
  57. package/tsdown.config.js +7 -13
@@ -15,7 +15,7 @@ function DayCalendar({
15
15
  const isCurrent = day === currentDay;
16
16
  const isLocked = day > currentDay;
17
17
  return /* @__PURE__ */ jsxDEV("div", {
18
- 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"),
18
+ className: cn("flex h-12 w-12 flex-col items-center justify-center rounded-lg border font-medium text-sm 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"),
19
19
  children: isCompleted ? /* @__PURE__ */ jsxDEV("span", {
20
20
  className: "text-lg",
21
21
  children: "✓"
@@ -1,8 +1,8 @@
1
1
  // src/components/FlashCard.tsx
2
- import { useState } from "react";
3
2
  import { Button } from "@contractspec/lib.design-system";
4
3
  import { Card, CardContent } from "@contractspec/lib.ui-kit-web/ui/card";
5
4
  import { cn } from "@contractspec/lib.ui-kit-web/ui/utils";
5
+ import { useState } from "react";
6
6
  import { jsxDEV } from "react/jsx-dev-runtime";
7
7
  "use client";
8
8
  function FlashCard({
@@ -13,7 +13,7 @@ function FlashCard({
13
13
  }) {
14
14
  const [isFlipped, setIsFlipped] = useState(false);
15
15
  return /* @__PURE__ */ jsxDEV(Card, {
16
- className: cn("relative cursor-pointer overflow-hidden transition-all duration-300", isCurrent && "ring-primary ring-2", isCompleted && "opacity-60"),
16
+ className: cn("relative cursor-pointer overflow-hidden transition-all duration-300", isCurrent && "ring-2 ring-primary", isCompleted && "opacity-60"),
17
17
  onClick: () => !isCompleted && setIsFlipped(!isFlipped),
18
18
  children: /* @__PURE__ */ jsxDEV(CardContent, {
19
19
  className: "p-6",
@@ -28,17 +28,17 @@ function FlashCard({
28
28
  className: "flex-1",
29
29
  children: [
30
30
  /* @__PURE__ */ jsxDEV("h3", {
31
- className: "text-lg font-semibold",
31
+ className: "font-semibold text-lg",
32
32
  children: step.title
33
33
  }, undefined, false, undefined, this),
34
34
  step.description && /* @__PURE__ */ jsxDEV("p", {
35
- className: "text-muted-foreground mt-1 text-sm",
35
+ className: "mt-1 text-muted-foreground text-sm",
36
36
  children: step.description
37
37
  }, undefined, false, undefined, this)
38
38
  ]
39
39
  }, undefined, true, undefined, this),
40
40
  step.xpReward && /* @__PURE__ */ jsxDEV("span", {
41
- className: "rounded-full bg-green-500/10 px-2 py-1 text-xs font-semibold text-green-500",
41
+ className: "rounded-full bg-green-500/10 px-2 py-1 font-semibold text-green-500 text-xs",
42
42
  children: [
43
43
  "+",
44
44
  step.xpReward,
@@ -54,7 +54,7 @@ function FlashCard({
54
54
  children: "✓"
55
55
  }, undefined, false, undefined, this),
56
56
  /* @__PURE__ */ jsxDEV("span", {
57
- className: "text-sm font-medium",
57
+ className: "font-medium text-sm",
58
58
  children: "Completed"
59
59
  }, undefined, false, undefined, this)
60
60
  ]
@@ -64,7 +64,7 @@ function MasteryRing({
64
64
  }, undefined, true, undefined, this)
65
65
  }, undefined, false, undefined, this),
66
66
  /* @__PURE__ */ jsxDEV("span", {
67
- className: cn("text-muted-foreground mt-1 truncate", styles.text),
67
+ className: cn("mt-1 truncate text-muted-foreground", styles.text),
68
68
  children: label
69
69
  }, undefined, false, undefined, this)
70
70
  ]
@@ -1,9 +1,82 @@
1
+ // src/components/MasteryRing.tsx
2
+ import { cn } from "@contractspec/lib.ui-kit-web/ui/utils";
3
+ import { jsxDEV } from "react/jsx-dev-runtime";
4
+ "use client";
5
+ var sizeStyles = {
6
+ sm: { container: "h-16 w-16", text: "text-xs", ring: 48, stroke: 4 },
7
+ md: { container: "h-24 w-24", text: "text-sm", ring: 72, stroke: 6 },
8
+ lg: { container: "h-32 w-32", text: "text-base", ring: 96, stroke: 8 }
9
+ };
10
+ var colorStyles = {
11
+ green: "stroke-green-500",
12
+ blue: "stroke-blue-500",
13
+ violet: "stroke-violet-500",
14
+ orange: "stroke-orange-500"
15
+ };
16
+ function MasteryRing({
17
+ label,
18
+ percentage,
19
+ size = "md",
20
+ color = "violet"
21
+ }) {
22
+ const styles = sizeStyles[size];
23
+ const radius = (styles.ring - styles.stroke) / 2;
24
+ const circumference = 2 * Math.PI * radius;
25
+ const strokeDashoffset = circumference - percentage / 100 * circumference;
26
+ return /* @__PURE__ */ jsxDEV("div", {
27
+ className: cn("relative flex flex-col items-center gap-1", styles.container),
28
+ children: [
29
+ /* @__PURE__ */ jsxDEV("svg", {
30
+ className: "absolute -rotate-90",
31
+ width: styles.ring,
32
+ height: styles.ring,
33
+ viewBox: `0 0 ${styles.ring} ${styles.ring}`,
34
+ children: [
35
+ /* @__PURE__ */ jsxDEV("circle", {
36
+ cx: styles.ring / 2,
37
+ cy: styles.ring / 2,
38
+ r: radius,
39
+ fill: "none",
40
+ strokeWidth: styles.stroke,
41
+ className: "stroke-muted"
42
+ }, undefined, false, undefined, this),
43
+ /* @__PURE__ */ jsxDEV("circle", {
44
+ cx: styles.ring / 2,
45
+ cy: styles.ring / 2,
46
+ r: radius,
47
+ fill: "none",
48
+ strokeWidth: styles.stroke,
49
+ strokeLinecap: "round",
50
+ strokeDasharray: circumference,
51
+ strokeDashoffset,
52
+ className: cn("transition-all duration-500", colorStyles[color])
53
+ }, undefined, false, undefined, this)
54
+ ]
55
+ }, undefined, true, undefined, this),
56
+ /* @__PURE__ */ jsxDEV("div", {
57
+ className: "flex h-full flex-col items-center justify-center",
58
+ children: /* @__PURE__ */ jsxDEV("span", {
59
+ className: cn("font-bold", styles.text),
60
+ children: [
61
+ Math.round(percentage),
62
+ "%"
63
+ ]
64
+ }, undefined, true, undefined, this)
65
+ }, undefined, false, undefined, this),
66
+ /* @__PURE__ */ jsxDEV("span", {
67
+ className: cn("mt-1 truncate text-muted-foreground", styles.text),
68
+ children: label
69
+ }, undefined, false, undefined, this)
70
+ ]
71
+ }, undefined, true, undefined, this);
72
+ }
73
+
1
74
  // src/components/FlashCard.tsx
2
- import { useState } from "react";
3
75
  import { Button } from "@contractspec/lib.design-system";
4
76
  import { Card, CardContent } from "@contractspec/lib.ui-kit-web/ui/card";
5
- import { cn } from "@contractspec/lib.ui-kit-web/ui/utils";
6
- import { jsxDEV } from "react/jsx-dev-runtime";
77
+ import { cn as cn2 } from "@contractspec/lib.ui-kit-web/ui/utils";
78
+ import { useState } from "react";
79
+ import { jsxDEV as jsxDEV2 } from "react/jsx-dev-runtime";
7
80
  "use client";
8
81
  function FlashCard({
9
82
  step,
@@ -12,33 +85,33 @@ function FlashCard({
12
85
  onComplete
13
86
  }) {
14
87
  const [isFlipped, setIsFlipped] = useState(false);
15
- return /* @__PURE__ */ jsxDEV(Card, {
16
- className: cn("relative cursor-pointer overflow-hidden transition-all duration-300", isCurrent && "ring-primary ring-2", isCompleted && "opacity-60"),
88
+ return /* @__PURE__ */ jsxDEV2(Card, {
89
+ className: cn2("relative cursor-pointer overflow-hidden transition-all duration-300", isCurrent && "ring-2 ring-primary", isCompleted && "opacity-60"),
17
90
  onClick: () => !isCompleted && setIsFlipped(!isFlipped),
18
- children: /* @__PURE__ */ jsxDEV(CardContent, {
91
+ children: /* @__PURE__ */ jsxDEV2(CardContent, {
19
92
  className: "p-6",
20
93
  children: [
21
- /* @__PURE__ */ jsxDEV("div", {
22
- className: cn("space-y-4 transition-opacity duration-200", isFlipped ? "opacity-0" : "opacity-100"),
94
+ /* @__PURE__ */ jsxDEV2("div", {
95
+ className: cn2("space-y-4 transition-opacity duration-200", isFlipped ? "opacity-0" : "opacity-100"),
23
96
  children: [
24
- /* @__PURE__ */ jsxDEV("div", {
97
+ /* @__PURE__ */ jsxDEV2("div", {
25
98
  className: "flex items-start justify-between",
26
99
  children: [
27
- /* @__PURE__ */ jsxDEV("div", {
100
+ /* @__PURE__ */ jsxDEV2("div", {
28
101
  className: "flex-1",
29
102
  children: [
30
- /* @__PURE__ */ jsxDEV("h3", {
31
- className: "text-lg font-semibold",
103
+ /* @__PURE__ */ jsxDEV2("h3", {
104
+ className: "font-semibold text-lg",
32
105
  children: step.title
33
106
  }, undefined, false, undefined, this),
34
- step.description && /* @__PURE__ */ jsxDEV("p", {
35
- className: "text-muted-foreground mt-1 text-sm",
107
+ step.description && /* @__PURE__ */ jsxDEV2("p", {
108
+ className: "mt-1 text-muted-foreground text-sm",
36
109
  children: step.description
37
110
  }, undefined, false, undefined, this)
38
111
  ]
39
112
  }, undefined, true, undefined, this),
40
- step.xpReward && /* @__PURE__ */ jsxDEV("span", {
41
- className: "rounded-full bg-green-500/10 px-2 py-1 text-xs font-semibold text-green-500",
113
+ step.xpReward && /* @__PURE__ */ jsxDEV2("span", {
114
+ className: "rounded-full bg-green-500/10 px-2 py-1 font-semibold text-green-500 text-xs",
42
115
  children: [
43
116
  "+",
44
117
  step.xpReward,
@@ -47,41 +120,41 @@ function FlashCard({
47
120
  }, undefined, true, undefined, this)
48
121
  ]
49
122
  }, undefined, true, undefined, this),
50
- isCompleted && /* @__PURE__ */ jsxDEV("div", {
123
+ isCompleted && /* @__PURE__ */ jsxDEV2("div", {
51
124
  className: "flex items-center gap-2 text-green-500",
52
125
  children: [
53
- /* @__PURE__ */ jsxDEV("span", {
126
+ /* @__PURE__ */ jsxDEV2("span", {
54
127
  children: "✓"
55
128
  }, undefined, false, undefined, this),
56
- /* @__PURE__ */ jsxDEV("span", {
57
- className: "text-sm font-medium",
129
+ /* @__PURE__ */ jsxDEV2("span", {
130
+ className: "font-medium text-sm",
58
131
  children: "Completed"
59
132
  }, undefined, false, undefined, this)
60
133
  ]
61
134
  }, undefined, true, undefined, this),
62
- isCurrent && !isCompleted && /* @__PURE__ */ jsxDEV("p", {
135
+ isCurrent && !isCompleted && /* @__PURE__ */ jsxDEV2("p", {
63
136
  className: "text-muted-foreground text-xs",
64
137
  children: "Tap to reveal action"
65
138
  }, undefined, false, undefined, this)
66
139
  ]
67
140
  }, undefined, true, undefined, this),
68
- isFlipped && !isCompleted && /* @__PURE__ */ jsxDEV("div", {
141
+ isFlipped && !isCompleted && /* @__PURE__ */ jsxDEV2("div", {
69
142
  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",
70
143
  children: [
71
- /* @__PURE__ */ jsxDEV("p", {
144
+ /* @__PURE__ */ jsxDEV2("p", {
72
145
  className: "text-center text-sm",
73
146
  children: step.instructions ?? "Complete this step to earn XP"
74
147
  }, undefined, false, undefined, this),
75
- /* @__PURE__ */ jsxDEV("div", {
148
+ /* @__PURE__ */ jsxDEV2("div", {
76
149
  className: "flex gap-2",
77
150
  children: [
78
- /* @__PURE__ */ jsxDEV(Button, {
151
+ /* @__PURE__ */ jsxDEV2(Button, {
79
152
  variant: "outline",
80
153
  size: "sm",
81
154
  onClick: () => setIsFlipped(false),
82
155
  children: "Back"
83
156
  }, undefined, false, undefined, this),
84
- /* @__PURE__ */ jsxDEV(Button, {
157
+ /* @__PURE__ */ jsxDEV2(Button, {
85
158
  size: "sm",
86
159
  onClick: (e) => {
87
160
  e.stopPropagation();
@@ -98,79 +171,6 @@ function FlashCard({
98
171
  }, undefined, false, undefined, this);
99
172
  }
100
173
 
101
- // src/components/MasteryRing.tsx
102
- import { cn as cn2 } from "@contractspec/lib.ui-kit-web/ui/utils";
103
- import { jsxDEV as jsxDEV2 } from "react/jsx-dev-runtime";
104
- "use client";
105
- var sizeStyles = {
106
- sm: { container: "h-16 w-16", text: "text-xs", ring: 48, stroke: 4 },
107
- md: { container: "h-24 w-24", text: "text-sm", ring: 72, stroke: 6 },
108
- lg: { container: "h-32 w-32", text: "text-base", ring: 96, stroke: 8 }
109
- };
110
- var colorStyles = {
111
- green: "stroke-green-500",
112
- blue: "stroke-blue-500",
113
- violet: "stroke-violet-500",
114
- orange: "stroke-orange-500"
115
- };
116
- function MasteryRing({
117
- label,
118
- percentage,
119
- size = "md",
120
- color = "violet"
121
- }) {
122
- const styles = sizeStyles[size];
123
- const radius = (styles.ring - styles.stroke) / 2;
124
- const circumference = 2 * Math.PI * radius;
125
- const strokeDashoffset = circumference - percentage / 100 * circumference;
126
- return /* @__PURE__ */ jsxDEV2("div", {
127
- className: cn2("relative flex flex-col items-center gap-1", styles.container),
128
- children: [
129
- /* @__PURE__ */ jsxDEV2("svg", {
130
- className: "absolute -rotate-90",
131
- width: styles.ring,
132
- height: styles.ring,
133
- viewBox: `0 0 ${styles.ring} ${styles.ring}`,
134
- children: [
135
- /* @__PURE__ */ jsxDEV2("circle", {
136
- cx: styles.ring / 2,
137
- cy: styles.ring / 2,
138
- r: radius,
139
- fill: "none",
140
- strokeWidth: styles.stroke,
141
- className: "stroke-muted"
142
- }, undefined, false, undefined, this),
143
- /* @__PURE__ */ jsxDEV2("circle", {
144
- cx: styles.ring / 2,
145
- cy: styles.ring / 2,
146
- r: radius,
147
- fill: "none",
148
- strokeWidth: styles.stroke,
149
- strokeLinecap: "round",
150
- strokeDasharray: circumference,
151
- strokeDashoffset,
152
- className: cn2("transition-all duration-500", colorStyles[color])
153
- }, undefined, false, undefined, this)
154
- ]
155
- }, undefined, true, undefined, this),
156
- /* @__PURE__ */ jsxDEV2("div", {
157
- className: "flex h-full flex-col items-center justify-center",
158
- children: /* @__PURE__ */ jsxDEV2("span", {
159
- className: cn2("font-bold", styles.text),
160
- children: [
161
- Math.round(percentage),
162
- "%"
163
- ]
164
- }, undefined, true, undefined, this)
165
- }, undefined, false, undefined, this),
166
- /* @__PURE__ */ jsxDEV2("span", {
167
- className: cn2("text-muted-foreground mt-1 truncate", styles.text),
168
- children: label
169
- }, undefined, false, undefined, this)
170
- ]
171
- }, undefined, true, undefined, this);
172
- }
173
-
174
174
  // src/components/DayCalendar.tsx
175
175
  import { cn as cn3 } from "@contractspec/lib.ui-kit-web/ui/utils";
176
176
  import { jsxDEV as jsxDEV3, Fragment } from "react/jsx-dev-runtime";
@@ -188,7 +188,7 @@ function DayCalendar({
188
188
  const isCurrent = day === currentDay;
189
189
  const isLocked = day > currentDay;
190
190
  return /* @__PURE__ */ jsxDEV3("div", {
191
- className: cn3("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"),
191
+ className: cn3("flex h-12 w-12 flex-col items-center justify-center rounded-lg border font-medium text-sm 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"),
192
192
  children: isCompleted ? /* @__PURE__ */ jsxDEV3("span", {
193
193
  className: "text-lg",
194
194
  children: "✓"