@newtonedev/configurator 0.1.0 → 0.1.2
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/dist/Configurator.d.ts.map +1 -1
- package/dist/bridge/toCSS.d.ts.map +1 -1
- package/dist/bridge/toThemeConfig.d.ts.map +1 -1
- package/dist/hex-conversion.d.ts +25 -0
- package/dist/hex-conversion.d.ts.map +1 -0
- package/dist/hooks/useWcagValidation.d.ts +20 -0
- package/dist/hooks/useWcagValidation.d.ts.map +1 -0
- package/dist/index.cjs +690 -49
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +6 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +676 -39
- package/dist/index.js.map +1 -1
- package/dist/panels/DesignPanel.d.ts +10 -0
- package/dist/panels/DesignPanel.d.ts.map +1 -0
- package/dist/panels/PalettePanel.d.ts +3 -2
- package/dist/panels/PalettePanel.d.ts.map +1 -1
- package/dist/state/actions.d.ts +57 -1
- package/dist/state/actions.d.ts.map +1 -1
- package/dist/state/defaults.d.ts.map +1 -1
- package/dist/state/reducer.d.ts.map +1 -1
- package/dist/types.d.ts +33 -0
- package/dist/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/Configurator.tsx +10 -0
- package/src/bridge/toCSS.ts +4 -0
- package/src/bridge/toThemeConfig.ts +113 -3
- package/src/hex-conversion.ts +99 -0
- package/src/hooks/useWcagValidation.ts +111 -0
- package/src/index.ts +9 -2
- package/src/panels/DesignPanel.tsx +149 -0
- package/src/panels/PalettePanel.tsx +182 -6
- package/src/state/actions.ts +21 -1
- package/src/state/defaults.ts +31 -0
- package/src/state/reducer.ts +181 -0
- package/src/types.ts +35 -0
package/dist/index.cjs
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var React = require('react');
|
|
4
4
|
var reactNative = require('react-native');
|
|
5
5
|
var components = require('@newtonedev/components');
|
|
6
6
|
var newtone = require('newtone');
|
|
7
7
|
|
|
8
8
|
function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
|
|
9
9
|
|
|
10
|
-
var
|
|
10
|
+
var React__default = /*#__PURE__*/_interopDefault(React);
|
|
11
11
|
|
|
12
12
|
// src/Configurator.tsx
|
|
13
13
|
|
|
@@ -76,6 +76,42 @@ var DEFAULT_CONFIGURATOR_STATE = {
|
|
|
76
76
|
preview: {
|
|
77
77
|
mode: "light",
|
|
78
78
|
theme: "neutral"
|
|
79
|
+
},
|
|
80
|
+
spacing: {
|
|
81
|
+
preset: "md"
|
|
82
|
+
// Medium (8px base): default/balanced spacing
|
|
83
|
+
},
|
|
84
|
+
roundness: {
|
|
85
|
+
intensity: 0.5
|
|
86
|
+
// 1.0x multiplier = preserves current hardcoded values
|
|
87
|
+
},
|
|
88
|
+
typography: {
|
|
89
|
+
fonts: {
|
|
90
|
+
mono: {
|
|
91
|
+
type: "system",
|
|
92
|
+
family: "ui-monospace",
|
|
93
|
+
fallback: "SFMono-Regular, Menlo, Monaco, Consolas, monospace"
|
|
94
|
+
},
|
|
95
|
+
display: {
|
|
96
|
+
type: "system",
|
|
97
|
+
family: "system-ui",
|
|
98
|
+
fallback: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'
|
|
99
|
+
},
|
|
100
|
+
default: {
|
|
101
|
+
type: "system",
|
|
102
|
+
family: "system-ui",
|
|
103
|
+
fallback: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'
|
|
104
|
+
}
|
|
105
|
+
},
|
|
106
|
+
scale: { baseSize: 16, ratio: 1.25 }
|
|
107
|
+
},
|
|
108
|
+
icons: {
|
|
109
|
+
variant: "rounded",
|
|
110
|
+
// Material Design 3 aesthetic
|
|
111
|
+
weight: 400,
|
|
112
|
+
// Normal weight
|
|
113
|
+
autoGrade: true
|
|
114
|
+
// Enable mode-aware grade
|
|
79
115
|
}
|
|
80
116
|
};
|
|
81
117
|
|
|
@@ -142,6 +178,52 @@ function configuratorReducer(state, action) {
|
|
|
142
178
|
hueGradeDirection: action.direction
|
|
143
179
|
})
|
|
144
180
|
};
|
|
181
|
+
case "SET_PALETTE_KEY_COLOR":
|
|
182
|
+
return {
|
|
183
|
+
...state,
|
|
184
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
185
|
+
keyColor: clamp(action.normalizedValue, 0, 1)
|
|
186
|
+
})
|
|
187
|
+
};
|
|
188
|
+
case "CLEAR_PALETTE_KEY_COLOR":
|
|
189
|
+
return {
|
|
190
|
+
...state,
|
|
191
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
192
|
+
keyColor: void 0
|
|
193
|
+
})
|
|
194
|
+
};
|
|
195
|
+
case "SET_PALETTE_FROM_HEX":
|
|
196
|
+
return {
|
|
197
|
+
...state,
|
|
198
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
199
|
+
hue: wrapHue(action.hue),
|
|
200
|
+
saturation: clamp(action.saturation, 0, 100),
|
|
201
|
+
keyColor: clamp(action.keyColor, 0, 1)
|
|
202
|
+
})
|
|
203
|
+
};
|
|
204
|
+
case "SET_PALETTE_KEY_COLOR_DARK":
|
|
205
|
+
return {
|
|
206
|
+
...state,
|
|
207
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
208
|
+
keyColorDark: clamp(action.normalizedValue, 0, 1)
|
|
209
|
+
})
|
|
210
|
+
};
|
|
211
|
+
case "CLEAR_PALETTE_KEY_COLOR_DARK":
|
|
212
|
+
return {
|
|
213
|
+
...state,
|
|
214
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
215
|
+
keyColorDark: void 0
|
|
216
|
+
})
|
|
217
|
+
};
|
|
218
|
+
case "SET_PALETTE_FROM_HEX_DARK":
|
|
219
|
+
return {
|
|
220
|
+
...state,
|
|
221
|
+
palettes: updatePalette(state.palettes, action.index, {
|
|
222
|
+
hue: wrapHue(action.hue),
|
|
223
|
+
saturation: clamp(action.saturation, 0, 100),
|
|
224
|
+
keyColorDark: clamp(action.keyColor, 0, 1)
|
|
225
|
+
})
|
|
226
|
+
};
|
|
145
227
|
// Dynamic range actions
|
|
146
228
|
case "SET_LIGHTEST":
|
|
147
229
|
return {
|
|
@@ -192,6 +274,125 @@ function configuratorReducer(state, action) {
|
|
|
192
274
|
dark: { ...state.globalHueGrading.dark, hue: wrapHue(action.hue) }
|
|
193
275
|
}
|
|
194
276
|
};
|
|
277
|
+
// Spacing actions
|
|
278
|
+
case "SET_SPACING_PRESET":
|
|
279
|
+
return {
|
|
280
|
+
...state,
|
|
281
|
+
spacing: {
|
|
282
|
+
preset: action.preset
|
|
283
|
+
}
|
|
284
|
+
};
|
|
285
|
+
// Roundness actions
|
|
286
|
+
case "SET_ROUNDNESS_INTENSITY":
|
|
287
|
+
return {
|
|
288
|
+
...state,
|
|
289
|
+
roundness: {
|
|
290
|
+
intensity: clamp(action.intensity, 0, 1)
|
|
291
|
+
}
|
|
292
|
+
};
|
|
293
|
+
// Typography actions
|
|
294
|
+
case "SET_TYPOGRAPHY_BASE_SIZE": {
|
|
295
|
+
const defaultTypography = DEFAULT_CONFIGURATOR_STATE.typography;
|
|
296
|
+
return {
|
|
297
|
+
...state,
|
|
298
|
+
typography: {
|
|
299
|
+
fonts: state.typography?.fonts ?? defaultTypography.fonts,
|
|
300
|
+
scale: {
|
|
301
|
+
baseSize: clamp(action.baseSize, 12, 24),
|
|
302
|
+
ratio: state.typography?.scale.ratio ?? defaultTypography.scale.ratio
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
};
|
|
306
|
+
}
|
|
307
|
+
case "SET_TYPOGRAPHY_RATIO": {
|
|
308
|
+
const defaultTypography = DEFAULT_CONFIGURATOR_STATE.typography;
|
|
309
|
+
return {
|
|
310
|
+
...state,
|
|
311
|
+
typography: {
|
|
312
|
+
fonts: state.typography?.fonts ?? defaultTypography.fonts,
|
|
313
|
+
scale: {
|
|
314
|
+
baseSize: state.typography?.scale.baseSize ?? defaultTypography.scale.baseSize,
|
|
315
|
+
ratio: clamp(action.ratio, 1.1, 1.5)
|
|
316
|
+
}
|
|
317
|
+
}
|
|
318
|
+
};
|
|
319
|
+
}
|
|
320
|
+
case "SET_FONT_MONO": {
|
|
321
|
+
const defaultTypography = DEFAULT_CONFIGURATOR_STATE.typography;
|
|
322
|
+
return {
|
|
323
|
+
...state,
|
|
324
|
+
typography: {
|
|
325
|
+
fonts: {
|
|
326
|
+
mono: action.font,
|
|
327
|
+
display: state.typography?.fonts.display ?? defaultTypography.fonts.display,
|
|
328
|
+
default: state.typography?.fonts.default ?? defaultTypography.fonts.default
|
|
329
|
+
},
|
|
330
|
+
scale: state.typography?.scale ?? defaultTypography.scale
|
|
331
|
+
}
|
|
332
|
+
};
|
|
333
|
+
}
|
|
334
|
+
case "SET_FONT_DISPLAY": {
|
|
335
|
+
const defaultTypography = DEFAULT_CONFIGURATOR_STATE.typography;
|
|
336
|
+
return {
|
|
337
|
+
...state,
|
|
338
|
+
typography: {
|
|
339
|
+
fonts: {
|
|
340
|
+
mono: state.typography?.fonts.mono ?? defaultTypography.fonts.mono,
|
|
341
|
+
display: action.font,
|
|
342
|
+
default: state.typography?.fonts.default ?? defaultTypography.fonts.default
|
|
343
|
+
},
|
|
344
|
+
scale: state.typography?.scale ?? defaultTypography.scale
|
|
345
|
+
}
|
|
346
|
+
};
|
|
347
|
+
}
|
|
348
|
+
case "SET_FONT_DEFAULT": {
|
|
349
|
+
const defaultTypography = DEFAULT_CONFIGURATOR_STATE.typography;
|
|
350
|
+
return {
|
|
351
|
+
...state,
|
|
352
|
+
typography: {
|
|
353
|
+
fonts: {
|
|
354
|
+
mono: state.typography?.fonts.mono ?? defaultTypography.fonts.mono,
|
|
355
|
+
display: state.typography?.fonts.display ?? defaultTypography.fonts.display,
|
|
356
|
+
default: action.font
|
|
357
|
+
},
|
|
358
|
+
scale: state.typography?.scale ?? defaultTypography.scale
|
|
359
|
+
}
|
|
360
|
+
};
|
|
361
|
+
}
|
|
362
|
+
// Icons actions
|
|
363
|
+
case "SET_ICON_VARIANT": {
|
|
364
|
+
const defaultIcons = DEFAULT_CONFIGURATOR_STATE.icons;
|
|
365
|
+
return {
|
|
366
|
+
...state,
|
|
367
|
+
icons: {
|
|
368
|
+
variant: action.variant,
|
|
369
|
+
weight: state.icons?.weight ?? defaultIcons.weight,
|
|
370
|
+
autoGrade: state.icons?.autoGrade ?? defaultIcons.autoGrade
|
|
371
|
+
}
|
|
372
|
+
};
|
|
373
|
+
}
|
|
374
|
+
case "SET_ICON_WEIGHT": {
|
|
375
|
+
const defaultIcons = DEFAULT_CONFIGURATOR_STATE.icons;
|
|
376
|
+
return {
|
|
377
|
+
...state,
|
|
378
|
+
icons: {
|
|
379
|
+
variant: state.icons?.variant ?? defaultIcons.variant,
|
|
380
|
+
weight: action.weight,
|
|
381
|
+
autoGrade: state.icons?.autoGrade ?? defaultIcons.autoGrade
|
|
382
|
+
}
|
|
383
|
+
};
|
|
384
|
+
}
|
|
385
|
+
case "SET_ICON_AUTO_GRADE": {
|
|
386
|
+
const defaultIcons = DEFAULT_CONFIGURATOR_STATE.icons;
|
|
387
|
+
return {
|
|
388
|
+
...state,
|
|
389
|
+
icons: {
|
|
390
|
+
variant: state.icons?.variant ?? defaultIcons.variant,
|
|
391
|
+
weight: state.icons?.weight ?? defaultIcons.weight,
|
|
392
|
+
autoGrade: action.autoGrade
|
|
393
|
+
}
|
|
394
|
+
};
|
|
395
|
+
}
|
|
195
396
|
// Preview actions
|
|
196
397
|
case "SET_PREVIEW_MODE":
|
|
197
398
|
return {
|
|
@@ -245,6 +446,57 @@ function traditionalHueToOklch(hue) {
|
|
|
245
446
|
}
|
|
246
447
|
|
|
247
448
|
// src/bridge/toThemeConfig.ts
|
|
449
|
+
var SPACING_PRESET_TO_BASE = {
|
|
450
|
+
xs: 6,
|
|
451
|
+
// Extra Small: compact/dense UI
|
|
452
|
+
sm: 7,
|
|
453
|
+
// Small: tighter spacing
|
|
454
|
+
md: 8,
|
|
455
|
+
// Medium: default/balanced
|
|
456
|
+
lg: 9,
|
|
457
|
+
// Large: more spacious
|
|
458
|
+
xl: 10
|
|
459
|
+
// Extra Large: maximum spacing
|
|
460
|
+
};
|
|
461
|
+
function roundnessToMultiplier(intensity) {
|
|
462
|
+
return intensity * 2;
|
|
463
|
+
}
|
|
464
|
+
function computeTypographyScale(baseSize, ratio) {
|
|
465
|
+
return {
|
|
466
|
+
xs: Math.round(baseSize / ratio ** 2),
|
|
467
|
+
sm: Math.round(baseSize / ratio),
|
|
468
|
+
base: baseSize,
|
|
469
|
+
md: Math.round(baseSize * ratio),
|
|
470
|
+
lg: Math.round(baseSize * ratio ** 2),
|
|
471
|
+
xl: Math.round(baseSize * ratio ** 3),
|
|
472
|
+
xxl: Math.round(baseSize * ratio ** 4)
|
|
473
|
+
};
|
|
474
|
+
}
|
|
475
|
+
var DEFAULT_FONTS = {
|
|
476
|
+
mono: {
|
|
477
|
+
type: "system",
|
|
478
|
+
family: "ui-monospace",
|
|
479
|
+
fallback: "SFMono-Regular, Menlo, Monaco, Consolas, monospace"
|
|
480
|
+
},
|
|
481
|
+
display: {
|
|
482
|
+
type: "system",
|
|
483
|
+
family: "system-ui",
|
|
484
|
+
fallback: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'
|
|
485
|
+
},
|
|
486
|
+
default: {
|
|
487
|
+
type: "system",
|
|
488
|
+
family: "system-ui",
|
|
489
|
+
fallback: '-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif'
|
|
490
|
+
}
|
|
491
|
+
};
|
|
492
|
+
var DEFAULT_ICONS = {
|
|
493
|
+
variant: "rounded",
|
|
494
|
+
// Material Design 3 aesthetic
|
|
495
|
+
weight: 400,
|
|
496
|
+
// Normal weight
|
|
497
|
+
autoGrade: true
|
|
498
|
+
// Enable mode-aware grade
|
|
499
|
+
};
|
|
248
500
|
function toThemeConfig(state) {
|
|
249
501
|
const palettes = state.palettes.map((p) => {
|
|
250
502
|
const oklchHue = traditionalHueToOklch(p.hue);
|
|
@@ -254,7 +506,14 @@ function toThemeConfig(state) {
|
|
|
254
506
|
strength: p.hueGradeStrength,
|
|
255
507
|
direction: p.hueGradeDirection
|
|
256
508
|
} : void 0;
|
|
257
|
-
return {
|
|
509
|
+
return {
|
|
510
|
+
hue: oklchHue,
|
|
511
|
+
saturation: p.saturation,
|
|
512
|
+
desaturation,
|
|
513
|
+
paletteHueGrading,
|
|
514
|
+
...p.keyColor !== void 0 ? { keyNormalizedValue: p.keyColor } : {},
|
|
515
|
+
...p.keyColorDark !== void 0 ? { keyNormalizedValueDark: p.keyColorDark } : {}
|
|
516
|
+
};
|
|
258
517
|
});
|
|
259
518
|
const light = state.globalHueGrading.light.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.light.hue), strength: state.globalHueGrading.light.strength } : void 0;
|
|
260
519
|
const dark = state.globalHueGrading.dark.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.dark.hue), strength: state.globalHueGrading.dark.strength } : void 0;
|
|
@@ -264,6 +523,8 @@ function toThemeConfig(state) {
|
|
|
264
523
|
darkest: state.dynamicRange.darkest,
|
|
265
524
|
...hueGrading ? { hueGrading } : {}
|
|
266
525
|
};
|
|
526
|
+
const spacingBase = SPACING_PRESET_TO_BASE[state.spacing?.preset ?? "md"];
|
|
527
|
+
const radiusMultiplier = roundnessToMultiplier(state.roundness?.intensity ?? 0.5);
|
|
267
528
|
return {
|
|
268
529
|
colorSystem: { dynamicRange, palettes },
|
|
269
530
|
themes: {
|
|
@@ -274,21 +535,56 @@ function toThemeConfig(state) {
|
|
|
274
535
|
},
|
|
275
536
|
elevation: {
|
|
276
537
|
offsets: [-0.02, 0, 0.04]
|
|
277
|
-
}
|
|
538
|
+
},
|
|
539
|
+
spacing: {
|
|
540
|
+
"00": Math.round(spacingBase * 0),
|
|
541
|
+
// Always 0
|
|
542
|
+
"02": Math.round(spacingBase * 0.25),
|
|
543
|
+
"04": Math.round(spacingBase * 0.5),
|
|
544
|
+
"06": Math.round(spacingBase * 0.75),
|
|
545
|
+
"08": Math.round(spacingBase * 1),
|
|
546
|
+
// Equals base
|
|
547
|
+
"10": Math.round(spacingBase * 1.25),
|
|
548
|
+
"12": Math.round(spacingBase * 1.5),
|
|
549
|
+
"16": Math.round(spacingBase * 2),
|
|
550
|
+
"20": Math.round(spacingBase * 2.5),
|
|
551
|
+
"24": Math.round(spacingBase * 3),
|
|
552
|
+
"32": Math.round(spacingBase * 4),
|
|
553
|
+
"40": Math.round(spacingBase * 5),
|
|
554
|
+
"48": Math.round(spacingBase * 6)
|
|
555
|
+
},
|
|
556
|
+
radius: {
|
|
557
|
+
none: 0,
|
|
558
|
+
sm: Math.round(4 * radiusMultiplier),
|
|
559
|
+
md: Math.round(6 * radiusMultiplier),
|
|
560
|
+
lg: Math.round(8 * radiusMultiplier),
|
|
561
|
+
xl: Math.round(12 * radiusMultiplier),
|
|
562
|
+
pill: 999
|
|
563
|
+
},
|
|
564
|
+
typography: {
|
|
565
|
+
fonts: state.typography?.fonts ?? DEFAULT_FONTS,
|
|
566
|
+
scale: computeTypographyScale(
|
|
567
|
+
state.typography?.scale.baseSize ?? 16,
|
|
568
|
+
state.typography?.scale.ratio ?? 1.25
|
|
569
|
+
),
|
|
570
|
+
lineHeight: { tight: 1.25, normal: 1.5, relaxed: 1.75 },
|
|
571
|
+
fontWeight: { regular: 400, medium: 500, semibold: 600, bold: 700 }
|
|
572
|
+
},
|
|
573
|
+
icons: state.icons ?? DEFAULT_ICONS
|
|
278
574
|
};
|
|
279
575
|
}
|
|
280
576
|
|
|
281
577
|
// src/hooks/useConfigurator.ts
|
|
282
578
|
function useConfigurator(initialState) {
|
|
283
579
|
const mergedInitial = initialState ? { ...DEFAULT_CONFIGURATOR_STATE, ...initialState } : DEFAULT_CONFIGURATOR_STATE;
|
|
284
|
-
const [state, dispatch] =
|
|
285
|
-
const themeConfig =
|
|
286
|
-
const reset =
|
|
580
|
+
const [state, dispatch] = React.useReducer(configuratorReducer, mergedInitial);
|
|
581
|
+
const themeConfig = React.useMemo(() => toThemeConfig(state), [state]);
|
|
582
|
+
const reset = React.useCallback(() => dispatch({ type: "RESET" }), []);
|
|
287
583
|
return { state, dispatch, themeConfig, reset };
|
|
288
584
|
}
|
|
289
585
|
var PREVIEW_STEPS = 26;
|
|
290
586
|
function usePreviewColors(state) {
|
|
291
|
-
return
|
|
587
|
+
return React.useMemo(() => {
|
|
292
588
|
const light = state.globalHueGrading.light.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.light.hue), strength: state.globalHueGrading.light.strength } : void 0;
|
|
293
589
|
const dark = state.globalHueGrading.dark.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.dark.hue), strength: state.globalHueGrading.dark.strength } : void 0;
|
|
294
590
|
const hueGrading = light || dark ? { light, dark } : void 0;
|
|
@@ -315,6 +611,105 @@ var SEMANTIC_HUE_RANGES = {
|
|
|
315
611
|
4: { min: 345, max: 375 }
|
|
316
612
|
// Error (reds, wraps 0°)
|
|
317
613
|
};
|
|
614
|
+
function useWcagValidation(state, paletteIndex) {
|
|
615
|
+
return React.useMemo(() => {
|
|
616
|
+
const palette = state.palettes[paletteIndex];
|
|
617
|
+
const neutral = state.palettes[0];
|
|
618
|
+
if (!palette || !neutral) {
|
|
619
|
+
return { keyColorContrast: null, passesAA: true, passesAALargeText: true, autoNormalizedValue: 0.5 };
|
|
620
|
+
}
|
|
621
|
+
const mode = state.preview.mode;
|
|
622
|
+
const light = state.globalHueGrading.light.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.light.hue), strength: state.globalHueGrading.light.strength } : void 0;
|
|
623
|
+
const dark = state.globalHueGrading.dark.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.dark.hue), strength: state.globalHueGrading.dark.strength } : void 0;
|
|
624
|
+
const hueGrading = light || dark ? { light, dark } : void 0;
|
|
625
|
+
const dynamicRange = {
|
|
626
|
+
lightest: state.dynamicRange.lightest,
|
|
627
|
+
darkest: state.dynamicRange.darkest,
|
|
628
|
+
...hueGrading ? { hueGrading } : {}
|
|
629
|
+
};
|
|
630
|
+
const neutralOklchHue = traditionalHueToOklch(neutral.hue);
|
|
631
|
+
const neutralDesat = neutral.desaturationStrength !== "none" ? { direction: neutral.desaturationDirection, strength: neutral.desaturationStrength } : void 0;
|
|
632
|
+
const neutralPhg = neutral.hueGradeStrength !== "none" ? { hue: traditionalHueToOklch(neutral.hueGradeHue), strength: neutral.hueGradeStrength, direction: neutral.hueGradeDirection } : void 0;
|
|
633
|
+
const backgroundNv = mode === "light" ? 0.95 : 0.1;
|
|
634
|
+
const background = newtone.getColor(neutralOklchHue, neutral.saturation, dynamicRange, backgroundNv, neutralDesat, neutralPhg);
|
|
635
|
+
const paletteOklchHue = traditionalHueToOklch(palette.hue);
|
|
636
|
+
const effectiveTextMode = mode === "light" ? "light" : "dark";
|
|
637
|
+
const paletteDesat = palette.desaturationStrength !== "none" ? { direction: palette.desaturationDirection, strength: palette.desaturationStrength } : void 0;
|
|
638
|
+
const palettePhg = palette.hueGradeStrength !== "none" ? { hue: traditionalHueToOklch(palette.hueGradeHue), strength: palette.hueGradeStrength, direction: palette.hueGradeDirection } : void 0;
|
|
639
|
+
const autoColor = newtone.getColorByContrast(
|
|
640
|
+
paletteOklchHue,
|
|
641
|
+
palette.saturation,
|
|
642
|
+
dynamicRange,
|
|
643
|
+
4.5,
|
|
644
|
+
effectiveTextMode,
|
|
645
|
+
paletteDesat,
|
|
646
|
+
palettePhg,
|
|
647
|
+
background
|
|
648
|
+
);
|
|
649
|
+
const autoNormalizedValue = newtone.lightnessToNormalizedValue(dynamicRange, autoColor.oklch.L);
|
|
650
|
+
const effectiveKeyColor = mode === "dark" ? palette.keyColorDark : palette.keyColor;
|
|
651
|
+
if (effectiveKeyColor === void 0) {
|
|
652
|
+
return { keyColorContrast: null, passesAA: true, passesAALargeText: true, autoNormalizedValue };
|
|
653
|
+
}
|
|
654
|
+
const keyColor = newtone.getColor(
|
|
655
|
+
paletteOklchHue,
|
|
656
|
+
palette.saturation,
|
|
657
|
+
dynamicRange,
|
|
658
|
+
effectiveKeyColor,
|
|
659
|
+
paletteDesat,
|
|
660
|
+
palettePhg
|
|
661
|
+
);
|
|
662
|
+
const contrast = newtone.getWcagContrastRatio(keyColor.srgb, background.srgb);
|
|
663
|
+
return {
|
|
664
|
+
keyColorContrast: contrast,
|
|
665
|
+
passesAA: contrast >= 4.5,
|
|
666
|
+
passesAALargeText: contrast >= 3,
|
|
667
|
+
autoNormalizedValue
|
|
668
|
+
};
|
|
669
|
+
}, [state, paletteIndex]);
|
|
670
|
+
}
|
|
671
|
+
var ACHROMATIC_THRESHOLD = 5e-3;
|
|
672
|
+
var traditionalHueLut = null;
|
|
673
|
+
function buildTraditionalHueLut() {
|
|
674
|
+
const lut = new Array(360);
|
|
675
|
+
for (let h = 0; h < 360; h++) {
|
|
676
|
+
lut[h] = traditionalHueToOklch(h);
|
|
677
|
+
}
|
|
678
|
+
return lut;
|
|
679
|
+
}
|
|
680
|
+
function oklchHueToTraditional(oklchHue) {
|
|
681
|
+
if (!traditionalHueLut) {
|
|
682
|
+
traditionalHueLut = buildTraditionalHueLut();
|
|
683
|
+
}
|
|
684
|
+
const target = (oklchHue % 360 + 360) % 360;
|
|
685
|
+
let bestHue = 0;
|
|
686
|
+
let bestDelta = Infinity;
|
|
687
|
+
for (let h = 0; h < 360; h++) {
|
|
688
|
+
const raw = Math.abs(traditionalHueLut[h] - target);
|
|
689
|
+
const delta = Math.min(raw, 360 - raw);
|
|
690
|
+
if (delta < bestDelta) {
|
|
691
|
+
bestDelta = delta;
|
|
692
|
+
bestHue = h;
|
|
693
|
+
}
|
|
694
|
+
}
|
|
695
|
+
return bestHue;
|
|
696
|
+
}
|
|
697
|
+
function hexToPaletteParams(hex, dynamicRange) {
|
|
698
|
+
const cleaned = hex.startsWith("#") ? hex.slice(1) : hex;
|
|
699
|
+
if (!/^[0-9a-fA-F]{3}$/.test(cleaned) && !/^[0-9a-fA-F]{6}$/.test(cleaned)) {
|
|
700
|
+
return null;
|
|
701
|
+
}
|
|
702
|
+
const srgb = newtone.hexToSrgb(hex);
|
|
703
|
+
const oklch = newtone.srgbToOklch(srgb);
|
|
704
|
+
const normalizedValue = newtone.lightnessToNormalizedValue(dynamicRange, oklch.L);
|
|
705
|
+
if (oklch.C < ACHROMATIC_THRESHOLD) {
|
|
706
|
+
return { hue: 0, saturation: 0, normalizedValue };
|
|
707
|
+
}
|
|
708
|
+
const hue = oklchHueToTraditional(oklch.h);
|
|
709
|
+
const maxChroma = newtone.findMaxChromaInGamut(oklch.L, oklch.h);
|
|
710
|
+
const saturation = maxChroma > 0 ? Math.min(100, Math.round(oklch.C / maxChroma * 100)) : 0;
|
|
711
|
+
return { hue, saturation, normalizedValue };
|
|
712
|
+
}
|
|
318
713
|
|
|
319
714
|
// src/panels/PalettePanel.tsx
|
|
320
715
|
var STRENGTH_OPTIONS = [
|
|
@@ -323,16 +718,124 @@ var STRENGTH_OPTIONS = [
|
|
|
323
718
|
{ label: "Medium", value: "medium" },
|
|
324
719
|
{ label: "Hard", value: "hard" }
|
|
325
720
|
];
|
|
326
|
-
function
|
|
721
|
+
function getHexAtNv(previewColors, nv) {
|
|
722
|
+
const idx = Math.round((1 - nv) * (previewColors.length - 1));
|
|
723
|
+
const clamped = Math.max(0, Math.min(previewColors.length - 1, idx));
|
|
724
|
+
return newtone.srgbToHex(previewColors[clamped].srgb);
|
|
725
|
+
}
|
|
726
|
+
function PalettePanel({ palette, index, dispatch, previewColors, state }) {
|
|
327
727
|
const tokens = components.useTokens(1);
|
|
328
728
|
const hueRange = SEMANTIC_HUE_RANGES[index];
|
|
329
|
-
|
|
729
|
+
const isNeutral = index === 0;
|
|
730
|
+
const mode = state.preview.mode;
|
|
731
|
+
const effectiveKeyColor = mode === "dark" ? palette.keyColorDark : palette.keyColor;
|
|
732
|
+
const setKeyColorAction = mode === "dark" ? "SET_PALETTE_KEY_COLOR_DARK" : "SET_PALETTE_KEY_COLOR";
|
|
733
|
+
const clearKeyColorAction = mode === "dark" ? "CLEAR_PALETTE_KEY_COLOR_DARK" : "CLEAR_PALETTE_KEY_COLOR";
|
|
734
|
+
const hexActionType = mode === "dark" ? "SET_PALETTE_FROM_HEX_DARK" : "SET_PALETTE_FROM_HEX";
|
|
735
|
+
const wcag = useWcagValidation(state, index);
|
|
736
|
+
const [hexText, setHexText] = React__default.default.useState("");
|
|
737
|
+
const [hexError, setHexError] = React__default.default.useState("");
|
|
738
|
+
const [isEditingHex, setIsEditingHex] = React__default.default.useState(false);
|
|
739
|
+
const [isHexUserSet, setIsHexUserSet] = React__default.default.useState(false);
|
|
740
|
+
React__default.default.useEffect(() => {
|
|
741
|
+
setHexText("");
|
|
742
|
+
setHexError("");
|
|
743
|
+
setIsEditingHex(false);
|
|
744
|
+
setIsHexUserSet(false);
|
|
745
|
+
}, [mode]);
|
|
746
|
+
const displayedHex = React__default.default.useMemo(() => {
|
|
747
|
+
if (!previewColors || previewColors.length === 0) return "";
|
|
748
|
+
const nv = effectiveKeyColor ?? wcag.autoNormalizedValue;
|
|
749
|
+
return getHexAtNv(previewColors, nv);
|
|
750
|
+
}, [previewColors, effectiveKeyColor, wcag.autoNormalizedValue]);
|
|
751
|
+
React__default.default.useEffect(() => {
|
|
752
|
+
if (!isEditingHex && !isHexUserSet) {
|
|
753
|
+
setHexText(displayedHex);
|
|
754
|
+
}
|
|
755
|
+
}, [displayedHex, isEditingHex, isHexUserSet]);
|
|
756
|
+
const dynamicRange = React__default.default.useMemo(() => {
|
|
757
|
+
const light = state.globalHueGrading.light.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.light.hue), strength: state.globalHueGrading.light.strength } : void 0;
|
|
758
|
+
const dark = state.globalHueGrading.dark.strength !== "none" ? { hue: traditionalHueToOklch(state.globalHueGrading.dark.hue), strength: state.globalHueGrading.dark.strength } : void 0;
|
|
759
|
+
const hueGrading = light || dark ? { light, dark } : void 0;
|
|
760
|
+
return {
|
|
761
|
+
lightest: state.dynamicRange.lightest,
|
|
762
|
+
darkest: state.dynamicRange.darkest,
|
|
763
|
+
...hueGrading ? { hueGrading } : {}
|
|
764
|
+
};
|
|
765
|
+
}, [state.dynamicRange, state.globalHueGrading]);
|
|
766
|
+
const handleHexSubmit = React__default.default.useCallback(() => {
|
|
767
|
+
setIsEditingHex(false);
|
|
768
|
+
const trimmed = hexText.trim();
|
|
769
|
+
if (!trimmed) {
|
|
770
|
+
setHexError("");
|
|
771
|
+
return;
|
|
772
|
+
}
|
|
773
|
+
const hex = trimmed.startsWith("#") ? trimmed : `#${trimmed}`;
|
|
774
|
+
const params = hexToPaletteParams(hex, dynamicRange);
|
|
775
|
+
if (!params) {
|
|
776
|
+
setHexError("Invalid hex color");
|
|
777
|
+
return;
|
|
778
|
+
}
|
|
779
|
+
setHexError("");
|
|
780
|
+
setIsHexUserSet(true);
|
|
781
|
+
dispatch({
|
|
782
|
+
type: hexActionType,
|
|
783
|
+
index,
|
|
784
|
+
hue: params.hue,
|
|
785
|
+
saturation: params.saturation,
|
|
786
|
+
keyColor: params.normalizedValue
|
|
787
|
+
});
|
|
788
|
+
}, [hexText, dynamicRange, dispatch, index, hexActionType]);
|
|
789
|
+
const handleClearKeyColor = React__default.default.useCallback(() => {
|
|
790
|
+
dispatch({ type: clearKeyColorAction, index });
|
|
791
|
+
setHexError("");
|
|
792
|
+
setIsHexUserSet(false);
|
|
793
|
+
}, [dispatch, index, clearKeyColorAction]);
|
|
794
|
+
const wcagWarning = React__default.default.useMemo(() => {
|
|
795
|
+
if (effectiveKeyColor === void 0 || wcag.keyColorContrast === null) return void 0;
|
|
796
|
+
if (wcag.passesAA) return void 0;
|
|
797
|
+
const ratio = wcag.keyColorContrast.toFixed(1);
|
|
798
|
+
if (wcag.passesAALargeText) {
|
|
799
|
+
return `Contrast ${ratio}:1 \u2014 passes large text (AA) but fails normal text (requires 4.5:1)`;
|
|
800
|
+
}
|
|
801
|
+
return `Contrast ${ratio}:1 \u2014 fails WCAG AA (requires 4.5:1 for normal text, 3:1 for large text)`;
|
|
802
|
+
}, [effectiveKeyColor, wcag]);
|
|
803
|
+
return /* @__PURE__ */ React__default.default.createElement(components.Card, { elevation: 1, style: styles.container }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles.title, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, palette.name), !isNeutral && previewColors && /* @__PURE__ */ React__default.default.createElement(React__default.default.Fragment, null, /* @__PURE__ */ React__default.default.createElement(
|
|
804
|
+
components.ColorScaleSlider,
|
|
805
|
+
{
|
|
806
|
+
colors: previewColors,
|
|
807
|
+
value: effectiveKeyColor ?? wcag.autoNormalizedValue,
|
|
808
|
+
onValueChange: (nv) => {
|
|
809
|
+
setIsHexUserSet(false);
|
|
810
|
+
dispatch({ type: setKeyColorAction, index, normalizedValue: nv });
|
|
811
|
+
},
|
|
812
|
+
label: "Key Color",
|
|
813
|
+
warning: wcagWarning,
|
|
814
|
+
trimEnds: true,
|
|
815
|
+
snap: true,
|
|
816
|
+
animateValue: true
|
|
817
|
+
}
|
|
818
|
+
), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.hexRow }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.hexInputContainer }, /* @__PURE__ */ React__default.default.createElement(
|
|
819
|
+
components.TextInput,
|
|
820
|
+
{
|
|
821
|
+
label: "Hex",
|
|
822
|
+
value: hexText,
|
|
823
|
+
onChangeText: (text) => {
|
|
824
|
+
setIsEditingHex(true);
|
|
825
|
+
setHexText(text);
|
|
826
|
+
setHexError("");
|
|
827
|
+
},
|
|
828
|
+
onBlur: handleHexSubmit,
|
|
829
|
+
onSubmitEditing: handleHexSubmit,
|
|
830
|
+
placeholder: "#000000"
|
|
831
|
+
}
|
|
832
|
+
)), effectiveKeyColor !== void 0 && /* @__PURE__ */ React__default.default.createElement(reactNative.Pressable, { onPress: handleClearKeyColor, style: styles.autoButton }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles.autoText, { color: newtone.srgbToHex(tokens.interactive.srgb) }] }, "Auto"))), hexError !== "" && /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles.errorText, { color: newtone.srgbToHex(tokens.error.srgb) }] }, hexError)), isNeutral && previewColors && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.inlineSwatches }, previewColors.map((color, i) => /* @__PURE__ */ React__default.default.createElement(
|
|
330
833
|
reactNative.View,
|
|
331
834
|
{
|
|
332
835
|
key: i,
|
|
333
836
|
style: [styles.inlineSwatch, { backgroundColor: newtone.srgbToHex(color.srgb) }]
|
|
334
837
|
}
|
|
335
|
-
))), /* @__PURE__ */
|
|
838
|
+
))), /* @__PURE__ */ React__default.default.createElement(
|
|
336
839
|
components.HueSlider,
|
|
337
840
|
{
|
|
338
841
|
value: palette.hue,
|
|
@@ -341,7 +844,7 @@ function PalettePanel({ palette, index, dispatch, previewColors }) {
|
|
|
341
844
|
showValue: true,
|
|
342
845
|
...hueRange ? { min: hueRange.min, max: hueRange.max } : {}
|
|
343
846
|
}
|
|
344
|
-
), /* @__PURE__ */
|
|
847
|
+
), /* @__PURE__ */ React__default.default.createElement(
|
|
345
848
|
components.Slider,
|
|
346
849
|
{
|
|
347
850
|
value: palette.saturation,
|
|
@@ -351,7 +854,7 @@ function PalettePanel({ palette, index, dispatch, previewColors }) {
|
|
|
351
854
|
label: "Saturation",
|
|
352
855
|
showValue: true
|
|
353
856
|
}
|
|
354
|
-
), /* @__PURE__ */
|
|
857
|
+
), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
355
858
|
components.Select,
|
|
356
859
|
{
|
|
357
860
|
options: STRENGTH_OPTIONS,
|
|
@@ -359,14 +862,14 @@ function PalettePanel({ palette, index, dispatch, previewColors }) {
|
|
|
359
862
|
onValueChange: (strength) => dispatch({ type: "SET_PALETTE_DESAT_STRENGTH", index, strength }),
|
|
360
863
|
label: "Desaturation"
|
|
361
864
|
}
|
|
362
|
-
)), palette.desaturationStrength !== "none" && /* @__PURE__ */
|
|
865
|
+
)), palette.desaturationStrength !== "none" && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.toggleContainer }, /* @__PURE__ */ React__default.default.createElement(
|
|
363
866
|
components.Toggle,
|
|
364
867
|
{
|
|
365
868
|
value: palette.desaturationDirection === "dark",
|
|
366
869
|
onValueChange: (v) => dispatch({ type: "SET_PALETTE_DESAT_DIRECTION", index, direction: v ? "dark" : "light" }),
|
|
367
870
|
label: "Invert"
|
|
368
871
|
}
|
|
369
|
-
))), /* @__PURE__ */
|
|
872
|
+
))), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
370
873
|
components.Select,
|
|
371
874
|
{
|
|
372
875
|
options: STRENGTH_OPTIONS,
|
|
@@ -374,14 +877,14 @@ function PalettePanel({ palette, index, dispatch, previewColors }) {
|
|
|
374
877
|
onValueChange: (strength) => dispatch({ type: "SET_PALETTE_HUE_GRADE_STRENGTH", index, strength }),
|
|
375
878
|
label: "Hue Grading"
|
|
376
879
|
}
|
|
377
|
-
)), palette.hueGradeStrength !== "none" && /* @__PURE__ */
|
|
880
|
+
)), palette.hueGradeStrength !== "none" && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles.toggleContainer }, /* @__PURE__ */ React__default.default.createElement(
|
|
378
881
|
components.Toggle,
|
|
379
882
|
{
|
|
380
883
|
value: palette.hueGradeDirection === "dark",
|
|
381
884
|
onValueChange: (v) => dispatch({ type: "SET_PALETTE_HUE_GRADE_DIRECTION", index, direction: v ? "dark" : "light" }),
|
|
382
885
|
label: "Invert"
|
|
383
886
|
}
|
|
384
|
-
))), palette.hueGradeStrength !== "none" && /* @__PURE__ */
|
|
887
|
+
))), palette.hueGradeStrength !== "none" && /* @__PURE__ */ React__default.default.createElement(
|
|
385
888
|
components.HueSlider,
|
|
386
889
|
{
|
|
387
890
|
value: palette.hueGradeHue,
|
|
@@ -420,6 +923,25 @@ var styles = reactNative.StyleSheet.create({
|
|
|
420
923
|
},
|
|
421
924
|
toggleContainer: {
|
|
422
925
|
paddingBottom: 2
|
|
926
|
+
},
|
|
927
|
+
hexRow: {
|
|
928
|
+
flexDirection: "row",
|
|
929
|
+
alignItems: "flex-end",
|
|
930
|
+
gap: 8
|
|
931
|
+
},
|
|
932
|
+
hexInputContainer: {
|
|
933
|
+
flex: 1
|
|
934
|
+
},
|
|
935
|
+
autoButton: {
|
|
936
|
+
paddingBottom: 6
|
|
937
|
+
},
|
|
938
|
+
autoText: {
|
|
939
|
+
fontSize: 13,
|
|
940
|
+
fontWeight: "600"
|
|
941
|
+
},
|
|
942
|
+
errorText: {
|
|
943
|
+
fontSize: 12,
|
|
944
|
+
fontWeight: "500"
|
|
423
945
|
}
|
|
424
946
|
});
|
|
425
947
|
var STRENGTH_OPTIONS2 = [
|
|
@@ -430,7 +952,7 @@ var STRENGTH_OPTIONS2 = [
|
|
|
430
952
|
];
|
|
431
953
|
function GlobalPanel({ state, dispatch }) {
|
|
432
954
|
const tokens = components.useTokens(1);
|
|
433
|
-
return /* @__PURE__ */
|
|
955
|
+
return /* @__PURE__ */ React__default.default.createElement(components.Card, { elevation: 1, style: styles2.container }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles2.title, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Dynamic Range"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
434
956
|
components.Slider,
|
|
435
957
|
{
|
|
436
958
|
value: Math.round(state.dynamicRange.lightest * 100),
|
|
@@ -440,7 +962,7 @@ function GlobalPanel({ state, dispatch }) {
|
|
|
440
962
|
label: "Lightest",
|
|
441
963
|
showValue: true
|
|
442
964
|
}
|
|
443
|
-
)), /* @__PURE__ */
|
|
965
|
+
)), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
444
966
|
components.Slider,
|
|
445
967
|
{
|
|
446
968
|
value: Math.round(state.dynamicRange.darkest * 100),
|
|
@@ -450,7 +972,7 @@ function GlobalPanel({ state, dispatch }) {
|
|
|
450
972
|
label: "Darkest",
|
|
451
973
|
showValue: true
|
|
452
974
|
}
|
|
453
|
-
))), /* @__PURE__ */
|
|
975
|
+
))), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles2.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Global Hue Grading \u2014 Light End"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
454
976
|
components.Select,
|
|
455
977
|
{
|
|
456
978
|
options: STRENGTH_OPTIONS2,
|
|
@@ -458,7 +980,7 @@ function GlobalPanel({ state, dispatch }) {
|
|
|
458
980
|
onValueChange: (s) => dispatch({ type: "SET_GLOBAL_GRADE_LIGHT_STRENGTH", strength: s }),
|
|
459
981
|
label: "Strength"
|
|
460
982
|
}
|
|
461
|
-
)), state.globalHueGrading.light.strength !== "none" && /* @__PURE__ */
|
|
983
|
+
)), state.globalHueGrading.light.strength !== "none" && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
462
984
|
components.HueSlider,
|
|
463
985
|
{
|
|
464
986
|
value: state.globalHueGrading.light.hue,
|
|
@@ -466,7 +988,7 @@ function GlobalPanel({ state, dispatch }) {
|
|
|
466
988
|
label: "Target Hue",
|
|
467
989
|
showValue: true
|
|
468
990
|
}
|
|
469
|
-
))), /* @__PURE__ */
|
|
991
|
+
))), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles2.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Global Hue Grading \u2014 Dark End"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
470
992
|
components.Select,
|
|
471
993
|
{
|
|
472
994
|
options: STRENGTH_OPTIONS2,
|
|
@@ -474,7 +996,7 @@ function GlobalPanel({ state, dispatch }) {
|
|
|
474
996
|
onValueChange: (s) => dispatch({ type: "SET_GLOBAL_GRADE_DARK_STRENGTH", strength: s }),
|
|
475
997
|
label: "Strength"
|
|
476
998
|
}
|
|
477
|
-
)), state.globalHueGrading.dark.strength !== "none" && /* @__PURE__ */
|
|
999
|
+
)), state.globalHueGrading.dark.strength !== "none" && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles2.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
478
1000
|
components.HueSlider,
|
|
479
1001
|
{
|
|
480
1002
|
value: state.globalHueGrading.dark.hue,
|
|
@@ -516,7 +1038,7 @@ function PreviewCard({
|
|
|
516
1038
|
dispatch
|
|
517
1039
|
}) {
|
|
518
1040
|
const tokens = components.useTokens(1);
|
|
519
|
-
return /* @__PURE__ */
|
|
1041
|
+
return /* @__PURE__ */ React__default.default.createElement(components.Card, { elevation: 1, style: styles3.container }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles3.title, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Component Preview"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles3.controls }, /* @__PURE__ */ React__default.default.createElement(
|
|
520
1042
|
components.Select,
|
|
521
1043
|
{
|
|
522
1044
|
options: THEME_OPTIONS,
|
|
@@ -524,11 +1046,11 @@ function PreviewCard({
|
|
|
524
1046
|
onValueChange: (t) => dispatch({ type: "SET_PREVIEW_THEME", theme: t }),
|
|
525
1047
|
label: "Theme"
|
|
526
1048
|
}
|
|
527
|
-
)), /* @__PURE__ */
|
|
528
|
-
} }), /* @__PURE__ */
|
|
1049
|
+
)), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: previewStyles.wrapper }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: previewStyles.row }, /* @__PURE__ */ React__default.default.createElement(components.Button, { variant: "primary", size: "sm" }, "Primary"), /* @__PURE__ */ React__default.default.createElement(components.Button, { variant: "secondary", size: "sm" }, "Secondary"), /* @__PURE__ */ React__default.default.createElement(components.Button, { variant: "ghost", size: "sm" }, "Ghost"), /* @__PURE__ */ React__default.default.createElement(components.Button, { variant: "outline", size: "sm" }, "Outline")), /* @__PURE__ */ React__default.default.createElement(components.TextInput, { label: "Sample Input", value: "Hello, Newtone", onChangeText: () => {
|
|
1050
|
+
} }), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: previewStyles.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: [previewStyles.statusDot, { backgroundColor: newtone.srgbToHex(tokens.success.srgb) }] }), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [previewStyles.statusText, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Success"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: [previewStyles.statusDot, { backgroundColor: newtone.srgbToHex(tokens.warning.srgb) }] }), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [previewStyles.statusText, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Warning"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: [previewStyles.statusDot, { backgroundColor: newtone.srgbToHex(tokens.error.srgb) }] }), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [previewStyles.statusText, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Error"))));
|
|
529
1051
|
}
|
|
530
1052
|
function PreviewPanel({ state, dispatch, themeConfig }) {
|
|
531
|
-
return /* @__PURE__ */
|
|
1053
|
+
return /* @__PURE__ */ React__default.default.createElement(
|
|
532
1054
|
components.NewtoneProvider,
|
|
533
1055
|
{
|
|
534
1056
|
key: `${state.preview.mode}-${state.preview.theme}`,
|
|
@@ -536,7 +1058,7 @@ function PreviewPanel({ state, dispatch, themeConfig }) {
|
|
|
536
1058
|
initialMode: state.preview.mode,
|
|
537
1059
|
initialTheme: state.preview.theme
|
|
538
1060
|
},
|
|
539
|
-
/* @__PURE__ */
|
|
1061
|
+
/* @__PURE__ */ React__default.default.createElement(PreviewCard, { state, dispatch })
|
|
540
1062
|
);
|
|
541
1063
|
}
|
|
542
1064
|
var styles3 = reactNative.StyleSheet.create({
|
|
@@ -583,7 +1105,11 @@ function toCSS(state) {
|
|
|
583
1105
|
mode,
|
|
584
1106
|
config.themes.neutral,
|
|
585
1107
|
1,
|
|
586
|
-
config.elevation.offsets
|
|
1108
|
+
config.elevation.offsets,
|
|
1109
|
+
config.spacing,
|
|
1110
|
+
config.radius,
|
|
1111
|
+
config.typography,
|
|
1112
|
+
config.icons
|
|
587
1113
|
);
|
|
588
1114
|
const selector = mode === "light" ? ":root" : '[data-theme="dark"]';
|
|
589
1115
|
css += `${selector} {
|
|
@@ -632,12 +1158,12 @@ function toJSON(state) {
|
|
|
632
1158
|
// src/panels/ExportPanel.tsx
|
|
633
1159
|
function ExportPanel({ state }) {
|
|
634
1160
|
const tokens = components.useTokens(1);
|
|
635
|
-
const [format, setFormat] =
|
|
636
|
-
const [copied, setCopied] =
|
|
637
|
-
const output =
|
|
1161
|
+
const [format, setFormat] = React.useState("css");
|
|
1162
|
+
const [copied, setCopied] = React.useState(false);
|
|
1163
|
+
const output = React.useMemo(() => {
|
|
638
1164
|
return format === "css" ? toCSS(state) : toJSON(state);
|
|
639
1165
|
}, [state, format]);
|
|
640
|
-
const handleCopy =
|
|
1166
|
+
const handleCopy = React.useCallback(() => {
|
|
641
1167
|
if (typeof navigator !== "undefined" && navigator.clipboard) {
|
|
642
1168
|
navigator.clipboard.writeText(output).then(() => {
|
|
643
1169
|
setCopied(true);
|
|
@@ -645,7 +1171,7 @@ function ExportPanel({ state }) {
|
|
|
645
1171
|
});
|
|
646
1172
|
}
|
|
647
1173
|
}, [output]);
|
|
648
|
-
return /* @__PURE__ */
|
|
1174
|
+
return /* @__PURE__ */ React__default.default.createElement(components.Card, { elevation: 1, style: styles4.container }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles4.title, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Export"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles4.tabs }, /* @__PURE__ */ React__default.default.createElement(
|
|
649
1175
|
components.Button,
|
|
650
1176
|
{
|
|
651
1177
|
variant: format === "css" ? "primary" : "ghost",
|
|
@@ -653,7 +1179,7 @@ function ExportPanel({ state }) {
|
|
|
653
1179
|
onPress: () => setFormat("css")
|
|
654
1180
|
},
|
|
655
1181
|
"CSS Variables"
|
|
656
|
-
), /* @__PURE__ */
|
|
1182
|
+
), /* @__PURE__ */ React__default.default.createElement(
|
|
657
1183
|
components.Button,
|
|
658
1184
|
{
|
|
659
1185
|
variant: format === "json" ? "primary" : "ghost",
|
|
@@ -661,7 +1187,7 @@ function ExportPanel({ state }) {
|
|
|
661
1187
|
onPress: () => setFormat("json")
|
|
662
1188
|
},
|
|
663
1189
|
"JSON"
|
|
664
|
-
), /* @__PURE__ */
|
|
1190
|
+
), /* @__PURE__ */ React__default.default.createElement(components.Button, { variant: "outline", size: "sm", onPress: handleCopy }, copied ? "Copied!" : "Copy")), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: [styles4.codeBlock, { backgroundColor: newtone.srgbToHex(tokens.backgroundSunken.srgb) }] }, /* @__PURE__ */ React__default.default.createElement(
|
|
665
1191
|
reactNative.Text,
|
|
666
1192
|
{
|
|
667
1193
|
style: [styles4.code, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }],
|
|
@@ -695,6 +1221,113 @@ var styles4 = reactNative.StyleSheet.create({
|
|
|
695
1221
|
lineHeight: 16
|
|
696
1222
|
}
|
|
697
1223
|
});
|
|
1224
|
+
var ICON_VARIANT_OPTIONS = [
|
|
1225
|
+
{ label: "Outlined", value: "outlined" },
|
|
1226
|
+
{ label: "Rounded", value: "rounded" },
|
|
1227
|
+
{ label: "Sharp", value: "sharp" }
|
|
1228
|
+
];
|
|
1229
|
+
var ICON_WEIGHT_OPTIONS = [
|
|
1230
|
+
{ label: "100", value: "100" },
|
|
1231
|
+
{ label: "200", value: "200" },
|
|
1232
|
+
{ label: "300", value: "300" },
|
|
1233
|
+
{ label: "400", value: "400" },
|
|
1234
|
+
{ label: "500", value: "500" },
|
|
1235
|
+
{ label: "600", value: "600" },
|
|
1236
|
+
{ label: "700", value: "700" }
|
|
1237
|
+
];
|
|
1238
|
+
function DesignPanel({ state, dispatch }) {
|
|
1239
|
+
const tokens = components.useTokens(1);
|
|
1240
|
+
const spacingPreset = state.spacing?.preset ?? "md";
|
|
1241
|
+
const intensity = state.roundness?.intensity ?? 0.5;
|
|
1242
|
+
const baseSize = state.typography?.scale.baseSize ?? 16;
|
|
1243
|
+
const ratio = state.typography?.scale.ratio ?? 1.25;
|
|
1244
|
+
const variant = state.icons?.variant ?? "rounded";
|
|
1245
|
+
const weight = state.icons?.weight ?? 400;
|
|
1246
|
+
return /* @__PURE__ */ React__default.default.createElement(components.Card, { elevation: 1, style: styles5.container }, /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles5.title, { color: newtone.srgbToHex(tokens.textPrimary.srgb) }] }, "Design System"), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles5.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Spacing"), /* @__PURE__ */ React__default.default.createElement(
|
|
1247
|
+
components.Select,
|
|
1248
|
+
{
|
|
1249
|
+
value: spacingPreset,
|
|
1250
|
+
onValueChange: (preset) => dispatch({ type: "SET_SPACING_PRESET", preset }),
|
|
1251
|
+
options: [
|
|
1252
|
+
{ value: "xs", label: "Extra Small" },
|
|
1253
|
+
{ value: "sm", label: "Small" },
|
|
1254
|
+
{ value: "md", label: "Medium" },
|
|
1255
|
+
{ value: "lg", label: "Large" },
|
|
1256
|
+
{ value: "xl", label: "Extra Large" }
|
|
1257
|
+
],
|
|
1258
|
+
label: "Preset"
|
|
1259
|
+
}
|
|
1260
|
+
), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles5.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Roundness"), /* @__PURE__ */ React__default.default.createElement(
|
|
1261
|
+
components.Slider,
|
|
1262
|
+
{
|
|
1263
|
+
value: Math.round(intensity * 100),
|
|
1264
|
+
onValueChange: (v) => dispatch({ type: "SET_ROUNDNESS_INTENSITY", intensity: v / 100 }),
|
|
1265
|
+
min: 0,
|
|
1266
|
+
max: 100,
|
|
1267
|
+
label: "Intensity",
|
|
1268
|
+
showValue: true
|
|
1269
|
+
}
|
|
1270
|
+
), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles5.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Typography"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
1271
|
+
components.Slider,
|
|
1272
|
+
{
|
|
1273
|
+
value: baseSize,
|
|
1274
|
+
onValueChange: (v) => dispatch({ type: "SET_TYPOGRAPHY_BASE_SIZE", baseSize: v }),
|
|
1275
|
+
min: 12,
|
|
1276
|
+
max: 24,
|
|
1277
|
+
step: 1,
|
|
1278
|
+
label: "Base Size",
|
|
1279
|
+
showValue: true
|
|
1280
|
+
}
|
|
1281
|
+
)), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
1282
|
+
components.Slider,
|
|
1283
|
+
{
|
|
1284
|
+
value: Math.round(ratio * 100),
|
|
1285
|
+
onValueChange: (v) => dispatch({ type: "SET_TYPOGRAPHY_RATIO", ratio: v / 100 }),
|
|
1286
|
+
min: 110,
|
|
1287
|
+
max: 150,
|
|
1288
|
+
step: 5,
|
|
1289
|
+
label: "Scale Ratio",
|
|
1290
|
+
showValue: true
|
|
1291
|
+
}
|
|
1292
|
+
))), /* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [styles5.subtitle, { color: newtone.srgbToHex(tokens.textSecondary.srgb) }] }, "Icons"), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.row }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
1293
|
+
components.Select,
|
|
1294
|
+
{
|
|
1295
|
+
options: ICON_VARIANT_OPTIONS,
|
|
1296
|
+
value: variant,
|
|
1297
|
+
onValueChange: (v) => dispatch({ type: "SET_ICON_VARIANT", variant: v }),
|
|
1298
|
+
label: "Variant"
|
|
1299
|
+
}
|
|
1300
|
+
)), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles5.flex }, /* @__PURE__ */ React__default.default.createElement(
|
|
1301
|
+
components.Select,
|
|
1302
|
+
{
|
|
1303
|
+
options: ICON_WEIGHT_OPTIONS,
|
|
1304
|
+
value: weight.toString(),
|
|
1305
|
+
onValueChange: (v) => dispatch({ type: "SET_ICON_WEIGHT", weight: parseInt(v) }),
|
|
1306
|
+
label: "Weight"
|
|
1307
|
+
}
|
|
1308
|
+
))));
|
|
1309
|
+
}
|
|
1310
|
+
var styles5 = reactNative.StyleSheet.create({
|
|
1311
|
+
container: {
|
|
1312
|
+
gap: 12
|
|
1313
|
+
},
|
|
1314
|
+
title: {
|
|
1315
|
+
fontSize: 16,
|
|
1316
|
+
fontWeight: "700"
|
|
1317
|
+
},
|
|
1318
|
+
subtitle: {
|
|
1319
|
+
fontSize: 13,
|
|
1320
|
+
fontWeight: "600",
|
|
1321
|
+
marginTop: 4
|
|
1322
|
+
},
|
|
1323
|
+
row: {
|
|
1324
|
+
flexDirection: "row",
|
|
1325
|
+
gap: 12
|
|
1326
|
+
},
|
|
1327
|
+
flex: {
|
|
1328
|
+
flex: 1
|
|
1329
|
+
}
|
|
1330
|
+
});
|
|
698
1331
|
|
|
699
1332
|
// src/Configurator.tsx
|
|
700
1333
|
function Configurator({
|
|
@@ -706,20 +1339,20 @@ function Configurator({
|
|
|
706
1339
|
const { state, dispatch, themeConfig, reset } = useConfigurator(initialState);
|
|
707
1340
|
const tokens = components.useTokens(1);
|
|
708
1341
|
const { setMode } = components.useNewtoneTheme();
|
|
709
|
-
const isInitialRender =
|
|
710
|
-
const [activePaletteIndex, setActivePaletteIndex] =
|
|
1342
|
+
const isInitialRender = React.useRef(true);
|
|
1343
|
+
const [activePaletteIndex, setActivePaletteIndex] = React.useState(0);
|
|
711
1344
|
const previews = usePreviewColors(state);
|
|
712
|
-
|
|
1345
|
+
React.useEffect(() => {
|
|
713
1346
|
setMode(state.preview.mode);
|
|
714
1347
|
}, []);
|
|
715
|
-
|
|
1348
|
+
React.useEffect(() => {
|
|
716
1349
|
if (isInitialRender.current) {
|
|
717
1350
|
isInitialRender.current = false;
|
|
718
1351
|
return;
|
|
719
1352
|
}
|
|
720
1353
|
onChange?.(state, themeConfig);
|
|
721
1354
|
}, [state, themeConfig, onChange]);
|
|
722
|
-
return /* @__PURE__ */
|
|
1355
|
+
return /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: [styles6.container, { backgroundColor: newtone.srgbToHex(tokens.backgroundSunken.srgb) }] }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.topBar }, /* @__PURE__ */ React__default.default.createElement(
|
|
723
1356
|
components.Toggle,
|
|
724
1357
|
{
|
|
725
1358
|
value: state.preview.mode === "dark",
|
|
@@ -730,21 +1363,21 @@ function Configurator({
|
|
|
730
1363
|
},
|
|
731
1364
|
label: "Dark Mode"
|
|
732
1365
|
}
|
|
733
|
-
)), /* @__PURE__ */
|
|
1366
|
+
)), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.topRow }, /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.topRowPanel }, /* @__PURE__ */ React__default.default.createElement(GlobalPanel, { state, dispatch })), showPreview && /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.topRowPanel }, /* @__PURE__ */ React__default.default.createElement(PreviewPanel, { state, dispatch, themeConfig }))), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.designRow }, /* @__PURE__ */ React__default.default.createElement(DesignPanel, { state, dispatch })), /* @__PURE__ */ React__default.default.createElement(reactNative.View, { style: styles6.tabBar }, state.palettes.map((palette, index) => /* @__PURE__ */ React__default.default.createElement(
|
|
734
1367
|
reactNative.Pressable,
|
|
735
1368
|
{
|
|
736
1369
|
key: index,
|
|
737
1370
|
onPress: () => setActivePaletteIndex(index),
|
|
738
1371
|
style: [
|
|
739
|
-
|
|
1372
|
+
styles6.tab,
|
|
740
1373
|
{
|
|
741
1374
|
backgroundColor: index === activePaletteIndex ? newtone.srgbToHex(tokens.background.srgb) : "transparent",
|
|
742
1375
|
borderColor: index === activePaletteIndex ? newtone.srgbToHex(tokens.border.srgb) : "transparent"
|
|
743
1376
|
}
|
|
744
1377
|
]
|
|
745
1378
|
},
|
|
746
|
-
/* @__PURE__ */
|
|
747
|
-
|
|
1379
|
+
/* @__PURE__ */ React__default.default.createElement(reactNative.Text, { style: [
|
|
1380
|
+
styles6.tabText,
|
|
748
1381
|
{
|
|
749
1382
|
color: newtone.srgbToHex(
|
|
750
1383
|
index === activePaletteIndex ? tokens.textPrimary.srgb : tokens.textSecondary.srgb
|
|
@@ -752,15 +1385,16 @@ function Configurator({
|
|
|
752
1385
|
fontWeight: index === activePaletteIndex ? "700" : "500"
|
|
753
1386
|
}
|
|
754
1387
|
] }, palette.name)
|
|
755
|
-
))), /* @__PURE__ */
|
|
1388
|
+
))), /* @__PURE__ */ React__default.default.createElement(
|
|
756
1389
|
PalettePanel,
|
|
757
1390
|
{
|
|
758
1391
|
palette: state.palettes[activePaletteIndex],
|
|
759
1392
|
index: activePaletteIndex,
|
|
760
1393
|
dispatch,
|
|
761
|
-
previewColors: previews[activePaletteIndex]
|
|
1394
|
+
previewColors: previews[activePaletteIndex],
|
|
1395
|
+
state
|
|
762
1396
|
}
|
|
763
|
-
), showExport && /* @__PURE__ */
|
|
1397
|
+
), showExport && /* @__PURE__ */ React__default.default.createElement(ExportPanel, { state }), /* @__PURE__ */ React__default.default.createElement(
|
|
764
1398
|
"button",
|
|
765
1399
|
{
|
|
766
1400
|
onClick: () => reset(),
|
|
@@ -779,7 +1413,7 @@ function Configurator({
|
|
|
779
1413
|
"Reset to Defaults"
|
|
780
1414
|
));
|
|
781
1415
|
}
|
|
782
|
-
var
|
|
1416
|
+
var styles6 = reactNative.StyleSheet.create({
|
|
783
1417
|
container: {
|
|
784
1418
|
borderRadius: 8,
|
|
785
1419
|
padding: 16,
|
|
@@ -799,6 +1433,9 @@ var styles5 = reactNative.StyleSheet.create({
|
|
|
799
1433
|
topRowPanel: {
|
|
800
1434
|
flex: 1
|
|
801
1435
|
},
|
|
1436
|
+
designRow: {
|
|
1437
|
+
marginBottom: 4
|
|
1438
|
+
},
|
|
802
1439
|
tabBar: {
|
|
803
1440
|
flexDirection: "row",
|
|
804
1441
|
gap: 4,
|
|
@@ -817,11 +1454,15 @@ var styles5 = reactNative.StyleSheet.create({
|
|
|
817
1454
|
|
|
818
1455
|
exports.Configurator = Configurator;
|
|
819
1456
|
exports.DEFAULT_CONFIGURATOR_STATE = DEFAULT_CONFIGURATOR_STATE;
|
|
1457
|
+
exports.SEMANTIC_HUE_RANGES = SEMANTIC_HUE_RANGES;
|
|
1458
|
+
exports.hexToPaletteParams = hexToPaletteParams;
|
|
1459
|
+
exports.oklchHueToTraditional = oklchHueToTraditional;
|
|
820
1460
|
exports.toCSS = toCSS;
|
|
821
1461
|
exports.toJSON = toJSON;
|
|
822
1462
|
exports.toThemeConfig = toThemeConfig;
|
|
823
1463
|
exports.traditionalHueToOklch = traditionalHueToOklch;
|
|
824
1464
|
exports.useConfigurator = useConfigurator;
|
|
825
1465
|
exports.usePreviewColors = usePreviewColors;
|
|
1466
|
+
exports.useWcagValidation = useWcagValidation;
|
|
826
1467
|
//# sourceMappingURL=index.cjs.map
|
|
827
1468
|
//# sourceMappingURL=index.cjs.map
|