@pure-ds/storybook 0.1.0
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/.storybook/addons/description/preview.js +15 -0
- package/.storybook/addons/description/register.js +60 -0
- package/.storybook/addons/html-preview/Panel.jsx +327 -0
- package/.storybook/addons/html-preview/constants.js +6 -0
- package/.storybook/addons/html-preview/preview.js +178 -0
- package/.storybook/addons/html-preview/register.js +16 -0
- package/.storybook/addons/pds-configurator/SearchTool.js +44 -0
- package/.storybook/addons/pds-configurator/Tool.js +30 -0
- package/.storybook/addons/pds-configurator/constants.js +9 -0
- package/.storybook/addons/pds-configurator/preview.js +159 -0
- package/.storybook/addons/pds-configurator/register.js +24 -0
- package/.storybook/docs.css +35 -0
- package/.storybook/htmlPreview.css +103 -0
- package/.storybook/htmlPreview.js +271 -0
- package/.storybook/main.js +160 -0
- package/.storybook/preview-body.html +48 -0
- package/.storybook/preview-head.html +11 -0
- package/.storybook/preview.js +1563 -0
- package/README.md +266 -0
- package/bin/index.js +40 -0
- package/dist/pds-reference.json +2101 -0
- package/package.json +45 -0
- package/pds.config.js +6 -0
- package/public/assets/css/app.css +1216 -0
- package/public/assets/data/auto-design-advanced.json +704 -0
- package/public/assets/data/auto-design-simple.json +123 -0
- package/public/assets/img/icon-512x512.png +0 -0
- package/public/assets/img/logo-trans.png +0 -0
- package/public/assets/img/logo.png +0 -0
- package/public/assets/js/app.js +15088 -0
- package/public/assets/js/app.js.map +7 -0
- package/public/assets/js/lit.js +1176 -0
- package/public/assets/js/lit.js.map +7 -0
- package/public/assets/js/pds.js +9801 -0
- package/public/assets/js/pds.js.map +7 -0
- package/public/assets/pds/components/pds-calendar.js +837 -0
- package/public/assets/pds/components/pds-drawer.js +857 -0
- package/public/assets/pds/components/pds-icon.js +338 -0
- package/public/assets/pds/components/pds-jsonform.js +1775 -0
- package/public/assets/pds/components/pds-richtext.js +1035 -0
- package/public/assets/pds/components/pds-scrollrow.js +331 -0
- package/public/assets/pds/components/pds-splitpanel.js +401 -0
- package/public/assets/pds/components/pds-tabstrip.js +251 -0
- package/public/assets/pds/components/pds-toaster.js +446 -0
- package/public/assets/pds/components/pds-upload.js +657 -0
- package/public/assets/pds/custom-elements.json +2003 -0
- package/public/assets/pds/icons/pds-icons.svg +498 -0
- package/public/assets/pds/pds-css-complete.json +1861 -0
- package/public/assets/pds/pds-runtime-config.json +11 -0
- package/public/assets/pds/pds.css-data.json +2152 -0
- package/public/assets/pds/styles/pds-components.css +1944 -0
- package/public/assets/pds/styles/pds-components.css.js +3895 -0
- package/public/assets/pds/styles/pds-primitives.css +352 -0
- package/public/assets/pds/styles/pds-primitives.css.js +711 -0
- package/public/assets/pds/styles/pds-styles.css +3761 -0
- package/public/assets/pds/styles/pds-styles.css.js +7529 -0
- package/public/assets/pds/styles/pds-tokens.css +699 -0
- package/public/assets/pds/styles/pds-tokens.css.js +1405 -0
- package/public/assets/pds/styles/pds-utilities.css +763 -0
- package/public/assets/pds/styles/pds-utilities.css.js +1533 -0
- package/public/assets/pds/vscode-custom-data.json +824 -0
- package/scripts/build-pds-reference.mjs +807 -0
- package/scripts/generate-stories.js +542 -0
- package/scripts/package-build.js +86 -0
- package/src/js/app.js +17 -0
- package/src/js/common/ask.js +208 -0
- package/src/js/common/common.js +20 -0
- package/src/js/common/font-loader.js +200 -0
- package/src/js/common/msg.js +90 -0
- package/src/js/lit.js +40 -0
- package/src/js/pds-core/pds-config.js +1162 -0
- package/src/js/pds-core/pds-enhancer-metadata.js +75 -0
- package/src/js/pds-core/pds-enhancers.js +357 -0
- package/src/js/pds-core/pds-enums.js +86 -0
- package/src/js/pds-core/pds-generator.js +5317 -0
- package/src/js/pds-core/pds-ontology.js +256 -0
- package/src/js/pds-core/pds-paths.js +109 -0
- package/src/js/pds-core/pds-query.js +571 -0
- package/src/js/pds-core/pds-registry.js +129 -0
- package/src/js/pds-core/pds.d.ts +129 -0
- package/src/js/pds.d.ts +408 -0
- package/src/js/pds.js +1579 -0
- package/src/pds-core/pds-api.js +105 -0
- package/stories/GettingStarted.md +96 -0
- package/stories/GettingStarted.stories.js +144 -0
- package/stories/WhatIsPDS.md +194 -0
- package/stories/WhatIsPDS.stories.js +144 -0
- package/stories/components/PdsCalendar.stories.js +263 -0
- package/stories/components/PdsDrawer.stories.js +623 -0
- package/stories/components/PdsIcon.stories.js +78 -0
- package/stories/components/PdsJsonform.stories.js +1444 -0
- package/stories/components/PdsRichtext.stories.js +367 -0
- package/stories/components/PdsScrollrow.stories.js +140 -0
- package/stories/components/PdsSplitpanel.stories.js +502 -0
- package/stories/components/PdsTabstrip.stories.js +442 -0
- package/stories/components/PdsToaster.stories.js +186 -0
- package/stories/components/PdsUpload.stories.js +66 -0
- package/stories/enhancements/Dropdowns.stories.js +185 -0
- package/stories/enhancements/InteractiveStates.stories.js +625 -0
- package/stories/enhancements/MeshGradients.stories.js +320 -0
- package/stories/enhancements/OpenGroups.stories.js +227 -0
- package/stories/enhancements/RangeSliders.stories.js +232 -0
- package/stories/enhancements/RequiredFields.stories.js +189 -0
- package/stories/enhancements/Toggles.stories.js +167 -0
- package/stories/foundations/Colors.stories.js +283 -0
- package/stories/foundations/Icons.stories.js +305 -0
- package/stories/foundations/SmartSurfaces.stories.js +367 -0
- package/stories/foundations/Spacing.stories.js +175 -0
- package/stories/foundations/Typography.stories.js +960 -0
- package/stories/foundations/ZIndex.stories.js +325 -0
- package/stories/patterns/BorderEffects.stories.js +72 -0
- package/stories/patterns/Layout.stories.js +99 -0
- package/stories/patterns/Utilities.stories.js +107 -0
- package/stories/primitives/Accordion.stories.js +359 -0
- package/stories/primitives/Alerts.stories.js +64 -0
- package/stories/primitives/Badges.stories.js +183 -0
- package/stories/primitives/Buttons.stories.js +229 -0
- package/stories/primitives/Cards.stories.js +353 -0
- package/stories/primitives/FormGroups.stories.js +569 -0
- package/stories/primitives/Forms.stories.js +131 -0
- package/stories/primitives/Media.stories.js +203 -0
- package/stories/primitives/Tables.stories.js +232 -0
- package/stories/reference/ReferenceCatalog.stories.js +28 -0
- package/stories/reference/reference-catalog.js +413 -0
- package/stories/reference/reference-docs.js +302 -0
- package/stories/reference/reference-helpers.js +310 -0
- package/stories/utilities/GridSystem.stories.js +208 -0
- package/stories/utils/PdsAsk.stories.js +420 -0
- package/stories/utils/toast-utils.js +148 -0
|
@@ -0,0 +1,542 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Story Generator for Pure Design System Storybook
|
|
3
|
+
*
|
|
4
|
+
* Reads pds-ontology.js and pds-demo.js to auto-generate stories
|
|
5
|
+
* organized by best-practice groups.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
import { readFileSync, writeFileSync, mkdirSync, existsSync } from 'fs';
|
|
9
|
+
import { join, dirname } from 'path';
|
|
10
|
+
import { fileURLToPath } from 'url';
|
|
11
|
+
|
|
12
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
13
|
+
const __dirname = dirname(__filename);
|
|
14
|
+
const ROOT_DIR = join(__dirname, '../../..');
|
|
15
|
+
const STORIES_DIR = join(__dirname, '../stories');
|
|
16
|
+
|
|
17
|
+
// Load ontology
|
|
18
|
+
const ontologyPath = join(ROOT_DIR, 'src/js/pds-core/pds-ontology.js');
|
|
19
|
+
const ontologyContent = readFileSync(ontologyPath, 'utf-8');
|
|
20
|
+
|
|
21
|
+
// Extract ontology object (simplified parsing)
|
|
22
|
+
const ontologyMatch = ontologyContent.match(/export const ontology = ({[\s\S]+?});[\s\S]*export default/);
|
|
23
|
+
if (!ontologyMatch) {
|
|
24
|
+
console.error('Failed to parse ontology');
|
|
25
|
+
process.exit(1);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// Load demo content
|
|
29
|
+
const demoPath = join(ROOT_DIR, 'packages/pds-configurator/src/pds-demo.js');
|
|
30
|
+
const demoContent = readFileSync(demoPath, 'utf-8');
|
|
31
|
+
|
|
32
|
+
// Story groups based on design system best practices
|
|
33
|
+
const STORY_GROUPS = {
|
|
34
|
+
foundations: {
|
|
35
|
+
title: 'Foundations',
|
|
36
|
+
description: 'Design tokens - colors, typography, spacing, icons',
|
|
37
|
+
stories: ['Colors', 'Typography', 'Spacing', 'Icons']
|
|
38
|
+
},
|
|
39
|
+
primitives: {
|
|
40
|
+
title: 'Primitives',
|
|
41
|
+
description: 'Basic UI elements - buttons, forms, cards, badges',
|
|
42
|
+
stories: ['Buttons', 'Forms', 'Cards', 'Badges', 'Alerts', 'Surfaces']
|
|
43
|
+
},
|
|
44
|
+
components: {
|
|
45
|
+
title: 'Components',
|
|
46
|
+
description: 'Web Components - rich interactive UI elements',
|
|
47
|
+
stories: [
|
|
48
|
+
'pds-icon',
|
|
49
|
+
'pds-drawer',
|
|
50
|
+
'pds-tabstrip',
|
|
51
|
+
'pds-upload',
|
|
52
|
+
'pds-toaster',
|
|
53
|
+
'pds-richtext',
|
|
54
|
+
'pds-jsonform',
|
|
55
|
+
'pds-splitpanel',
|
|
56
|
+
'pds-scrollrow'
|
|
57
|
+
]
|
|
58
|
+
},
|
|
59
|
+
patterns: {
|
|
60
|
+
title: 'Patterns',
|
|
61
|
+
description: 'Layout patterns and utility classes',
|
|
62
|
+
stories: ['Layout', 'Utilities', 'BorderEffects']
|
|
63
|
+
},
|
|
64
|
+
enhancements: {
|
|
65
|
+
title: 'Enhancements',
|
|
66
|
+
description: 'Progressive enhancements for semantic HTML',
|
|
67
|
+
stories: ['Dropdowns', 'Toggles', 'RangeSliders', 'RequiredFields']
|
|
68
|
+
}
|
|
69
|
+
};
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* Extract HTML section from pds-demo.js
|
|
73
|
+
*/
|
|
74
|
+
function extractDemoSection(sectionId) {
|
|
75
|
+
// Try matching by ID or data-section attribute
|
|
76
|
+
const sectionRegex = new RegExp(`<section[^>]*(?:id|data-section)=["']${sectionId}["'][^>]*>([\\s\\S]*?)<\\/section>`, 'i');
|
|
77
|
+
const match = demoContent.match(sectionRegex);
|
|
78
|
+
return match ? match[1].trim() : null;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* Generate story template
|
|
83
|
+
*/
|
|
84
|
+
function generateStoryTemplate(group, storyName, content = '', extraCode = '') {
|
|
85
|
+
const title = storyName.replace(/([A-Z])/g, ' $1').trim();
|
|
86
|
+
const argTypes = `
|
|
87
|
+
preset: {
|
|
88
|
+
control: 'select',
|
|
89
|
+
options: ['default', 'ocean-breeze', 'midnight-steel', 'sunset-vibes', 'forest-calm', 'lavender-dream'],
|
|
90
|
+
description: 'Choose a design preset'
|
|
91
|
+
},
|
|
92
|
+
primaryColor: {
|
|
93
|
+
control: 'color',
|
|
94
|
+
description: 'Override primary color'
|
|
95
|
+
},
|
|
96
|
+
secondaryColor: {
|
|
97
|
+
control: 'color',
|
|
98
|
+
description: 'Override secondary color'
|
|
99
|
+
}`;
|
|
100
|
+
|
|
101
|
+
return `import { html } from 'lit';
|
|
102
|
+
|
|
103
|
+
export default {
|
|
104
|
+
title: '${STORY_GROUPS[group].title}/${title}',
|
|
105
|
+
parameters: {
|
|
106
|
+
docs: {
|
|
107
|
+
description: {
|
|
108
|
+
component: '${STORY_GROUPS[group].description}'
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
},
|
|
112
|
+
argTypes: {${argTypes}
|
|
113
|
+
}
|
|
114
|
+
};
|
|
115
|
+
|
|
116
|
+
export const Default = {
|
|
117
|
+
render: (args) => {
|
|
118
|
+
// Apply preset if changed
|
|
119
|
+
if (args.preset) {
|
|
120
|
+
import('../../../src/js/pds.js').then(({ PDS }) => {
|
|
121
|
+
PDS.applyDesign({ preset: args.preset });
|
|
122
|
+
});
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
// Apply color overrides
|
|
126
|
+
if (args.primaryColor || args.secondaryColor) {
|
|
127
|
+
import('../../../src/js/pds.js').then(({ PDS }) => {
|
|
128
|
+
PDS.applyDesign({
|
|
129
|
+
design: {
|
|
130
|
+
colors: {
|
|
131
|
+
primary: args.primaryColor,
|
|
132
|
+
secondary: args.secondaryColor
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
});
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
${extraCode}
|
|
140
|
+
|
|
141
|
+
return html\`
|
|
142
|
+
<div class="story-container" style="padding: 2rem;">
|
|
143
|
+
${content || `<p>Story content for ${title}</p>`}
|
|
144
|
+
</div>
|
|
145
|
+
\`;
|
|
146
|
+
},
|
|
147
|
+
args: {
|
|
148
|
+
preset: 'default'
|
|
149
|
+
}
|
|
150
|
+
};
|
|
151
|
+
`;
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* Generate foundation stories
|
|
156
|
+
*/
|
|
157
|
+
function generateFoundationStories() {
|
|
158
|
+
console.log('Generating foundation stories...');
|
|
159
|
+
|
|
160
|
+
// Colors - Use custom implementation since pds-demo.js uses dynamic Lit methods
|
|
161
|
+
const colorsCode = `
|
|
162
|
+
const renderColorCard = (name, color) => html\`
|
|
163
|
+
<div class="color-card">
|
|
164
|
+
<div class="color-swatch" style="background-color: var(--color-\${color}-500);"></div>
|
|
165
|
+
<div class="color-info">
|
|
166
|
+
<strong>\${name}</strong>
|
|
167
|
+
<code>var(--color-\${color}-500)</code>
|
|
168
|
+
</div>
|
|
169
|
+
<div class="color-scale" style="--scale-color: var(--color-\${color}-500);">
|
|
170
|
+
\${[50, 100, 200, 300, 400, 500, 600, 700, 800, 900].map(
|
|
171
|
+
(shade) => html\`<div style="--value: \${shade}"></div>\`
|
|
172
|
+
)}
|
|
173
|
+
</div>
|
|
174
|
+
</div>
|
|
175
|
+
\`;
|
|
176
|
+
|
|
177
|
+
const renderColorScale = (color) => html\`
|
|
178
|
+
<div class="color-scale-row">
|
|
179
|
+
\${[50, 100, 200, 300, 400, 500, 600, 700, 800, 900].map(shade => html\`
|
|
180
|
+
<div class="scale-item">
|
|
181
|
+
<div class="swatch" style="background-color: var(--color-\${color}-\${shade})"></div>
|
|
182
|
+
<span class="label">\${shade}</span>
|
|
183
|
+
</div>
|
|
184
|
+
\`)}
|
|
185
|
+
</div>
|
|
186
|
+
\`;
|
|
187
|
+
`;
|
|
188
|
+
|
|
189
|
+
const colorsHTML = `
|
|
190
|
+
<section class="showcase-section" data-section="color-system">
|
|
191
|
+
<h2><pds-icon icon="palette" size="lg" class="icon-primary"></pds-icon> Color System</h2>
|
|
192
|
+
<div class="color-grid">
|
|
193
|
+
\${renderColorCard("Primary", "primary")}
|
|
194
|
+
\${renderColorCard("Secondary", "secondary")}
|
|
195
|
+
\${renderColorCard("Accent", "accent")}
|
|
196
|
+
\${renderColorCard("Success", "success")}
|
|
197
|
+
\${renderColorCard("Warning", "warning")}
|
|
198
|
+
\${renderColorCard("Danger", "danger")}
|
|
199
|
+
\${renderColorCard("Info", "info")}
|
|
200
|
+
</div>
|
|
201
|
+
|
|
202
|
+
<h3>Gray Scale (from Secondary)</h3>
|
|
203
|
+
<div class="gray-scale-grid">
|
|
204
|
+
\${[50, 100, 200, 300, 400, 500, 600, 700, 800].map(
|
|
205
|
+
(shade) => html\`
|
|
206
|
+
<div class="gray-scale-item">
|
|
207
|
+
<div
|
|
208
|
+
class="gray-scale-swatch"
|
|
209
|
+
style="background-color: var(--color-gray-\${shade});"
|
|
210
|
+
title="gray-\${shade}"
|
|
211
|
+
></div>
|
|
212
|
+
<div class="gray-scale-label">\${shade}</div>
|
|
213
|
+
</div>
|
|
214
|
+
\`
|
|
215
|
+
)}
|
|
216
|
+
</div>
|
|
217
|
+
</section>
|
|
218
|
+
`;
|
|
219
|
+
|
|
220
|
+
writeStory('foundations', 'Colors', generateStoryTemplate('foundations', 'Colors', colorsHTML, colorsCode));
|
|
221
|
+
|
|
222
|
+
// Typography
|
|
223
|
+
const typographyHTML = extractDemoSection('typography') || `
|
|
224
|
+
<h1>Heading 1</h1>
|
|
225
|
+
|
|
226
|
+
<h2>Heading 2</h2>
|
|
227
|
+
<h3>Heading 3</h3>
|
|
228
|
+
<h4>Heading 4</h4>
|
|
229
|
+
<h5>Heading 5</h5>
|
|
230
|
+
<h6>Heading 6</h6>
|
|
231
|
+
<p>Body paragraph with <strong>bold</strong>, <em>italic</em>, and <a href="#">link</a> text.</p>
|
|
232
|
+
`;
|
|
233
|
+
|
|
234
|
+
writeStory('foundations', 'Typography', generateStoryTemplate('foundations', 'Typography', typographyHTML));
|
|
235
|
+
|
|
236
|
+
// Spacing
|
|
237
|
+
const spacingHTML = `
|
|
238
|
+
<div style="display: flex; flex-direction: column; gap: var(--spacing-2);">
|
|
239
|
+
<div style="background: var(--color-primary-100); padding: var(--spacing-1);">Spacing 1</div>
|
|
240
|
+
<div style="background: var(--color-primary-200); padding: var(--spacing-2);">Spacing 2</div>
|
|
241
|
+
<div style="background: var(--color-primary-300); padding: var(--spacing-3);">Spacing 3</div>
|
|
242
|
+
<div style="background: var(--color-primary-400); padding: var(--spacing-4);">Spacing 4</div>
|
|
243
|
+
<div style="background: var(--color-primary-500); padding: var(--spacing-5); color: white;">Spacing 5</div>
|
|
244
|
+
</div>
|
|
245
|
+
`;
|
|
246
|
+
|
|
247
|
+
writeStory('foundations', 'Spacing', generateStoryTemplate('foundations', 'Spacing', spacingHTML));
|
|
248
|
+
|
|
249
|
+
// Icons
|
|
250
|
+
const iconsHTML = extractDemoSection('icons') || `
|
|
251
|
+
<div style="display: flex; gap: 1rem; flex-wrap: wrap;">
|
|
252
|
+
<pds-icon icon="heart" size="lg"></pds-icon>
|
|
253
|
+
<pds-icon icon="star" size="lg"></pds-icon>
|
|
254
|
+
<pds-icon icon="user" size="lg"></pds-icon>
|
|
255
|
+
<pds-icon icon="bell" size="lg"></pds-icon>
|
|
256
|
+
<pds-icon icon="magnifying-glass" size="lg"></pds-icon>
|
|
257
|
+
<pds-icon icon="list" size="lg"></pds-icon>
|
|
258
|
+
<pds-icon icon="x" size="lg"></pds-icon>
|
|
259
|
+
<pds-icon icon="check" size="lg"></pds-icon>
|
|
260
|
+
</div>
|
|
261
|
+
`;
|
|
262
|
+
|
|
263
|
+
writeStory('foundations', 'Icons', generateStoryTemplate('foundations', 'Icons', iconsHTML));
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
/**
|
|
267
|
+
* Generate primitive stories
|
|
268
|
+
*/
|
|
269
|
+
function generatePrimitiveStories() {
|
|
270
|
+
console.log('Generating primitive stories...');
|
|
271
|
+
|
|
272
|
+
// Buttons
|
|
273
|
+
const buttonsHTML = extractDemoSection('buttons') || `
|
|
274
|
+
<div style="display: flex; gap: 1rem; flex-wrap: wrap;">
|
|
275
|
+
<button class="btn-primary">Primary</button>
|
|
276
|
+
<button class="btn-secondary">Secondary</button>
|
|
277
|
+
<button class="btn-outline">Outline</button>
|
|
278
|
+
<button class="btn-ghost">Ghost</button>
|
|
279
|
+
<button class="btn-primary" disabled>Disabled</button>
|
|
280
|
+
</div>
|
|
281
|
+
<br/>
|
|
282
|
+
<div style="display: flex; gap: 1rem; flex-wrap: wrap;">
|
|
283
|
+
<button class="btn-primary btn-sm">Small</button>
|
|
284
|
+
<button class="btn-primary">Medium</button>
|
|
285
|
+
<button class="btn-primary btn-lg">Large</button>
|
|
286
|
+
</div>
|
|
287
|
+
`;
|
|
288
|
+
|
|
289
|
+
writeStory('primitives', 'Buttons', generateStoryTemplate('primitives', 'Buttons', buttonsHTML));
|
|
290
|
+
|
|
291
|
+
// Forms
|
|
292
|
+
const formsHTML = extractDemoSection('forms') || `
|
|
293
|
+
<form style="max-width: 400px;">
|
|
294
|
+
<label>
|
|
295
|
+
<span>Text Input</span>
|
|
296
|
+
<input type="text" placeholder="Enter text...">
|
|
297
|
+
</label>
|
|
298
|
+
<label>
|
|
299
|
+
<span>Email</span>
|
|
300
|
+
<input type="email" required placeholder="email@example.com">
|
|
301
|
+
</label>
|
|
302
|
+
<label>
|
|
303
|
+
<span>Select</span>
|
|
304
|
+
<select>
|
|
305
|
+
<option>Option 1</option>
|
|
306
|
+
<option>Option 2</option>
|
|
307
|
+
<option>Option 3</option>
|
|
308
|
+
</select>
|
|
309
|
+
</label>
|
|
310
|
+
<label>
|
|
311
|
+
<span>Textarea</span>
|
|
312
|
+
<textarea rows="4" placeholder="Enter longer text..."></textarea>
|
|
313
|
+
</label>
|
|
314
|
+
<button type="submit" class="btn-primary">Submit</button>
|
|
315
|
+
</form>
|
|
316
|
+
`;
|
|
317
|
+
|
|
318
|
+
writeStory('primitives', 'Forms', generateStoryTemplate('primitives', 'Forms', formsHTML));
|
|
319
|
+
|
|
320
|
+
// Cards
|
|
321
|
+
const cardsHTML = `
|
|
322
|
+
<div style="display: grid; grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); gap: 1rem;">
|
|
323
|
+
<article class="card">
|
|
324
|
+
<h3>Card Title</h3>
|
|
325
|
+
<p>Card content goes here. This is a basic card primitive.</p>
|
|
326
|
+
<button class="btn-primary">Action</button>
|
|
327
|
+
</article>
|
|
328
|
+
<article class="card">
|
|
329
|
+
<h3>Another Card</h3>
|
|
330
|
+
<p>Cards are versatile containers for content.</p>
|
|
331
|
+
<button class="btn-outline">Learn More</button>
|
|
332
|
+
</article>
|
|
333
|
+
</div>
|
|
334
|
+
`;
|
|
335
|
+
|
|
336
|
+
writeStory('primitives', 'Cards', generateStoryTemplate('primitives', 'Cards', cardsHTML));
|
|
337
|
+
|
|
338
|
+
// Badges
|
|
339
|
+
const badgesHTML = `
|
|
340
|
+
<div style="display: flex; gap: 1rem; flex-wrap: wrap; align-items: center;">
|
|
341
|
+
<span class="badge">Default</span>
|
|
342
|
+
<span class="badge badge-primary">Primary</span>
|
|
343
|
+
<span class="badge badge-success">Success</span>
|
|
344
|
+
<span class="badge badge-warning">Warning</span>
|
|
345
|
+
<span class="badge badge-danger">Danger</span>
|
|
346
|
+
<span class="pill">Pill</span>
|
|
347
|
+
</div>
|
|
348
|
+
`;
|
|
349
|
+
|
|
350
|
+
writeStory('primitives', 'Badges', generateStoryTemplate('primitives', 'Badges', badgesHTML));
|
|
351
|
+
|
|
352
|
+
// Alerts
|
|
353
|
+
const alertsHTML = `
|
|
354
|
+
<div style="display: flex; flex-direction: column; gap: 1rem;">
|
|
355
|
+
<div class="alert alert-info">This is an info alert.</div>
|
|
356
|
+
<div class="alert alert-success">This is a success alert.</div>
|
|
357
|
+
<div class="alert alert-warning">This is a warning alert.</div>
|
|
358
|
+
<div class="alert alert-danger">This is a danger alert.</div>
|
|
359
|
+
</div>
|
|
360
|
+
`;
|
|
361
|
+
|
|
362
|
+
writeStory('primitives', 'Alerts', generateStoryTemplate('primitives', 'Alerts', alertsHTML));
|
|
363
|
+
}
|
|
364
|
+
|
|
365
|
+
/**
|
|
366
|
+
* Generate component stories
|
|
367
|
+
*/
|
|
368
|
+
function generateComponentStories() {
|
|
369
|
+
console.log('Generating component stories...');
|
|
370
|
+
|
|
371
|
+
// pds-icon
|
|
372
|
+
writeStory('components', 'PdsIcon', `import { html } from 'lit';
|
|
373
|
+
|
|
374
|
+
export default {
|
|
375
|
+
title: 'PDS/Components/pds-icon',
|
|
376
|
+
parameters: {
|
|
377
|
+
docs: {
|
|
378
|
+
description: {
|
|
379
|
+
component: 'SVG sprite icons with fallbacks'
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
},
|
|
383
|
+
argTypes: {
|
|
384
|
+
icon: {
|
|
385
|
+
control: 'text',
|
|
386
|
+
description: 'Icon name from sprite'
|
|
387
|
+
},
|
|
388
|
+
size: {
|
|
389
|
+
control: 'select',
|
|
390
|
+
options: ['xs', 'sm', 'md', 'lg', 'xl', '2xl'],
|
|
391
|
+
description: 'Named size'
|
|
392
|
+
},
|
|
393
|
+
color: {
|
|
394
|
+
control: 'color',
|
|
395
|
+
description: 'Icon color'
|
|
396
|
+
}
|
|
397
|
+
}
|
|
398
|
+
};
|
|
399
|
+
|
|
400
|
+
export const Default = {
|
|
401
|
+
render: (args) => html\`
|
|
402
|
+
<pds-icon
|
|
403
|
+
icon="\${args.icon}"
|
|
404
|
+
size="\${args.size}"
|
|
405
|
+
color="\${args.color}">
|
|
406
|
+
</pds-icon>
|
|
407
|
+
\`,
|
|
408
|
+
args: {
|
|
409
|
+
icon: 'heart',
|
|
410
|
+
size: 'lg',
|
|
411
|
+
color: 'currentColor'
|
|
412
|
+
}
|
|
413
|
+
};
|
|
414
|
+
|
|
415
|
+
export const AllSizes = () => html\`
|
|
416
|
+
<div style="display: flex; gap: 1rem; align-items: center;">
|
|
417
|
+
<pds-icon icon="star" size="xs"></pds-icon>
|
|
418
|
+
<pds-icon icon="star" size="sm"></pds-icon>
|
|
419
|
+
<pds-icon icon="star" size="md"></pds-icon>
|
|
420
|
+
<pds-icon icon="star" size="lg"></pds-icon>
|
|
421
|
+
<pds-icon icon="star" size="xl"></pds-icon>
|
|
422
|
+
<pds-icon icon="star" size="2xl"></pds-icon>
|
|
423
|
+
</div>
|
|
424
|
+
\`;
|
|
425
|
+
|
|
426
|
+
export const ColoredIcons = () => html\`
|
|
427
|
+
<div style="display: flex; gap: 1rem;">
|
|
428
|
+
<pds-icon icon="heart" size="lg" color="red"></pds-icon>
|
|
429
|
+
<pds-icon icon="star" size="lg" color="gold"></pds-icon>
|
|
430
|
+
<pds-icon icon="check" size="lg" color="green"></pds-icon>
|
|
431
|
+
<pds-icon icon="x" size="lg" color="var(--color-danger-500)"></pds-icon>
|
|
432
|
+
</div>
|
|
433
|
+
\`;
|
|
434
|
+
`);
|
|
435
|
+
|
|
436
|
+
// pds-drawer
|
|
437
|
+
writeStory('components', 'PdsDrawer', `import { html } from 'lit';
|
|
438
|
+
|
|
439
|
+
export default {
|
|
440
|
+
title: 'PDS/Components/pds-drawer',
|
|
441
|
+
parameters: {
|
|
442
|
+
docs: {
|
|
443
|
+
description: {
|
|
444
|
+
component: 'Slide-out panels from any edge'
|
|
445
|
+
}
|
|
446
|
+
}
|
|
447
|
+
},
|
|
448
|
+
argTypes: {
|
|
449
|
+
position: {
|
|
450
|
+
control: 'select',
|
|
451
|
+
options: ['left', 'right', 'top', 'bottom'],
|
|
452
|
+
description: 'Edge to slide from'
|
|
453
|
+
}
|
|
454
|
+
}
|
|
455
|
+
};
|
|
456
|
+
|
|
457
|
+
export const Default = {
|
|
458
|
+
render: (args) => html\`
|
|
459
|
+
<button class="btn-primary" onclick="document.getElementById('demo-drawer').open()">
|
|
460
|
+
Open Drawer
|
|
461
|
+
</button>
|
|
462
|
+
|
|
463
|
+
<pds-drawer id="demo-drawer" position="\${args.position}">
|
|
464
|
+
<h2 slot="header">Drawer Title</h2>
|
|
465
|
+
<div style="padding: 1rem;">
|
|
466
|
+
<p>Drawer content goes here.</p>
|
|
467
|
+
<button class="btn-secondary" onclick="document.getElementById('demo-drawer').close()">
|
|
468
|
+
Close
|
|
469
|
+
</button>
|
|
470
|
+
</div>
|
|
471
|
+
</pds-drawer>
|
|
472
|
+
\`,
|
|
473
|
+
args: {
|
|
474
|
+
position: 'right'
|
|
475
|
+
}
|
|
476
|
+
};
|
|
477
|
+
`);
|
|
478
|
+
|
|
479
|
+
// pds-tabstrip
|
|
480
|
+
writeStory('components', 'PdsTabstrip', `import { html } from 'lit';
|
|
481
|
+
|
|
482
|
+
export default {
|
|
483
|
+
title: 'PDS/Components/pds-tabstrip',
|
|
484
|
+
parameters: {
|
|
485
|
+
docs: {
|
|
486
|
+
description: {
|
|
487
|
+
component: 'Accessible tab interface with keyboard navigation'
|
|
488
|
+
}
|
|
489
|
+
}
|
|
490
|
+
}
|
|
491
|
+
};
|
|
492
|
+
|
|
493
|
+
export const Default = () => html\`
|
|
494
|
+
<pds-tabstrip>
|
|
495
|
+
<button slot="tab">Overview</button>
|
|
496
|
+
<div slot="panel">
|
|
497
|
+
<h3>Overview</h3>
|
|
498
|
+
<p>This is the overview panel.</p>
|
|
499
|
+
</div>
|
|
500
|
+
|
|
501
|
+
<button slot="tab">Details</button>
|
|
502
|
+
<div slot="panel">
|
|
503
|
+
<h3>Details</h3>
|
|
504
|
+
<p>This is the details panel.</p>
|
|
505
|
+
</div>
|
|
506
|
+
|
|
507
|
+
<button slot="tab">Settings</button>
|
|
508
|
+
<div slot="panel">
|
|
509
|
+
<h3>Settings</h3>
|
|
510
|
+
<p>This is the settings panel.</p>
|
|
511
|
+
</div>
|
|
512
|
+
</pds-tabstrip>
|
|
513
|
+
\`;
|
|
514
|
+
`);
|
|
515
|
+
}
|
|
516
|
+
|
|
517
|
+
/**
|
|
518
|
+
* Write story file
|
|
519
|
+
*/
|
|
520
|
+
function writeStory(group, name, content) {
|
|
521
|
+
const dir = join(STORIES_DIR, group);
|
|
522
|
+
if (!existsSync(dir)) {
|
|
523
|
+
mkdirSync(dir, { recursive: true });
|
|
524
|
+
}
|
|
525
|
+
|
|
526
|
+
const filename = `${name}.stories.js`;
|
|
527
|
+
const filepath = join(dir, filename);
|
|
528
|
+
|
|
529
|
+
writeFileSync(filepath, content, 'utf-8');
|
|
530
|
+
console.log(` ✓ Generated ${group}/${filename}`);
|
|
531
|
+
}
|
|
532
|
+
|
|
533
|
+
/**
|
|
534
|
+
* Main execution
|
|
535
|
+
*/
|
|
536
|
+
console.log('🎨 Generating PDS Storybook stories...\n');
|
|
537
|
+
|
|
538
|
+
generateFoundationStories();
|
|
539
|
+
generatePrimitiveStories();
|
|
540
|
+
generateComponentStories();
|
|
541
|
+
|
|
542
|
+
console.log('\n✨ Story generation complete!');
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import { cpSync, mkdirSync, rmSync, readFileSync, writeFileSync, readdirSync, statSync } from 'fs';
|
|
2
|
+
import { join, dirname } from 'path';
|
|
3
|
+
import { fileURLToPath } from 'url';
|
|
4
|
+
import { execSync } from 'child_process';
|
|
5
|
+
|
|
6
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
7
|
+
const __dirname = dirname(__filename);
|
|
8
|
+
const packageRoot = join(__dirname, '..');
|
|
9
|
+
const monorepoRoot = join(packageRoot, '../..');
|
|
10
|
+
|
|
11
|
+
// Paths
|
|
12
|
+
const srcPublicAssets = join(monorepoRoot, 'public/assets');
|
|
13
|
+
const destPublicAssets = join(packageRoot, 'public/assets');
|
|
14
|
+
|
|
15
|
+
const srcSource = join(monorepoRoot, 'src');
|
|
16
|
+
const destSource = join(packageRoot, 'src');
|
|
17
|
+
|
|
18
|
+
console.log('📦 Packaging PDS Storybook...');
|
|
19
|
+
|
|
20
|
+
// 1. Copy Assets
|
|
21
|
+
console.log('Copying assets...');
|
|
22
|
+
if (process.cwd() !== packageRoot) {
|
|
23
|
+
// Safety check to ensure we are running from package root or we know where we are
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
rmSync(destPublicAssets, { recursive: true, force: true });
|
|
27
|
+
mkdirSync(dirname(destPublicAssets), { recursive: true });
|
|
28
|
+
cpSync(srcPublicAssets, destPublicAssets, { recursive: true });
|
|
29
|
+
|
|
30
|
+
// 2. Copy Source
|
|
31
|
+
console.log('Copying source...');
|
|
32
|
+
rmSync(destSource, { recursive: true, force: true });
|
|
33
|
+
cpSync(srcSource, destSource, { recursive: true });
|
|
34
|
+
|
|
35
|
+
// Copy custom-elements.json
|
|
36
|
+
console.log('Copying custom-elements.json...');
|
|
37
|
+
cpSync(join(monorepoRoot, 'custom-elements.json'), join(packageRoot, 'custom-elements.json'));
|
|
38
|
+
|
|
39
|
+
// 3. Run Generation Scripts
|
|
40
|
+
console.log('Generating stories...');
|
|
41
|
+
// We run the scripts. They will generate stories into `stories/`.
|
|
42
|
+
// These scripts use `../../../src` to READ data. That is fine as long as we are in the monorepo during build.
|
|
43
|
+
execSync('node scripts/generate-stories.js', { cwd: packageRoot, stdio: 'inherit' });
|
|
44
|
+
|
|
45
|
+
console.log('Building reference...');
|
|
46
|
+
execSync('node scripts/build-pds-reference.mjs', { cwd: packageRoot, stdio: 'inherit' });
|
|
47
|
+
|
|
48
|
+
// 4. Patch Generated Stories
|
|
49
|
+
// The generated stories might contain `../../../src`. We need to change it to `../../src`.
|
|
50
|
+
// However, we are now using Vite aliases to handle this, so we don't need to patch the source files.
|
|
51
|
+
// This preserves the user's source code integrity.
|
|
52
|
+
console.log('Skipping story patching (handled by Vite aliases)...');
|
|
53
|
+
|
|
54
|
+
/*
|
|
55
|
+
function replaceInDir(dir, pattern, replacement) {
|
|
56
|
+
const files = readdirSync(dir);
|
|
57
|
+
for (const file of files) {
|
|
58
|
+
const filePath = join(dir, file);
|
|
59
|
+
const stat = statSync(filePath);
|
|
60
|
+
if (stat.isDirectory()) {
|
|
61
|
+
replaceInDir(filePath, pattern, replacement);
|
|
62
|
+
} else if (file.endsWith('.js') || file.endsWith('.mjs')) {
|
|
63
|
+
let content = readFileSync(filePath, 'utf-8');
|
|
64
|
+
if (content.includes(pattern)) {
|
|
65
|
+
content = content.replaceAll(pattern, replacement);
|
|
66
|
+
writeFileSync(filePath, content);
|
|
67
|
+
console.log(`Patched ${file}`);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
const storiesDir = join(packageRoot, 'stories');
|
|
74
|
+
replaceInDir(storiesDir, '../../../../src/', '../../src/');
|
|
75
|
+
replaceInDir(storiesDir, '../../../src/', '../../src/'); // Keep this just in case
|
|
76
|
+
*/
|
|
77
|
+
|
|
78
|
+
// 5. Copy static markdown files and utils
|
|
79
|
+
console.log('Copying static story assets...');
|
|
80
|
+
// These files are imported by stories but not generated, so we need to ensure they are present
|
|
81
|
+
// if they are not already in the stories folder (which they are, because they are source files).
|
|
82
|
+
// However, we need to make sure we didn't delete them if we cleaned the folder.
|
|
83
|
+
// But wait, `stories` folder is part of the package source, we only generate INTO it.
|
|
84
|
+
// So we don't need to copy them.
|
|
85
|
+
|
|
86
|
+
console.log('✅ Package build complete.');
|
package/src/js/app.js
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import "../../packages/pds-configurator/src/pds-configurator.js";
|
|
2
|
+
import { PDS } from "./pds";
|
|
3
|
+
import { config } from "../../pds.config.js"
|
|
4
|
+
|
|
5
|
+
// Initialize PDS once at app startup using the new unified shape
|
|
6
|
+
await PDS.start(config);
|
|
7
|
+
|
|
8
|
+
document.body.innerHTML = /*html*/ `
|
|
9
|
+
<header>
|
|
10
|
+
<pds-toaster id="global-toaster"></pds-toaster>
|
|
11
|
+
</header>
|
|
12
|
+
|
|
13
|
+
<main>
|
|
14
|
+
<pds-configurator></pds-configurator>
|
|
15
|
+
</main>
|
|
16
|
+
<pds-drawer id="global-drawer" position="bottom"></pds-drawer>
|
|
17
|
+
`
|