@pure-ds/storybook 0.1.4 → 0.1.5

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.
@@ -1,5 +1,5 @@
1
1
  {
2
- "generatedAt": "2025-12-16T13:26:32.466Z",
2
+ "generatedAt": "2025-12-16T13:32:15.533Z",
3
3
  "sources": {
4
4
  "customElements": "custom-elements.json",
5
5
  "ontology": "src\\js\\pds-core\\pds-ontology.js",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pure-ds/storybook",
3
- "version": "0.1.4",
3
+ "version": "0.1.5",
4
4
  "description": "Storybook showcase for Pure Design System with live configuration",
5
5
  "type": "module",
6
6
  "private": false,
@@ -32,6 +32,13 @@ console.log('Copying source...');
32
32
  rmSync(destSource, { recursive: true, force: true });
33
33
  cpSync(srcSource, destSource, { recursive: true });
34
34
 
35
+ // Copy pds-configurator source
36
+ console.log('Copying pds-configurator...');
37
+ const pdsConfiguratorSrc = join(monorepoRoot, 'packages/pds-configurator/src');
38
+ const destPdsConfigurator = join(destSource, 'js/pds-configurator');
39
+ mkdirSync(destPdsConfigurator, { recursive: true });
40
+ cpSync(pdsConfiguratorSrc, destPdsConfigurator, { recursive: true });
41
+
35
42
  // Copy custom-elements.json
36
43
  console.log('Copying custom-elements.json...');
37
44
  cpSync(join(monorepoRoot, 'custom-elements.json'), join(packageRoot, 'custom-elements.json'));
@@ -0,0 +1,153 @@
1
+ /**
2
+ * Convert a raw PDS token object into a Figma-friendly token structure.
3
+ *
4
+ * - Input: your PDS JSON (colors, spacing, radius, typography, shadows, layout, transitions, zIndex, icons, ...)
5
+ * - Output: deeply equivalent tree where every primitive leaf becomes:
6
+ * { value: ..., type: "color" | "dimension" | "fontSize" | ... }
7
+ *
8
+ * This targets Figma / Dev Mode / Tokens Studio style where:
9
+ * - leaf tokens have `value` and `type`
10
+ * - groups remain nested
11
+ */
12
+ export function figmafyTokens(rawTokens) {
13
+ function detectType(path, key, value) {
14
+ const root = path[0];
15
+
16
+ // 1) Root-level heuristics
17
+ if (root === "colors") {
18
+ // Treat scheme as mode string, not color
19
+ if (key === "scheme") return "string";
20
+ return "color";
21
+ }
22
+
23
+ if (root === "spacing" || root === "radius" || root === "borderWidths") {
24
+ return "dimension";
25
+ }
26
+
27
+ if (root === "typography") {
28
+ const group = path[1];
29
+ if (group === "fontFamily") return "fontFamily";
30
+ if (group === "fontSize") return "fontSize";
31
+ if (group === "fontWeight") return "fontWeight";
32
+ if (group === "lineHeight") return "lineHeight";
33
+ return "string";
34
+ }
35
+
36
+ if (root === "shadows") {
37
+ return "shadow";
38
+ }
39
+
40
+ if (root === "layout") {
41
+ // maxWidth, breakpoints, pageMargin, etc. → dimensions
42
+ return "dimension";
43
+ }
44
+
45
+ if (root === "transitions") {
46
+ // e.g. "90ms"
47
+ return "duration";
48
+ }
49
+
50
+ if (root === "zIndex") {
51
+ // dropdown, modal, etc.
52
+ return "number";
53
+ }
54
+
55
+ if (root === "icons") {
56
+ // defaultSize & sizes.* are dimensions, the rest config strings
57
+ if (key === "defaultSize" || path.includes("sizes")) {
58
+ return "dimension";
59
+ }
60
+ return "string";
61
+ }
62
+
63
+ // 2) Generic heuristics (fallbacks)
64
+ if (typeof value === "number") {
65
+ return "number";
66
+ }
67
+
68
+ if (typeof value === "string") {
69
+ // duration: "150ms"
70
+ if (/^\d+(\.\d+)?ms$/.test(value)) return "duration";
71
+
72
+ // dimension: "16px", "1.5rem", "100%", etc.
73
+ if (/^\d+(\.\d+)?(px|rem|em|vh|vw|%)$/.test(value)) return "dimension";
74
+
75
+ // color: hex, rgb/rgba/hsl/hsla/oklab/etc.
76
+ if (
77
+ /^#([0-9a-fA-F]{3}|[0-9a-fA-F]{6}|[0-9a-fA-F]{8})$/.test(value) ||
78
+ /^(rgb|rgba|hsl|hsla|oklab|lab)\(/.test(value)
79
+ ) {
80
+ return "color";
81
+ }
82
+ }
83
+
84
+ // If we don't know, leave it typeless so tools can decide
85
+ return undefined;
86
+ }
87
+
88
+ function isPlainObject(x) {
89
+ return x !== null && typeof x === "object" && !Array.isArray(x);
90
+ }
91
+
92
+ function walk(node, path = []) {
93
+ if (node == null) return node;
94
+
95
+ // Arrays: map recursively (rare in your current structure, but safe)
96
+ if (Array.isArray(node)) {
97
+ return node.map((item, index) => walk(item, path.concat(String(index))));
98
+ }
99
+
100
+ // Objects: either a nested group or already a token
101
+ if (isPlainObject(node)) {
102
+ // If it already looks like a token leaf, keep it as-is
103
+ if (
104
+ Object.prototype.hasOwnProperty.call(node, "value") &&
105
+ (Object.prototype.hasOwnProperty.call(node, "type") ||
106
+ Object.keys(node).length === 1)
107
+ ) {
108
+ return node;
109
+ }
110
+
111
+ const result = {};
112
+ for (const [key, value] of Object.entries(node)) {
113
+ result[key] = walk(value, path.concat(key));
114
+ }
115
+ return result;
116
+ }
117
+
118
+ // Primitive leaf → convert to { value, type? }
119
+ const key = path[path.length - 1] ?? "";
120
+ const type = detectType(path, key, node);
121
+
122
+ let value = node;
123
+
124
+ // Normalize numbers for zIndex & other numeric tokens
125
+ if (type === "number" && typeof value === "string") {
126
+ const num = Number(value);
127
+ if (!Number.isNaN(num)) {
128
+ value = num;
129
+ }
130
+ }
131
+
132
+ // Return leaf token
133
+ if (type) {
134
+ return { value, type };
135
+ }
136
+ return { value };
137
+ }
138
+
139
+ return walk(rawTokens, []);
140
+ }
141
+
142
+ /*
143
+ Usage example:
144
+
145
+ import { figmafyTokens } from './figmafyTokens.mjs';
146
+ import rawPdsTokens from './design-tokens.pds.json' assert { type: 'json' };
147
+
148
+ const figmaTokens = figmafyTokens(rawPdsTokens);
149
+
150
+ // Now:
151
+ /// - write figmaTokens to design-tokens.figma.json
152
+ /// - or feed it directly to Tokens Studio / Figma Dev Mode tooling.
153
+ */