@charcoal-ui/styled 2.4.0 → 2.6.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.
Files changed (67) hide show
  1. package/dist/SetThemeScript.d.ts +20 -20
  2. package/dist/TokenInjector.d.ts +12 -12
  3. package/dist/TokenInjector.d.ts.map +1 -1
  4. package/dist/builders/border.d.ts +10 -0
  5. package/dist/builders/border.d.ts.map +1 -0
  6. package/dist/builders/borderRadius.d.ts +7 -0
  7. package/dist/builders/borderRadius.d.ts.map +1 -0
  8. package/dist/builders/colors.d.ts +13 -0
  9. package/dist/builders/colors.d.ts.map +1 -0
  10. package/dist/builders/elementEffect.d.ts +7 -0
  11. package/dist/builders/elementEffect.d.ts.map +1 -0
  12. package/dist/builders/o.d.ts +114 -0
  13. package/dist/builders/o.d.ts.map +1 -0
  14. package/dist/builders/outline.d.ts +10 -0
  15. package/dist/builders/outline.d.ts.map +1 -0
  16. package/dist/builders/size.d.ts +23 -0
  17. package/dist/builders/size.d.ts.map +1 -0
  18. package/dist/builders/spacing.d.ts +15 -0
  19. package/dist/builders/spacing.d.ts.map +1 -0
  20. package/dist/builders/transition.d.ts +7 -0
  21. package/dist/builders/transition.d.ts.map +1 -0
  22. package/dist/builders/typography.d.ts +11 -0
  23. package/dist/builders/typography.d.ts.map +1 -0
  24. package/dist/defineThemeVariables.test.d.ts +1 -1
  25. package/dist/{lib.d.ts → factories/lib.d.ts} +88 -89
  26. package/dist/factories/lib.d.ts.map +1 -0
  27. package/dist/helper.d.ts +38 -38
  28. package/dist/helper.d.ts.map +1 -1
  29. package/dist/index.cjs.js +918 -0
  30. package/dist/index.cjs.js.map +1 -0
  31. package/dist/index.d.ts +128 -67
  32. package/dist/index.d.ts.map +1 -1
  33. package/dist/index.esm.js +886 -0
  34. package/dist/index.esm.js.map +1 -0
  35. package/dist/index.story.d.ts +25 -24
  36. package/dist/index.story.d.ts.map +1 -1
  37. package/dist/index.test.d.ts +2 -0
  38. package/dist/index.test.d.ts.map +1 -0
  39. package/dist/internals/index.d.ts +42 -0
  40. package/dist/internals/index.d.ts.map +1 -0
  41. package/dist/util.d.ts +100 -66
  42. package/dist/util.d.ts.map +1 -1
  43. package/package.json +19 -16
  44. package/src/__snapshots__/index.test.tsx.snap +768 -0
  45. package/src/builders/border.ts +63 -0
  46. package/src/builders/borderRadius.ts +32 -0
  47. package/src/builders/colors.ts +198 -0
  48. package/src/builders/elementEffect.ts +54 -0
  49. package/src/builders/o.ts +36 -0
  50. package/src/builders/outline.ts +79 -0
  51. package/src/builders/size.ts +61 -0
  52. package/src/builders/spacing.ts +113 -0
  53. package/src/builders/transition.ts +32 -0
  54. package/src/builders/typography.ts +97 -0
  55. package/src/{lib.ts → factories/lib.ts} +30 -25
  56. package/src/index.story.tsx +2 -2
  57. package/src/index.test.tsx +24 -0
  58. package/src/index.ts +36 -696
  59. package/src/internals/index.ts +84 -0
  60. package/src/util.ts +46 -3
  61. package/dist/index.cjs +0 -1051
  62. package/dist/index.cjs.map +0 -1
  63. package/dist/index.modern.js +0 -826
  64. package/dist/index.modern.js.map +0 -1
  65. package/dist/index.module.js +0 -1034
  66. package/dist/index.module.js.map +0 -1
  67. package/dist/lib.d.ts.map +0 -1
@@ -0,0 +1,918 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
22
+ mod
23
+ ));
24
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
25
+
26
+ // src/index.ts
27
+ var src_exports = {};
28
+ __export(src_exports, {
29
+ SetThemeScript: () => SetThemeScript,
30
+ TokenInjector: () => TokenInjector,
31
+ createTheme: () => createTheme,
32
+ defineThemeVariables: () => defineThemeVariables,
33
+ getThemeSync: () => getThemeSync,
34
+ makeSetThemeScriptCode: () => makeSetThemeScriptCode,
35
+ prefersColorScheme: () => prefersColorScheme,
36
+ themeSelector: () => themeSelector,
37
+ themeSetter: () => themeSetter,
38
+ useLocalStorage: () => useLocalStorage,
39
+ useMedia: () => useMedia,
40
+ useTheme: () => useTheme,
41
+ useThemeSetter: () => useThemeSetter
42
+ });
43
+ module.exports = __toCommonJS(src_exports);
44
+
45
+ // src/util.ts
46
+ var import_utils = require("@charcoal-ui/utils");
47
+ function unreachable(value) {
48
+ throw new Error(
49
+ arguments.length === 0 ? "unreachable" : `unreachable (${JSON.stringify(value)})`
50
+ );
51
+ }
52
+ var isPresent = (value) => value != null;
53
+ function objectAssign(...sources) {
54
+ return Object.assign({}, ...sources);
55
+ }
56
+ function keyof(obj) {
57
+ return Object.keys(obj);
58
+ }
59
+ function wrapArray(value) {
60
+ return Array.isArray(value) ? value : [value];
61
+ }
62
+ var noThemeProvider = new Error(
63
+ "`theme` is invalid. `<ThemeProvider>` is not likely mounted."
64
+ );
65
+ function defineThemeVariables(colorParams, effectParams) {
66
+ return function toCssObject(props) {
67
+ if (!isPresent(props.theme)) {
68
+ throw noThemeProvider;
69
+ }
70
+ const colors2 = (0, import_utils.filterObject)(colorParams, isPresent);
71
+ const effects = Object.entries({
72
+ ...props.theme.effect,
73
+ ...effectParams
74
+ });
75
+ return (0, import_utils.flatMapObject)(colors2, (colorKey, color) => [
76
+ [(0, import_utils.customPropertyToken)(colorKey), color],
77
+ ...effects.map(([effectKey, effect]) => [
78
+ (0, import_utils.customPropertyToken)(colorKey, [effectKey]),
79
+ (0, import_utils.applyEffect)(color, [effect])
80
+ ])
81
+ ]);
82
+ };
83
+ }
84
+ function isSupportedEffect(effect) {
85
+ return ["hover", "press", "disabled"].includes(effect);
86
+ }
87
+ var variable = (value) => `var(${value})`;
88
+ function onEffectPseudo(effect, css2) {
89
+ return effect === "hover" ? { "&:hover": { [import_utils.notDisabledSelector]: css2 } } : effect === "press" ? { "&:active": { [import_utils.notDisabledSelector]: css2 } } : effect === "disabled" ? { [import_utils.disabledSelector]: css2 } : unreachable(effect);
90
+ }
91
+
92
+ // src/internals/index.ts
93
+ var internalSym = Symbol("internal");
94
+ function createInternal({
95
+ toCSS,
96
+ context = {}
97
+ }) {
98
+ return {
99
+ [internalSym]: {
100
+ toCSS,
101
+ context
102
+ }
103
+ };
104
+ }
105
+ function __DO_NOT_USE_ACCESS_PRIVATE_PROPERTY__(internal) {
106
+ return internal[internalSym];
107
+ }
108
+ var shouldCancelHalfLeading = ({
109
+ cancelHalfLeadingPx,
110
+ hasVerticalPadding = false
111
+ }) => cancelHalfLeadingPx !== void 0 && !hasVerticalPadding;
112
+ function getContext(internals) {
113
+ return internals.reduce(
114
+ (context, internal) => ({
115
+ ...context,
116
+ ...__DO_NOT_USE_ACCESS_PRIVATE_PROPERTY__(internal).context
117
+ }),
118
+ {}
119
+ );
120
+ }
121
+ function toCSSObjects(internals) {
122
+ const context = getContext(internals);
123
+ return internals.map(
124
+ (v) => __DO_NOT_USE_ACCESS_PRIVATE_PROPERTY__(v).toCSS(context)
125
+ );
126
+ }
127
+
128
+ // src/factories/lib.ts
129
+ var defineProperties = (source, member, chain) => Object.defineProperties(
130
+ source,
131
+ Object.fromEntries(
132
+ member.map((key) => [
133
+ key,
134
+ { get: () => chain(key), enumerable: true, configurable: true }
135
+ ])
136
+ )
137
+ );
138
+ var defineMethods = (source, member, chain) => Object.defineProperties(
139
+ source,
140
+ Object.fromEntries(
141
+ member.map((key) => [
142
+ key,
143
+ {
144
+ value: (...args) => chain(key, ...args),
145
+ enumerable: true,
146
+ configurable: true
147
+ }
148
+ ])
149
+ )
150
+ );
151
+ var defineConstantProperties = (source, def) => defineProperties(source, Object.keys(def), (key) => def[key]);
152
+ var definePropertyChains = (modifiers, source) => function definePropertiesRecursively(applied) {
153
+ const notApplied = modifiers.filter((v) => !applied.includes(v));
154
+ return defineProperties(
155
+ source(applied),
156
+ notApplied,
157
+ (modifier) => notApplied.length === 0 ? unreachable() : definePropertiesRecursively([...applied, modifier])
158
+ );
159
+ }([]);
160
+ var defineMethodChains = (modifiers, source, ..._inferPhantom) => function defineMethodsRecursively(applied) {
161
+ const notApplied = modifiers.filter(
162
+ (v) => !applied.map(([w]) => w).includes(v)
163
+ );
164
+ return defineMethods(
165
+ source(applied),
166
+ notApplied,
167
+ (modifier, ...args) => notApplied.length === 0 ? unreachable() : defineMethodsRecursively([...applied, [modifier, ...args]])
168
+ );
169
+ }([]);
170
+
171
+ // src/builders/border.ts
172
+ var borderDirections = ["top", "right", "bottom", "left"];
173
+ function borderProperty(direction) {
174
+ return `border-${direction}`;
175
+ }
176
+ function borderShorthand(color) {
177
+ return `solid 1px ${color}`;
178
+ }
179
+ var createBorderCss = (theme) => (variant, directions) => {
180
+ const all = directions.length === 0;
181
+ const value = borderShorthand(theme.border[variant].color);
182
+ return createInternal({
183
+ toCSS() {
184
+ return {
185
+ ...all ? { border: value } : directions.reduce(
186
+ (acc, direction) => ({
187
+ ...acc,
188
+ [borderProperty(direction)]: value
189
+ }),
190
+ {}
191
+ )
192
+ };
193
+ }
194
+ });
195
+ };
196
+ function border(theme) {
197
+ const borderTypes = keyof(theme.border);
198
+ const borderCss = createBorderCss(theme);
199
+ const borderObject = defineConstantProperties(
200
+ {},
201
+ {
202
+ border: defineProperties(
203
+ {},
204
+ borderTypes,
205
+ (variant) => definePropertyChains(
206
+ borderDirections,
207
+ (modifiers) => borderCss(variant, modifiers)
208
+ )
209
+ )
210
+ }
211
+ );
212
+ return borderObject;
213
+ }
214
+
215
+ // src/builders/borderRadius.ts
216
+ var import_utils2 = require("@charcoal-ui/utils");
217
+ var createBorderRadiusCss = (theme) => (size2) => {
218
+ return createInternal({
219
+ toCSS() {
220
+ return {
221
+ borderRadius: (0, import_utils2.px)(theme.borderRadius[size2])
222
+ };
223
+ }
224
+ });
225
+ };
226
+ function borderRadius(theme) {
227
+ const borderRadiusCss = createBorderRadiusCss(theme);
228
+ const borderRadiusObject = defineConstantProperties(
229
+ {},
230
+ {
231
+ borderRadius: (radius) => borderRadiusCss(radius)
232
+ }
233
+ );
234
+ return borderRadiusObject;
235
+ }
236
+
237
+ // src/builders/colors.ts
238
+ var import_utils4 = require("@charcoal-ui/utils");
239
+ var import_warning = __toESM(require("warning"));
240
+
241
+ // src/builders/transition.ts
242
+ var import_utils3 = require("@charcoal-ui/utils");
243
+ var TRANSITION_DURATION = 0.2;
244
+ function transition(_theme) {
245
+ const duration = (0, import_utils3.dur)(TRANSITION_DURATION);
246
+ const transition2 = (property) => ({
247
+ transition: property.map((v) => `${duration} ${v}`).join(", ")
248
+ });
249
+ function toCSS({
250
+ colorTransition = false,
251
+ backgroundColorTransition = false,
252
+ boxShadowTransition = false
253
+ }) {
254
+ return transition2(
255
+ [
256
+ colorTransition ? "color" : null,
257
+ backgroundColorTransition ? "background-color" : null,
258
+ boxShadowTransition ? "box-shadow" : null
259
+ ].filter(isPresent)
260
+ );
261
+ }
262
+ return createInternal({ toCSS });
263
+ }
264
+
265
+ // src/builders/colors.ts
266
+ function targetProperty(target) {
267
+ return target === "bg" ? "background-color" : "color";
268
+ }
269
+ var createColorCss = (_theme) => (target, color, effects = []) => {
270
+ function toCSS() {
271
+ return {
272
+ [targetProperty(target)]: variable(
273
+ (0, import_utils4.customPropertyToken)(color.toString())
274
+ ),
275
+ ...effects.filter(isSupportedEffect).reduce(
276
+ (acc, effect) => ({
277
+ ...acc,
278
+ ...onEffectPseudo(effect, {
279
+ [targetProperty(target)]: variable(
280
+ (0, import_utils4.customPropertyToken)(color.toString(), [effect])
281
+ )
282
+ })
283
+ }),
284
+ {}
285
+ )
286
+ };
287
+ }
288
+ return createInternal({
289
+ toCSS,
290
+ context: effects.length > 0 ? target === "font" ? {
291
+ colorTransition: true
292
+ } : {
293
+ backgroundColorTransition: true
294
+ } : {}
295
+ });
296
+ };
297
+ var createGradientColorCss = (theme) => (color, effects = [], direction) => {
298
+ const toLinearGradient = (0, import_utils4.gradient)(direction);
299
+ function toCSS(context) {
300
+ const optimized = !shouldCancelHalfLeading(context);
301
+ const duration = (0, import_utils4.dur)(TRANSITION_DURATION);
302
+ if (optimized && effects.length > 0) {
303
+ return {
304
+ position: "relative",
305
+ zIndex: 0,
306
+ overflow: "hidden",
307
+ ...effects.filter(isSupportedEffect).reduce(
308
+ (acc, effect) => ({
309
+ ...acc,
310
+ "&::before": {
311
+ zIndex: -1,
312
+ ...overlayElement,
313
+ transition: `${duration} background-color`
314
+ },
315
+ "&::after": {
316
+ zIndex: -2,
317
+ ...overlayElement,
318
+ ...toLinearGradient(theme.gradientColor[color])
319
+ },
320
+ ...onEffectPseudo(effect, {
321
+ "&::before": {
322
+ backgroundColor: (0, import_utils4.applyEffect)(
323
+ null,
324
+ theme.effect[effect] ?? []
325
+ )
326
+ }
327
+ })
328
+ }),
329
+ {}
330
+ )
331
+ };
332
+ }
333
+ (0, import_warning.default)(
334
+ effects.length === 0,
335
+ `'Transition' will not be applied. You can get around this by specifying 'preserveHalfLeading' or both 'padding' and 'typograpy'.`
336
+ );
337
+ return {
338
+ ...toLinearGradient(theme.gradientColor[color]),
339
+ ...effects.filter(isSupportedEffect).reduce(
340
+ (acc, effect) => ({
341
+ ...acc,
342
+ ...onEffectPseudo(effect, {
343
+ ...toLinearGradient(
344
+ (0, import_utils4.applyEffectToGradient)(theme.effect[effect] ?? [])(
345
+ theme.gradientColor[color]
346
+ )
347
+ )
348
+ })
349
+ }),
350
+ {}
351
+ )
352
+ };
353
+ }
354
+ return createInternal({ toCSS });
355
+ };
356
+ var overlayElement = {
357
+ content: "''",
358
+ display: "block",
359
+ position: "absolute",
360
+ width: "100%",
361
+ height: "100%",
362
+ top: 0,
363
+ left: 0
364
+ };
365
+ function colors(theme) {
366
+ const colors2 = keyof(theme.color);
367
+ const effects = keyof(theme.effect);
368
+ const gradientColors = keyof(theme.gradientColor);
369
+ const colorCss = createColorCss(theme);
370
+ const gradientColorCss = createGradientColorCss(theme);
371
+ const colorObject = defineConstantProperties(
372
+ {},
373
+ {
374
+ bg: objectAssign(
375
+ defineProperties(
376
+ {},
377
+ colors2,
378
+ (color) => definePropertyChains(
379
+ effects,
380
+ (modifiers) => colorCss("bg", color, modifiers)
381
+ )
382
+ ),
383
+ defineProperties(
384
+ {},
385
+ gradientColors,
386
+ (color) => (direction) => definePropertyChains(
387
+ effects,
388
+ (modifiers) => gradientColorCss(color, modifiers, direction)
389
+ )
390
+ )
391
+ ),
392
+ font: defineProperties(
393
+ {},
394
+ colors2,
395
+ (color) => definePropertyChains(
396
+ effects,
397
+ (modifiers) => colorCss("font", color, modifiers)
398
+ )
399
+ )
400
+ }
401
+ );
402
+ return colorObject;
403
+ }
404
+
405
+ // src/builders/elementEffect.ts
406
+ var createElementEffectCss = (theme) => (effects = []) => createInternal({
407
+ toCSS() {
408
+ return effects.filter(isSupportedEffect).reduce(
409
+ (acc, effect) => ({
410
+ ...acc,
411
+ ...onEffectPseudo(effect, {
412
+ opacity: !Array.isArray(
413
+ theme.elementEffect[effect]
414
+ ) && theme.elementEffect[effect]?.type === "opacity" ? theme.elementEffect[effect]?.opacity : unreachable()
415
+ })
416
+ }),
417
+ {}
418
+ );
419
+ }
420
+ });
421
+ function elementEffect(theme) {
422
+ const effectTypes = keyof(
423
+ theme.elementEffect
424
+ );
425
+ const elementEffectCss = createElementEffectCss(theme);
426
+ const elementEffectObject = definePropertyChains(
427
+ effectTypes,
428
+ (modifiers) => elementEffectCss(modifiers)
429
+ );
430
+ return elementEffectObject;
431
+ }
432
+
433
+ // src/builders/outline.ts
434
+ var import_utils5 = require("@charcoal-ui/utils");
435
+ var outlineType = ["focus"];
436
+ var outlineCss = (weight, color) => ({
437
+ boxShadow: `0 0 0 ${(0, import_utils5.px)(weight)} ${color}`
438
+ });
439
+ var createOutlineColorCss = (theme) => (variant, modifiers) => {
440
+ const weight = theme.outline[variant].weight;
441
+ const color = theme.outline[variant].color;
442
+ return createInternal({
443
+ toCSS() {
444
+ return modifiers.includes("focus") ? onFocus(outlineCss(weight, color)) : { "&&": { [import_utils5.notDisabledSelector]: outlineCss(weight, color) } };
445
+ },
446
+ context: {
447
+ boxShadowTransition: true
448
+ }
449
+ });
450
+ };
451
+ var onFocus = (css2) => ({
452
+ [import_utils5.notDisabledSelector]: {
453
+ "&:focus, &:active": {
454
+ outline: "none",
455
+ ...css2
456
+ },
457
+ "&:focus:not(:focus-visible), &:active:not(:focus-visible)": {
458
+ outline: "none"
459
+ },
460
+ "&:focus-visible": {
461
+ outline: "none",
462
+ ...css2
463
+ }
464
+ }
465
+ });
466
+ function outline(theme) {
467
+ const outlineCss2 = createOutlineColorCss(theme);
468
+ const outlineObject = defineConstantProperties(
469
+ {},
470
+ {
471
+ outline: defineProperties(
472
+ {},
473
+ keyof(theme.outline),
474
+ (variant) => definePropertyChains(
475
+ outlineType,
476
+ (modifiers) => outlineCss2(variant, modifiers)
477
+ )
478
+ )
479
+ }
480
+ );
481
+ return outlineObject;
482
+ }
483
+
484
+ // src/builders/size.ts
485
+ var import_foundation = require("@charcoal-ui/foundation");
486
+ var import_utils6 = require("@charcoal-ui/utils");
487
+ var fixedProperties = ["width", "height"];
488
+ var createFixedPxCss = (theme) => (property, size2) => createInternal({
489
+ toCSS() {
490
+ return {
491
+ [property]: size2 === "auto" ? "auto" : (0, import_utils6.px)(theme.spacing[size2])
492
+ };
493
+ }
494
+ });
495
+ var createFixedRelativeCss = (_theme) => (property, amount) => createInternal({
496
+ toCSS() {
497
+ return {
498
+ [property]: amount
499
+ };
500
+ }
501
+ });
502
+ var createFixedColumnCss = (theme) => (property, span) => createInternal({
503
+ toCSS() {
504
+ return {
505
+ [property]: (0, import_utils6.px)(
506
+ (0, import_foundation.columnSystem)(span, theme.grid.unit.column, theme.grid.unit.gutter)
507
+ )
508
+ };
509
+ }
510
+ });
511
+ function size(theme) {
512
+ const fixedPxCss = createFixedPxCss(theme);
513
+ const fixedColumnCss = createFixedColumnCss(theme);
514
+ const fixedRelativeCss = createFixedRelativeCss(theme);
515
+ const fixedObject = defineProperties(
516
+ {},
517
+ fixedProperties,
518
+ (property) => defineConstantProperties(
519
+ {},
520
+ {
521
+ px: (size2) => fixedPxCss(property, size2),
522
+ column: (span) => fixedColumnCss(property, span),
523
+ auto: fixedRelativeCss(property, "auto"),
524
+ full: fixedRelativeCss(property, "100%")
525
+ }
526
+ )
527
+ );
528
+ return fixedObject;
529
+ }
530
+
531
+ // src/builders/spacing.ts
532
+ var import_utils7 = require("@charcoal-ui/utils");
533
+ var spacingProperties = ["margin", "padding"];
534
+ var spacingDirections = [
535
+ "top",
536
+ "right",
537
+ "bottom",
538
+ "left",
539
+ "vertical",
540
+ "horizontal",
541
+ "all"
542
+ ];
543
+ function spacingProperty(property, direction) {
544
+ return `${property}-${direction}`;
545
+ }
546
+ var createSpacingCss = (theme) => (property, modifiers) => {
547
+ const { top, right, bottom, left } = modifiers.reduce(
548
+ (acc, [direction, size2]) => {
549
+ if (direction === "all") {
550
+ acc.top = size2;
551
+ acc.right = size2;
552
+ acc.bottom = size2;
553
+ acc.left = size2;
554
+ } else if (direction === "vertical") {
555
+ acc.top = size2;
556
+ acc.bottom = size2;
557
+ } else if (direction === "horizontal") {
558
+ acc.right = size2;
559
+ acc.left = size2;
560
+ } else {
561
+ acc[direction] = size2;
562
+ }
563
+ return acc;
564
+ },
565
+ {}
566
+ );
567
+ const hasVerticalPadding = property === "padding" && top !== void 0 && bottom !== void 0 && top !== "auto" && bottom !== "auto";
568
+ function toCSS({ cancelHalfLeadingPx = 0 }) {
569
+ return {
570
+ ...top !== void 0 && {
571
+ [spacingProperty(property, "top")]: top === "auto" ? "auto" : (0, import_utils7.px)(
572
+ theme.spacing[top] + (hasVerticalPadding ? cancelHalfLeadingPx : 0)
573
+ )
574
+ },
575
+ ...bottom !== void 0 && {
576
+ [spacingProperty(property, "bottom")]: bottom === "auto" ? "auto" : (0, import_utils7.px)(
577
+ theme.spacing[bottom] + (hasVerticalPadding ? cancelHalfLeadingPx : 0)
578
+ )
579
+ },
580
+ ...right !== void 0 && {
581
+ [spacingProperty(property, "right")]: right === "auto" ? "auto" : (0, import_utils7.px)(theme.spacing[right])
582
+ },
583
+ ...left !== void 0 && {
584
+ [spacingProperty(property, "left")]: left === "auto" ? "auto" : (0, import_utils7.px)(theme.spacing[left])
585
+ }
586
+ };
587
+ }
588
+ return createInternal({
589
+ toCSS,
590
+ context: hasVerticalPadding ? { hasVerticalPadding: true } : {}
591
+ });
592
+ };
593
+ function spacing(theme) {
594
+ const spacingCss = createSpacingCss(theme);
595
+ const spacingObject = defineProperties(
596
+ {},
597
+ spacingProperties,
598
+ (spacingProperty2) => defineMethodChains(
599
+ spacingDirections,
600
+ (modifiers) => spacingCss(spacingProperty2, modifiers),
601
+ {}
602
+ )
603
+ );
604
+ return spacingObject;
605
+ }
606
+
607
+ // src/builders/typography.ts
608
+ var import_utils8 = require("@charcoal-ui/utils");
609
+ var createTypographyCss = (theme) => (size2, options = {}) => {
610
+ const {
611
+ preserveHalfLeading = false,
612
+ monospace = false,
613
+ bold = false
614
+ } = options;
615
+ const descriptor = theme.typography.size[size2];
616
+ const margin = -(0, import_utils8.halfLeading)(descriptor);
617
+ function toCSS(context) {
618
+ return {
619
+ fontSize: (0, import_utils8.px)(descriptor.fontSize),
620
+ lineHeight: (0, import_utils8.px)(descriptor.lineHeight),
621
+ ...monospace && {
622
+ fontFamily: "monospace"
623
+ },
624
+ ...bold && {
625
+ fontWeight: "bold"
626
+ },
627
+ ...shouldCancelHalfLeading(context) && {
628
+ display: "flow-root",
629
+ "&::before": {
630
+ ...leadingCancel,
631
+ marginTop: (0, import_utils8.px)(margin)
632
+ },
633
+ "&::after": {
634
+ ...leadingCancel,
635
+ marginBottom: (0, import_utils8.px)(margin)
636
+ }
637
+ }
638
+ };
639
+ }
640
+ return createInternal({
641
+ toCSS,
642
+ context: !preserveHalfLeading ? {
643
+ cancelHalfLeadingPx: margin
644
+ } : {}
645
+ });
646
+ };
647
+ var leadingCancel = {
648
+ display: "block",
649
+ width: 0,
650
+ height: 0,
651
+ content: `''`
652
+ };
653
+ var typographyModifiers = [
654
+ "monospace",
655
+ "bold",
656
+ "preserveHalfLeading"
657
+ ];
658
+ function typography(theme) {
659
+ const typographyCss = createTypographyCss(theme);
660
+ const typographyObject = defineProperties(
661
+ {},
662
+ ["typography"],
663
+ (_) => (size2) => definePropertyChains(
664
+ typographyModifiers,
665
+ (modifiers) => typographyCss(size2, {
666
+ preserveHalfLeading: modifiers.includes("preserveHalfLeading"),
667
+ monospace: modifiers.includes("monospace"),
668
+ bold: modifiers.includes("bold")
669
+ })
670
+ )
671
+ );
672
+ return typographyObject;
673
+ }
674
+
675
+ // src/builders/o.ts
676
+ function createO(theme) {
677
+ return objectAssign(
678
+ colors(theme),
679
+ typography(theme),
680
+ spacing(theme),
681
+ size(theme),
682
+ elementEffect(theme),
683
+ border(theme),
684
+ borderRadius(theme),
685
+ outline(theme)
686
+ );
687
+ }
688
+
689
+ // src/TokenInjector.tsx
690
+ var import_react = __toESM(require("react"));
691
+ var import_styled_components = require("styled-components");
692
+ var GlobalStyle = import_styled_components.createGlobalStyle`
693
+ ${({
694
+ themeMap,
695
+ background
696
+ }) => Object.entries(themeMap).map(
697
+ ([key, theme]) => key.startsWith("@media") ? import_styled_components.css`
698
+ ${key} {
699
+ :root {
700
+ ${background !== void 0 && import_styled_components.css`
701
+ background-color: ${theme.color[background]};
702
+ `}
703
+ ${defineColorVariableCSS(theme)}
704
+ }
705
+ }
706
+ ` : import_styled_components.css`
707
+ /* stylelint-disable-next-line no-duplicate-selectors */
708
+ ${key} {
709
+ ${background !== void 0 && import_styled_components.css`
710
+ background-color: ${theme.color[background]};
711
+ `}
712
+ ${defineColorVariableCSS(theme)}
713
+ }
714
+ `
715
+ )}
716
+ `;
717
+ function TokenInjector({
718
+ theme: themeMap,
719
+ background
720
+ }) {
721
+ return /* @__PURE__ */ import_react.default.createElement(GlobalStyle, { themeMap, background });
722
+ }
723
+ var defineColorVariableCSS = (theme) => Object.entries(defineThemeVariables(theme.color)({ theme })).map(([varName, value]) => variableDefinition(varName, value.toString())).join(";");
724
+ var variableDefinition = (prop, value) => `${prop}: ${value}`;
725
+
726
+ // src/helper.ts
727
+ var import_react2 = require("react");
728
+ var LOCAL_STORAGE_KEY = "charcoal-theme";
729
+ var DEFAULT_ROOT_ATTRIBUTE = "theme";
730
+ var keyStringRegExp = new RegExp(/^(\w|-)+$/);
731
+ function assertKeyString(key) {
732
+ if (!keyStringRegExp.test(key)) {
733
+ throw new Error(`Unexpected key :${key}, expect: /^(\\w|-)+$/`);
734
+ }
735
+ }
736
+ var themeSetter = (attr = DEFAULT_ROOT_ATTRIBUTE) => (theme) => {
737
+ assertKeyString(attr);
738
+ if (theme !== void 0) {
739
+ document.documentElement.dataset[attr] = theme;
740
+ } else {
741
+ delete document.documentElement.dataset[attr];
742
+ }
743
+ };
744
+ function themeSelector(theme, attr) {
745
+ return `:root[data-${attr ?? DEFAULT_ROOT_ATTRIBUTE}='${theme}']`;
746
+ }
747
+ function prefersColorScheme(theme) {
748
+ return `@media (prefers-color-scheme: ${theme})`;
749
+ }
750
+ function useThemeSetter({
751
+ key = LOCAL_STORAGE_KEY,
752
+ setter = themeSetter()
753
+ } = {}) {
754
+ const [theme, , system] = useTheme(key);
755
+ (0, import_react2.useEffect)(() => {
756
+ if (theme === void 0) {
757
+ return;
758
+ }
759
+ setter(system ? void 0 : theme);
760
+ }, [setter, system, theme]);
761
+ }
762
+ function getThemeSync(key = LOCAL_STORAGE_KEY) {
763
+ const theme = localStorage.getItem(key);
764
+ return theme;
765
+ }
766
+ var useTheme = (key = LOCAL_STORAGE_KEY) => {
767
+ assertKeyString(key);
768
+ const isDark = useMedia("(prefers-color-scheme: dark)");
769
+ const media = isDark !== void 0 ? isDark ? "dark" : "light" : void 0;
770
+ const [local, setTheme, ready] = useLocalStorage(key);
771
+ const theme = !ready || media === void 0 ? void 0 : local ?? media;
772
+ const system = local === void 0;
773
+ return [theme, setTheme, system];
774
+ };
775
+ function useLocalStorage(key, defaultValue) {
776
+ const [ready, setReady] = (0, import_react2.useState)(false);
777
+ const [state, setState] = (0, import_react2.useState)();
778
+ const defaultValueMemo = (0, import_react2.useMemo)(() => defaultValue?.(), [defaultValue]);
779
+ (0, import_react2.useEffect)(() => {
780
+ fetch();
781
+ window.addEventListener("storage", handleStorage);
782
+ return () => {
783
+ window.removeEventListener("storage", handleStorage);
784
+ };
785
+ });
786
+ const handleStorage = (e) => {
787
+ if (e.storageArea !== localStorage) {
788
+ return;
789
+ }
790
+ if (e.key !== key) {
791
+ return;
792
+ }
793
+ fetch();
794
+ };
795
+ const fetch = () => {
796
+ const raw = localStorage.getItem(key);
797
+ setState((raw !== null ? deserialize(raw) : null) ?? defaultValueMemo);
798
+ setReady(true);
799
+ };
800
+ const set = (value) => {
801
+ if (value === void 0) {
802
+ localStorage.removeItem(key);
803
+ } else {
804
+ const raw = serialize(value);
805
+ localStorage.setItem(key, raw);
806
+ }
807
+ const event = new StorageEvent("storage", {
808
+ bubbles: true,
809
+ cancelable: false,
810
+ key,
811
+ url: location.href,
812
+ storageArea: localStorage
813
+ });
814
+ dispatchEvent(event);
815
+ };
816
+ return [state ?? defaultValueMemo, set, ready];
817
+ }
818
+ function deserialize(raw) {
819
+ try {
820
+ return JSON.parse(raw);
821
+ } catch {
822
+ return raw;
823
+ }
824
+ }
825
+ function serialize(value) {
826
+ if (typeof value === "string") {
827
+ return value;
828
+ } else {
829
+ return JSON.stringify(value);
830
+ }
831
+ }
832
+ function useMedia(query) {
833
+ const [match, setState] = (0, import_react2.useState)();
834
+ (0, import_react2.useEffect)(() => {
835
+ const matcher = window.matchMedia(query);
836
+ const onChange = () => {
837
+ setState(matcher.matches);
838
+ };
839
+ matcher.addEventListener("change", onChange);
840
+ setState(matcher.matches);
841
+ return () => {
842
+ matcher.removeEventListener("change", onChange);
843
+ };
844
+ }, [query]);
845
+ return match;
846
+ }
847
+
848
+ // src/SetThemeScript.tsx
849
+ var import_react3 = __toESM(require("react"));
850
+ function makeSetThemeScriptCode({
851
+ localStorageKey = defaultProps.localStorageKey,
852
+ rootAttribute = defaultProps.rootAttribute
853
+ } = defaultProps) {
854
+ assertKeyString(localStorageKey);
855
+ assertKeyString(rootAttribute);
856
+ return `'use strict';
857
+ (function () {
858
+ var localStorageKey = '${localStorageKey}'
859
+ var rootAttribute = '${rootAttribute}'
860
+ var currentTheme = localStorage.getItem(localStorageKey);
861
+ if (currentTheme) {
862
+ document.documentElement.dataset[rootAttribute] = currentTheme;
863
+ }
864
+ })();
865
+ `;
866
+ }
867
+ function SetThemeScript(props) {
868
+ const src = makeSetThemeScriptCode(props);
869
+ return /* @__PURE__ */ import_react3.default.createElement(
870
+ "script",
871
+ {
872
+ dangerouslySetInnerHTML: {
873
+ __html: src
874
+ }
875
+ }
876
+ );
877
+ }
878
+ var defaultProps = {
879
+ localStorageKey: LOCAL_STORAGE_KEY,
880
+ rootAttribute: DEFAULT_ROOT_ATTRIBUTE
881
+ };
882
+ SetThemeScript.defaultProps = defaultProps;
883
+
884
+ // src/index.ts
885
+ var nonBlank = (value) => isPresent(value) && value !== false;
886
+ function createTheme(_styled) {
887
+ return function theme(specFn) {
888
+ return function interpolate({ theme: theme2 }) {
889
+ if (!isPresent(theme2)) {
890
+ throw noThemeProvider;
891
+ }
892
+ const internals = [
893
+ ...wrapArray(
894
+ specFn(createO(theme2))
895
+ ),
896
+ transition(theme2)
897
+ ].filter(nonBlank);
898
+ return toCSSObjects(internals);
899
+ };
900
+ };
901
+ }
902
+ // Annotate the CommonJS export names for ESM import in node:
903
+ 0 && (module.exports = {
904
+ SetThemeScript,
905
+ TokenInjector,
906
+ createTheme,
907
+ defineThemeVariables,
908
+ getThemeSync,
909
+ makeSetThemeScriptCode,
910
+ prefersColorScheme,
911
+ themeSelector,
912
+ themeSetter,
913
+ useLocalStorage,
914
+ useMedia,
915
+ useTheme,
916
+ useThemeSetter
917
+ });
918
+ //# sourceMappingURL=index.cjs.js.map