srcdev-nuxt-components 9.0.15 → 9.0.16

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 (107) hide show
  1. package/.claude/settings.json +25 -0
  2. package/.claude/skills/component-aria-landmark.md +68 -0
  3. package/.claude/skills/component-dynamic-slots.md +150 -0
  4. package/.claude/skills/component-local-style-override.md +126 -0
  5. package/.claude/skills/component-prop-driven-container-layout.md +42 -0
  6. package/.claude/skills/components/accordian-core.md +159 -0
  7. package/.claude/skills/components/contact-section.md +101 -0
  8. package/.claude/skills/components/expanding-panel.md +156 -0
  9. package/.claude/skills/components/eyebrow-text.md +25 -0
  10. package/.claude/skills/components/hero-text.md +25 -0
  11. package/.claude/skills/components/layout-grid-by-cols.md +147 -0
  12. package/.claude/skills/components/layout-row.md +35 -0
  13. package/.claude/skills/components/link-text.md +33 -0
  14. package/.claude/skills/components/page-hero-highlights.md +224 -0
  15. package/.claude/skills/components/services-card.md +28 -0
  16. package/.claude/skills/components/services-section.md +25 -0
  17. package/.claude/skills/components/stepper-list.md +227 -0
  18. package/.claude/skills/css-grid-max-width-gutters.md +67 -0
  19. package/.claude/skills/index.md +14 -3
  20. package/.claude/skills/storybook-add-story.md +60 -0
  21. package/.claude/skills/testing-add-unit-test.md +56 -0
  22. package/app/assets/styles/setup/01.config/index.css +0 -1
  23. package/app/assets/styles/setup/03.theming/default/_dark.css +2 -2
  24. package/app/assets/styles/setup/04.elements/forms/02.typography.css +1 -0
  25. package/app/assets/styles/setup/05.typography/02.utility-classes/_font-classes-page-link.css +14 -14
  26. package/app/assets/styles/setup/index.css +0 -1
  27. package/app/components/01.atoms/card/CardCore.vue +92 -0
  28. package/app/components/01.atoms/card/stories/CardCore.stories.ts +132 -0
  29. package/app/components/01.atoms/card/tests/CardCore.spec.ts +207 -0
  30. package/app/components/01.atoms/card/tests/__snapshots__/CardCore.spec.ts.snap +43 -0
  31. package/app/components/01.atoms/content-wrappers/content-columns-2/ContentColumns2.vue +51 -0
  32. package/app/components/01.atoms/content-wrappers/content-columns-2/stories/ContentColumns2.stories.ts +110 -0
  33. package/app/components/01.atoms/content-wrappers/content-columns-2/tests/ContentColumns2.spec.ts +105 -0
  34. package/app/components/01.atoms/content-wrappers/content-columns-2/tests/__snapshots__/ContentColumns2.spec.ts.snap +14 -0
  35. package/app/components/01.atoms/content-wrappers/content-width/ContentWidth.vue +88 -0
  36. package/app/components/01.atoms/content-wrappers/content-width/stories/ContentWidth.stories.ts +362 -0
  37. package/app/components/01.atoms/content-wrappers/content-width/tests/ContentWidth.spec.ts +132 -0
  38. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-cols/LayoutGridByCols.vue +71 -0
  39. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-cols/stories/LayoutGridByCols.stories.ts +219 -0
  40. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-cols/tests/LayoutGridByCols.spec.ts +174 -0
  41. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-cols/tests/__snapshots__/LayoutGrid.spec.ts.snap +36 -0
  42. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-cols/tests/__snapshots__/LayoutGridByCols.spec.ts.snap +36 -0
  43. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/LayoutGridByWidth.vue +70 -0
  44. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/stories/LayoutGridByWidth.stories.ts +220 -0
  45. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/tests/LayoutGridByWidth.spec.ts +174 -0
  46. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/tests/__snapshots__/LayoutGrid.spec.ts.snap +36 -0
  47. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/tests/__snapshots__/LayoutGridByCols.spec.ts.snap +36 -0
  48. package/app/components/01.atoms/content-wrappers/layout-grid/layout-grid-by-width/tests/__snapshots__/LayoutGridByWidth.spec.ts.snap +36 -0
  49. package/app/components/01.atoms/text-blocks/eyebrow-text/stories/EyebrowText.stories.ts +1 -1
  50. package/app/components/01.atoms/text-blocks/hero-text/stories/HeroText.stories.ts +1 -1
  51. package/app/components/01.atoms/text-blocks/link-text/stories/LinkText.stories.ts +1 -1
  52. package/app/components/02.molecules/contact-section/stories/ContactSection.stories.ts +5 -0
  53. package/app/components/02.molecules/contact-section/tests/ContactSection.spec.ts +15 -0
  54. package/app/components/02.molecules/contact-section/tests/ContactSection.vue +25 -17
  55. package/app/components/{accordian → 02.molecules/expandable/accordian}/stories/AccordianCore.stories.ts +1 -1
  56. package/app/components/02.molecules/expandable/expanding-panel/stories/ExpandingPanel.stories.ts +245 -0
  57. package/app/components/02.molecules/expandable/expanding-panel/tests/ExpandingPanel.spec.ts +351 -0
  58. package/app/components/02.molecules/expandable/expanding-panel/tests/__snapshots__/ExpandingPanel.spec.ts.snap +38 -0
  59. package/app/components/02.molecules/navigation/navigation-horizontal/NavigationHorizontal.vue +139 -0
  60. package/app/components/02.molecules/navigation/navigation-horizontal/NavigationHorizontalAdvanced.vue +172 -0
  61. package/app/components/02.molecules/profile-section/ProfileSection.vue +2 -3
  62. package/app/components/02.molecules/profile-section/tests/ProfileSection.spec.ts +2 -2
  63. package/app/components/02.molecules/stepper-list/StepperList.vue +131 -92
  64. package/app/components/02.molecules/stepper-list/stories/StepperList.stories.ts +31 -0
  65. package/app/components/02.molecules/stepper-list/tests/StepperList.spec.ts +24 -0
  66. package/app/components/02.molecules/stepper-list/tests/__snapshots__/StepperList.spec.ts.snap +22 -9
  67. package/app/components/03.organisms/image-galleries/slider-gallery/SliderGallery.vue +782 -0
  68. package/app/components/03.organisms/image-galleries/slider-gallery/stories/SliderGallery.stories.ts +233 -0
  69. package/app/components/03.organisms/image-galleries/slider-gallery/tests/SliderGallery.spec.ts +226 -0
  70. package/app/components/03.organisms/image-galleries/slider-gallery/tests/__snapshots__/SliderGallery.spec.ts.snap +69 -0
  71. package/app/components/03.organisms/services/services-grids/ServicesCardGrid.vue +1 -1
  72. package/app/components/03.organisms/services/services-grids/ServicesSectionGrid.vue +1 -1
  73. package/app/components/03.organisms/services/services-section/ServicesSection.vue +2 -3
  74. package/app/components/04.templates/page-hero-highlights/PageHeroHighlights.vue +239 -0
  75. package/app/components/04.templates/page-hero-highlights/stories/PageHeroHighlights.stories.ts +404 -0
  76. package/app/components/04.templates/page-hero-highlights/tests/PageHeroHighlights.spec.ts +198 -0
  77. package/app/components/04.templates/page-hero-highlights/tests/__snapshots__/PageHeroHighlights.spec.ts.snap +19 -0
  78. package/app/components/container-glow/ContainerGlowCore.vue +20 -27
  79. package/app/components/forms/input-button/InputButtonCore.vue +105 -104
  80. package/app/components/glowing-border/stories/GlowingBorder.stories.ts +21 -21
  81. package/app/composables/useAriaLabelledById.ts +13 -0
  82. package/app/layouts/default.vue +8 -3
  83. package/app/pages/forms/examples/buttons/index.vue +6 -6
  84. package/app/pages/forms/examples/material/checkbox-radio-panels.vue +3 -3
  85. package/app/pages/forms/examples/material/text-fields.vue +607 -610
  86. package/app/pages/page-hero-highlights.vue +81 -0
  87. package/app/pages/ui/{display-card.vue → card-core.vue} +15 -15
  88. package/app/pages/ui/contact-section.vue +1 -1
  89. package/app/pages/ui/container-glow.vue +1 -1
  90. package/app/pages/ui/content-width.vue +126 -0
  91. package/app/pages/ui/glowing-border.vue +9 -9
  92. package/app/pages/ui/navigation/navigation-horizontal.vue +493 -0
  93. package/app/pages/ui/services/services-section/[slug].vue +3 -1
  94. package/package.json +2 -2
  95. package/app/assets/styles/setup/01.config/_basic-resets.css +0 -9
  96. package/app/components/content-columns/TwoColumns.vue +0 -59
  97. package/app/components/content-columns/stories/TwoColumns.stories.ts +0 -561
  98. package/app/components/content-containers/ContentContainer.vue +0 -89
  99. package/app/components/content-containers/stories/ContentContainer.stories.ts +0 -465
  100. package/app/components/content-grid/ContentGrid.vue +0 -85
  101. package/app/components/display-card/DisplayCard.vue +0 -122
  102. package/app/components/image-galleries/SliderGallery.vue +0 -786
  103. package/app/pages/ui/content-container.vue +0 -112
  104. /package/app/components/{accordian → 02.molecules/expandable/accordian}/AccordianCore.vue +0 -0
  105. /package/app/components/{accordian → 02.molecules/expandable/accordian}/tests/AccordianCore.spec.ts +0 -0
  106. /package/app/components/{accordian → 02.molecules/expandable/accordian}/tests/__snapshots__/AccordianCore.spec.ts.snap +0 -0
  107. /package/app/components/{expanding-panel → 02.molecules/expandable/expanding-panel}/ExpandingPanel.vue +0 -0
@@ -0,0 +1,493 @@
1
+ <template>
2
+ <div>
3
+ <NuxtLayout name="default">
4
+ <template #layout-content>
5
+ <LayoutRow tag="div" variant="content" :style-class-passthrough="['mbe-20']">
6
+ <h2 class="page-heading-2">Navigation Horizontal</h2>
7
+ <p class="page-body-medium">This navigation has a reflective glow effect</p>
8
+ </LayoutRow>
9
+
10
+ <LayoutRow tag="div" variant="content" :style-class-passthrough="['mbe-20']">
11
+ <DisplayThemeSwitch />
12
+ </LayoutRow>
13
+
14
+ <LayoutRow tag="div" variant="full-width" :style-class-passthrough="['mbe-4']">
15
+ <LayoutRow tag="div" variant="content">
16
+ <h3 class="page-heading-3">Control settings</h3>
17
+ </LayoutRow>
18
+ <div class="nav-preview" :class="`theme-${theme}`" :style="navStyle">
19
+ <NavigationHorizontal :nav-item-data="navItemData" />
20
+ </div>
21
+ </LayoutRow>
22
+
23
+ <LayoutRow tag="div" variant="full-width" :style-class-passthrough="['mbe-4']">
24
+ <LayoutRow tag="div" variant="content">
25
+ <h3 class="page-heading-3">User controllable</h3>
26
+ </LayoutRow>
27
+ <div class="nav-preview" :class="`theme-${theme}`" :style="navStyle">
28
+ <NavigationHorizontalAdvanced :nav-item-data="navItemData" />
29
+ </div>
30
+ </LayoutRow>
31
+
32
+ <LayoutRow tag="div" variant="content" :style-class-passthrough="['mbe-20']">
33
+ <div class="nav-playground">
34
+ <fieldset>
35
+ <legend>Theme</legend>
36
+ <div class="control-row">
37
+ <label>Light / Dark</label>
38
+ <div class="theme-toggle">
39
+ <button :class="{ active: theme === 'light' }" @click="setTheme('light')">Light</button>
40
+ <button :class="{ active: theme === 'dark' }" @click="setTheme('dark')">Dark</button>
41
+ </div>
42
+ </div>
43
+ </fieldset>
44
+
45
+ <fieldset>
46
+ <legend>Colours</legend>
47
+ <div class="control-row">
48
+ <label for="active-colour">Active / glow colour</label>
49
+ <input id="active-colour" v-model="controls.activeColour" type="color" />
50
+ </div>
51
+ <div class="control-row">
52
+ <label for="link-colour">Link text colour</label>
53
+ <input id="link-colour" v-model="controls.linkColour" type="color" />
54
+ </div>
55
+ <div class="control-row">
56
+ <label for="link-bg">Link background</label>
57
+ <input id="link-bg" v-model="controls.linkBg" type="color" />
58
+ </div>
59
+ <div class="control-row">
60
+ <label for="border-colour">Border colour</label>
61
+ <input id="border-colour" v-model="controls.borderColour" type="color" />
62
+ </div>
63
+ <div class="control-row">
64
+ <label for="border-opacity">Border opacity — {{ controls.borderOpacity }}</label>
65
+ <input
66
+ id="border-opacity"
67
+ v-model.number="controls.borderOpacity"
68
+ type="range"
69
+ min="0"
70
+ max="1"
71
+ step="0.05"
72
+ />
73
+ </div>
74
+ </fieldset>
75
+
76
+ <fieldset>
77
+ <legend>Borders</legend>
78
+ <div class="control-row">
79
+ <label for="border-start">Border top — {{ controls.borderStart }}px</label>
80
+ <input id="border-start" v-model.number="controls.borderStart" type="range" min="0" max="10" step="1" />
81
+ </div>
82
+ <div class="control-row">
83
+ <label for="border-end">Border bottom — {{ controls.borderEnd }}px</label>
84
+ <input id="border-end" v-model.number="controls.borderEnd" type="range" min="0" max="10" step="1" />
85
+ </div>
86
+ </fieldset>
87
+
88
+ <fieldset>
89
+ <legend>Layout</legend>
90
+ <div class="control-row">
91
+ <label for="list-padding">List padding — {{ controls.listPadding }}rem</label>
92
+ <input
93
+ id="list-padding"
94
+ v-model.number="controls.listPadding"
95
+ type="range"
96
+ min="0"
97
+ max="6"
98
+ step="0.5"
99
+ />
100
+ </div>
101
+ <div class="control-row">
102
+ <label for="list-gap">List gap — {{ controls.listGap }}rem</label>
103
+ <input id="list-gap" v-model.number="controls.listGap" type="range" min="0" max="10" step="0.25" />
104
+ </div>
105
+ <div class="control-row">
106
+ <label for="link-padding-block">Link vertical padding — {{ controls.linkPaddingBlock }}rem</label>
107
+ <input
108
+ id="link-padding-block"
109
+ v-model.number="controls.linkPaddingBlock"
110
+ type="range"
111
+ min="0"
112
+ max="2"
113
+ step="0.1"
114
+ />
115
+ </div>
116
+ <div class="control-row">
117
+ <label for="link-padding-inline">Link horizontal padding — {{ controls.linkPaddingInline }}rem</label>
118
+ <input
119
+ id="link-padding-inline"
120
+ v-model.number="controls.linkPaddingInline"
121
+ type="range"
122
+ min="0"
123
+ max="3"
124
+ step="0.1"
125
+ />
126
+ </div>
127
+ <div class="control-row">
128
+ <label for="link-border-radius">Link border radius — {{ controls.linkBorderRadius }}rem</label>
129
+ <input
130
+ id="link-border-radius"
131
+ v-model.number="controls.linkBorderRadius"
132
+ type="range"
133
+ min="0"
134
+ max="2"
135
+ step="0.1"
136
+ />
137
+ </div>
138
+ </fieldset>
139
+
140
+ <fieldset>
141
+ <legend>Glow Effect</legend>
142
+ <div class="control-row">
143
+ <label for="glow-pos-x">Origin X — {{ controls.glowPosX }}%</label>
144
+ <input id="glow-pos-x" v-model.number="controls.glowPosX" type="range" min="-100" max="100" step="1" />
145
+ </div>
146
+ <div class="control-row">
147
+ <label for="glow-pos-y">Origin Y — {{ controls.glowPosY }}%</label>
148
+ <input id="glow-pos-y" v-model.number="controls.glowPosY" type="range" min="-100" max="200" step="1" />
149
+ </div>
150
+ <div class="control-row">
151
+ <label for="glow-inner-stop">Inner gradient stop — {{ controls.glowInnerStop }}%</label>
152
+ <input
153
+ id="glow-inner-stop"
154
+ v-model.number="controls.glowInnerStop"
155
+ type="range"
156
+ min="0"
157
+ max="50"
158
+ step="1"
159
+ />
160
+ </div>
161
+ <div class="control-row">
162
+ <label for="glow-outer-stop">Outer gradient stop — {{ controls.glowOuterStop }}%</label>
163
+ <input
164
+ id="glow-outer-stop"
165
+ v-model.number="controls.glowOuterStop"
166
+ type="range"
167
+ min="50"
168
+ max="100"
169
+ step="1"
170
+ />
171
+ </div>
172
+ <div class="control-row">
173
+ <label for="glow-size">Glow spread — {{ controls.glowSize }}px</label>
174
+ <input id="glow-size" v-model.number="controls.glowSize" type="range" min="0" max="100" step="1" />
175
+ </div>
176
+ <div class="control-row">
177
+ <label for="glow-opacity">Glow opacity — {{ controls.glowOpacity }}</label>
178
+ <input
179
+ id="glow-opacity"
180
+ v-model.number="controls.glowOpacity"
181
+ type="range"
182
+ min="0"
183
+ max="1"
184
+ step="0.05"
185
+ />
186
+ </div>
187
+ <div class="control-row">
188
+ <label for="anchor-offset">Anchor spread — {{ controls.anchorOffset }}px</label>
189
+ <input
190
+ id="anchor-offset"
191
+ v-model.number="controls.anchorOffset"
192
+ type="range"
193
+ min="0"
194
+ max="100"
195
+ step="1"
196
+ />
197
+ </div>
198
+ </fieldset>
199
+
200
+ <fieldset>
201
+ <legend>Animation</legend>
202
+ <div class="control-row">
203
+ <label for="transition-duration">Transition — {{ controls.transitionDuration }}ms</label>
204
+ <input
205
+ id="transition-duration"
206
+ v-model.number="controls.transitionDuration"
207
+ type="range"
208
+ min="0"
209
+ max="1000"
210
+ step="50"
211
+ />
212
+ </div>
213
+ </fieldset>
214
+ </div>
215
+ </LayoutRow>
216
+
217
+ <LayoutRow tag="div" variant="content" :style-class-passthrough="['mbe-20']">
218
+ <div class="css-snippet">
219
+ <div class="css-snippet-header">
220
+ <h3 class="page-heading-3">CSS Token Snippet</h3>
221
+ <button class="copy-btn" @click="copySnippet">{{ copied ? "Copied!" : "Copy" }}</button>
222
+ </div>
223
+ <pre class="css-snippet-code">{{ cssSnippet }}</pre>
224
+ </div>
225
+ </LayoutRow>
226
+ </template>
227
+ </NuxtLayout>
228
+ </div>
229
+ </template>
230
+
231
+ <script setup lang="ts">
232
+ import type { NavItemData } from "~/components/02.molecules/navigation/navigation-horizontal/NavigationHorizontal.vue";
233
+ definePageMeta({
234
+ layout: false,
235
+ });
236
+
237
+ useHead({
238
+ title: "Navigation Horizontal",
239
+ meta: [
240
+ {
241
+ name: "description",
242
+ content: "Navigation Horizontal Meta description content",
243
+ },
244
+ ],
245
+ bodyAttrs: {
246
+ class: "navigation-horizontal-page",
247
+ },
248
+ });
249
+
250
+ const navItemData: NavItemData = {
251
+ main: [
252
+ { text: "Home", href: "#", isExternal: true, iconName: "home", cssName: "home-link" },
253
+ { text: "About", href: "#", isExternal: true, iconName: "info", cssName: "about-link" },
254
+ { text: "Services", href: "#", isExternal: true, iconName: "services", cssName: "services-link" },
255
+ { text: "Contact", href: "#", isExternal: true, iconName: "contact", cssName: "contact-link" },
256
+ ],
257
+ };
258
+
259
+ type Theme = "light" | "dark";
260
+
261
+ const themeDefaults: Record<
262
+ Theme,
263
+ { linkColour: string; linkBg: string; borderColour: string; borderOpacity: number }
264
+ > = {
265
+ dark: { linkColour: "#ffffff", linkBg: "#333333", borderColour: "#ffffff", borderOpacity: 0.2 },
266
+ light: { linkColour: "#1a1a1a", linkBg: "#e8e8e8", borderColour: "#000000", borderOpacity: 0.15 },
267
+ };
268
+
269
+ const theme = ref<Theme>("dark");
270
+
271
+ const controls = reactive({
272
+ activeColour: "#00ff00",
273
+ linkColour: themeDefaults.dark.linkColour,
274
+ linkBg: themeDefaults.dark.linkBg,
275
+ borderColour: themeDefaults.dark.borderColour,
276
+ borderOpacity: themeDefaults.dark.borderOpacity,
277
+ borderStart: 0,
278
+ borderEnd: 3,
279
+ listPadding: 2,
280
+ listGap: 3,
281
+ linkPaddingBlock: 0.5,
282
+ linkPaddingInline: 1,
283
+ linkBorderRadius: 0.2,
284
+ glowPosX: 50,
285
+ glowPosY: 100,
286
+ glowInnerStop: 10,
287
+ glowOuterStop: 75,
288
+ glowSize: 32,
289
+ glowOpacity: 0.5,
290
+ anchorOffset: 40,
291
+ transitionDuration: 300,
292
+ });
293
+
294
+ const setTheme = (newTheme: Theme) => {
295
+ theme.value = newTheme;
296
+ const defaults = themeDefaults[newTheme];
297
+ controls.linkColour = defaults.linkColour;
298
+ controls.linkBg = defaults.linkBg;
299
+ controls.borderColour = defaults.borderColour;
300
+ controls.borderOpacity = defaults.borderOpacity;
301
+ };
302
+
303
+ const cssSnippet = computed(() => {
304
+ const borderColour = `color-mix(in srgb, ${controls.borderColour} ${Math.round(controls.borderOpacity * 100)}%, transparent)`;
305
+ return `.your-selector {
306
+ /* Colours */
307
+ --nav-active-colour: ${controls.activeColour};
308
+ --nav-link-colour: ${controls.linkColour};
309
+ --nav-link-bg: ${controls.linkBg};
310
+ --nav-border-colour: ${borderColour};
311
+
312
+ /* Borders */
313
+ --nav-border-start: ${controls.borderStart}px;
314
+ --nav-border-end: ${controls.borderEnd}px;
315
+
316
+ /* Layout */
317
+ --nav-list-padding: ${controls.listPadding}rem;
318
+ --nav-list-gap: ${controls.listGap}rem;
319
+ --nav-link-padding-block: ${controls.linkPaddingBlock}rem;
320
+ --nav-link-padding-inline: ${controls.linkPaddingInline}rem;
321
+ --nav-link-border-radius: ${controls.linkBorderRadius}rem;
322
+
323
+ /* Glow effect */
324
+ --nav-glow-pos-x: ${controls.glowPosX}%;
325
+ --nav-glow-pos-y: ${controls.glowPosY}%;
326
+ --nav-glow-inner-stop: ${controls.glowInnerStop}%;
327
+ --nav-glow-outer-stop: ${controls.glowOuterStop}%;
328
+ --nav-glow-size: ${controls.glowSize}px;
329
+ --nav-glow-opacity: ${controls.glowOpacity};
330
+ --nav-anchor-offset: ${controls.anchorOffset}px;
331
+
332
+ /* Animation */
333
+ --nav-transition-duration: ${controls.transitionDuration}ms;
334
+ }`;
335
+ });
336
+
337
+ const copied = ref(false);
338
+ const copySnippet = async () => {
339
+ await navigator.clipboard.writeText(cssSnippet.value);
340
+ copied.value = true;
341
+ setTimeout(() => {
342
+ copied.value = false;
343
+ }, 2000);
344
+ };
345
+
346
+ const navStyle = computed(() => ({
347
+ "--nav-active-colour": controls.activeColour,
348
+ "--nav-link-colour": controls.linkColour,
349
+ "--nav-link-bg": controls.linkBg,
350
+ "--nav-border-colour": `color-mix(in srgb, ${controls.borderColour} ${Math.round(controls.borderOpacity * 100)}%, transparent)`,
351
+ "--nav-border-start": `${controls.borderStart}px`,
352
+ "--nav-border-end": `${controls.borderEnd}px`,
353
+ "--nav-list-padding": `${controls.listPadding}rem`,
354
+ "--nav-list-gap": `${controls.listGap}rem`,
355
+ "--nav-link-padding-block": `${controls.linkPaddingBlock}rem`,
356
+ "--nav-link-padding-inline": `${controls.linkPaddingInline}rem`,
357
+ "--nav-link-border-radius": `${controls.linkBorderRadius}rem`,
358
+ "--nav-glow-pos-x": `${controls.glowPosX}%`,
359
+ "--nav-glow-pos-y": `${controls.glowPosY}%`,
360
+ "--nav-glow-inner-stop": `${controls.glowInnerStop}%`,
361
+ "--nav-glow-outer-stop": `${controls.glowOuterStop}%`,
362
+ "--nav-glow-size": `${controls.glowSize}px`,
363
+ "--nav-glow-opacity": String(controls.glowOpacity),
364
+ "--nav-anchor-offset": `${controls.anchorOffset}px`,
365
+ "--nav-transition-duration": `${controls.transitionDuration}ms`,
366
+ "color-scheme": theme.value,
367
+ }));
368
+ </script>
369
+
370
+ <style lang="css">
371
+ .navigation-horizontal-page {
372
+ .nav-preview {
373
+ padding: 4rem 0;
374
+ transition: background 300ms;
375
+
376
+ &.theme-dark {
377
+ --page-bg: hsl(0 0% 8%);
378
+ /* background: var(--page-bg); */
379
+ }
380
+
381
+ &.theme-light {
382
+ --page-bg: hsl(0 0% 95%);
383
+ /* background: var(--page-bg); */
384
+ }
385
+ }
386
+
387
+ .nav-playground {
388
+ display: grid;
389
+ grid-template-columns: repeat(auto-fit, minmax(30rem, 1fr));
390
+ gap: 2rem;
391
+ padding-block: 2rem;
392
+
393
+ fieldset {
394
+ border: 1px solid light-dark(var(--slate-04), var(--slate-06));
395
+ border-radius: 0.4rem;
396
+ padding: 1.6rem;
397
+
398
+ legend {
399
+ font-weight: bold;
400
+ padding: 0 0.8rem;
401
+ font-size: 1.4rem;
402
+ }
403
+
404
+ .control-row {
405
+ display: grid;
406
+ grid-template-columns: 1fr 14rem;
407
+ gap: 1rem;
408
+ align-items: center;
409
+ padding: 0.5rem 0;
410
+
411
+ label {
412
+ font-size: 1.3rem;
413
+ }
414
+
415
+ input[type="range"] {
416
+ width: 100%;
417
+ cursor: pointer;
418
+ }
419
+
420
+ input[type="color"] {
421
+ height: 3.2rem;
422
+ width: 100%;
423
+ padding: 0.2rem;
424
+ border: 1px solid light-dark(var(--slate-04), var(--slate-06));
425
+ border-radius: 0.2rem;
426
+ cursor: pointer;
427
+ background: transparent;
428
+ }
429
+ }
430
+ }
431
+
432
+ .theme-toggle {
433
+ display: flex;
434
+ gap: 0.4rem;
435
+
436
+ button {
437
+ padding: 0.4rem 1.6rem;
438
+ border: 1px solid light-dark(var(--slate-05), var(--slate-06));
439
+ border-radius: 0.2rem;
440
+ cursor: pointer;
441
+ background: transparent;
442
+ font-size: 1.3rem;
443
+ color: inherit;
444
+
445
+ &.active {
446
+ background: light-dark(var(--slate-03), var(--slate-07));
447
+ font-weight: bold;
448
+ }
449
+ }
450
+ }
451
+ }
452
+
453
+ .css-snippet {
454
+ border: 1px solid light-dark(var(--slate-04), var(--slate-06));
455
+ border-radius: 0.4rem;
456
+ overflow: hidden;
457
+
458
+ .css-snippet-header {
459
+ display: flex;
460
+ justify-content: space-between;
461
+ align-items: center;
462
+ padding: 1rem 1.6rem;
463
+ border-block-end: 1px solid light-dark(var(--slate-04), var(--slate-06));
464
+ /* background: light-dark(var(--slate-02), var(--slate-08)); */
465
+ }
466
+
467
+ .css-snippet-code {
468
+ margin: 0;
469
+ padding: 1.6rem;
470
+ font-family: monospace;
471
+ font-size: 1.3rem;
472
+ line-height: 1.6;
473
+ overflow-x: auto;
474
+ white-space: pre;
475
+ /* background: light-dark(var(--slate-01), var(--slate-09)); */
476
+ }
477
+
478
+ .copy-btn {
479
+ padding: 0.4rem 1.2rem;
480
+ border: 1px solid light-dark(var(--slate-05), var(--slate-06));
481
+ border-radius: 0.2rem;
482
+ cursor: pointer;
483
+ background: transparent;
484
+ font-size: 1.3rem;
485
+ color: inherit;
486
+
487
+ &:hover {
488
+ background: light-dark(var(--slate-03), var(--slate-07));
489
+ }
490
+ }
491
+ }
492
+ }
493
+ </style>
@@ -17,7 +17,9 @@
17
17
  :style-class-passthrough="['mb-20']"
18
18
  />
19
19
 
20
- <p class="page-body-normal"><NuxtLink to="/ui/services/services-cards">Back to Services</NuxtLink></p>
20
+ <p class="page-body-normal">
21
+ <NuxtLink to="/ui/services/services-cards" class="page-link-normal">Back to Services</NuxtLink>
22
+ </p>
21
23
  </LayoutRow>
22
24
 
23
25
  <LayoutRow tag="div" variant="content" :style-class-passthrough="['mbe-20']">
package/package.json CHANGED
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "srcdev-nuxt-components",
3
3
  "type": "module",
4
- "version": "9.0.15",
4
+ "version": "9.0.16",
5
5
  "main": "nuxt.config.ts",
6
6
  "types": "types.d.ts",
7
7
  "license": "MIT",
8
8
  "engines": {
9
- "node": ">=20.19.0",
9
+ "node": ">=20.19.0 <23",
10
10
  "npm": ">=10.0.0"
11
11
  },
12
12
  "scripts": {
@@ -1,9 +0,0 @@
1
- /**
2
- Reset list elements
3
- */
4
- ul,
5
- ol {
6
- padding: 0;
7
- margin: 0;
8
- list-style: none;
9
- }
@@ -1,59 +0,0 @@
1
- <template>
2
- <component
3
- :is="props.tag"
4
- class="two-column-layout-container"
5
- :class="[elementClasses]"
6
- :data-testid="props.dataTestid"
7
- >
8
- <div class="two-column-layout">
9
- <div v-if="slots.col1" class="col-1">
10
- <slot name="col1"></slot>
11
- </div>
12
- <div v-if="slots.col2" class="col-2">
13
- <slot name="col2"></slot>
14
- </div>
15
- </div>
16
- </component>
17
- </template>
18
-
19
- <script setup lang="ts">
20
- const props = defineProps({
21
- dataTestid: {
22
- type: String,
23
- default: "two-column-layout",
24
- },
25
- tag: {
26
- type: String,
27
- default: "div",
28
- validator(value: string) {
29
- return ["div", "section", "article", "aside", "header", "footer", "main", "nav"].includes(value);
30
- },
31
- },
32
- styleClassPassthrough: {
33
- type: [String, Array] as PropType<string | string[]>,
34
- default: () => [],
35
- },
36
- });
37
- const slots = useSlots();
38
- const { elementClasses } = useStyleClassPassthrough(props.styleClassPassthrough);
39
- </script>
40
-
41
- <style lang="css">
42
- @layer components {
43
- .two-column-layout-container {
44
- container-type: inline-size;
45
- container-name: two-column-layout;
46
-
47
- .two-column-layout {
48
- display: grid;
49
- justify-content: start;
50
- grid-auto-flow: row;
51
- gap: 32px;
52
-
53
- @container two-column-layout (width >= 1064px) {
54
- grid-template-columns: repeat(2, 1fr);
55
- }
56
- }
57
- }
58
- }
59
- </style>