@pie-players/pie-theme 0.3.65 → 0.3.67

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.
@@ -0,0 +1,1081 @@
1
+ import { PIE_THEME_SCHEME_PARTICIPATION } from "./scheme-participation.js";
2
+ function deepFreeze(value) {
3
+ if (value && typeof value === "object" && !Object.isFrozen(value)) {
4
+ for (const child of Object.values(value)) {
5
+ deepFreeze(child);
6
+ }
7
+ Object.freeze(value);
8
+ }
9
+ return value;
10
+ }
11
+ const LIGHT_BASE_THEME = {
12
+ "--pie-text": "black",
13
+ "--pie-disabled": "grey",
14
+ "--pie-disabled-secondary": "#ababab",
15
+ "--pie-correct": "#208537",
16
+ "--pie-correct-secondary": "#e8f5e9",
17
+ "--pie-correct-tertiary": "#087d38",
18
+ "--pie-correct-icon": "#087d38",
19
+ "--pie-incorrect": "#a65f00",
20
+ "--pie-content-emphasis": "#b00000",
21
+ "--pie-incorrect-secondary": "#ffebee",
22
+ "--pie-incorrect-icon": "#bf0d00",
23
+ "--pie-missing": "#d32f2f",
24
+ "--pie-missing-icon": "#6a78a1",
25
+ "--pie-primary": "#3f51b5",
26
+ "--pie-primary-light": "#9fa8da",
27
+ "--pie-primary-dark": "#283593",
28
+ "--pie-faded-primary": "#dcdafb",
29
+ "--pie-secondary": "#f50057",
30
+ "--pie-secondary-light": "#f48fb1",
31
+ "--pie-secondary-dark": "#880e4f",
32
+ "--pie-tertiary": "#146eb3",
33
+ "--pie-tertiary-light": "#d0e2f0",
34
+ "--pie-background": "rgba(255, 255, 255, 0)",
35
+ "--pie-background-dark": "#ecedf1",
36
+ "--pie-secondary-background": "rgba(241, 241, 241, 1)",
37
+ "--pie-dropdown-background": "#e0e1e6",
38
+ "--pie-border": "#8f8f8f",
39
+ "--pie-border-light": "#d1d1d1",
40
+ "--pie-border-dark": "#646464",
41
+ "--pie-border-gray": "#7e8494",
42
+ "--pie-black": "#000000",
43
+ "--pie-white": "#ffffff",
44
+ "--pie-focus-checked": "#bbdefb",
45
+ "--pie-focus-checked-border": "#1565c0",
46
+ "--pie-focus-unchecked": "#e0e0e0",
47
+ "--pie-focus-unchecked-border": "#757575",
48
+ "--pie-blue-grey-100": "#f3f5f7",
49
+ "--pie-blue-grey-300": "#c0c3cf",
50
+ "--pie-blue-grey-600": "#7e8494",
51
+ "--pie-blue-grey-900": "#152452",
52
+ "--pie-font-scale": "1",
53
+ "--pie-button-bg": "#ffffff",
54
+ "--pie-button-border": "#8f8f8f",
55
+ "--pie-button-color": "#374151",
56
+ "--pie-button-hover-bg": "#f9fafb",
57
+ "--pie-button-hover-border": "#8b919c",
58
+ "--pie-button-hover-color": "#111827",
59
+ "--pie-button-active-bg": "#f3f4f6",
60
+ "--pie-button-focus-outline": "#3b82f6",
61
+ // Share by which a component's own fixed hues collapse into the palette. A
62
+ // Base Theme keeps them, because it is a full palette and a hue encoding
63
+ // still reads against it; every scheme below sets 100%, because a
64
+ // two-colour palette is a promise the whole surface has to keep.
65
+ "--pie-fixed-hue-collapse": "0%",
66
+ };
67
+ // The three component-public accessibility tokens participate in built-in
68
+ // schemes, but are not canonical semantic defaults in the published registry.
69
+ const LIGHT_BASE_ACCESSIBILITY_VARS = {
70
+ "--pie-annotation-underline": "#4221d5",
71
+ "--pie-annotation-underline-dark": "#9c89ec",
72
+ "--pie-tool-annotation-toolbar-border": "#5c5c5c",
73
+ };
74
+ const DARK_BASE_THEME = {
75
+ "--pie-text": "#ffffff",
76
+ "--pie-disabled": "#999999",
77
+ "--pie-disabled-secondary": "#777777",
78
+ "--pie-correct": "#00ff00",
79
+ "--pie-correct-secondary": "#003300",
80
+ "--pie-correct-tertiary": "#00cc00",
81
+ "--pie-correct-icon": "#00ff00",
82
+ "--pie-incorrect": "#ff3333",
83
+ "--pie-content-emphasis": "#ff6666",
84
+ "--pie-incorrect-secondary": "#330000",
85
+ "--pie-incorrect-icon": "#ff0000",
86
+ "--pie-missing": "#ff6666",
87
+ "--pie-missing-icon": "#6666ff",
88
+ "--pie-primary": "#ffff00",
89
+ "--pie-primary-light": "#ffff99",
90
+ "--pie-primary-dark": "#cccc00",
91
+ "--pie-faded-primary": "#666600",
92
+ "--pie-secondary": "#ff00ff",
93
+ "--pie-secondary-light": "#ff99ff",
94
+ "--pie-secondary-dark": "#cc00cc",
95
+ "--pie-tertiary": "#00ffff",
96
+ "--pie-tertiary-light": "#99ffff",
97
+ "--pie-background": "#000000",
98
+ "--pie-background-dark": "#1a1a1a",
99
+ "--pie-secondary-background": "#222222",
100
+ "--pie-dropdown-background": "#2a2a2a",
101
+ "--pie-border": "#ffffff",
102
+ "--pie-border-light": "#cccccc",
103
+ "--pie-border-dark": "#ffffff",
104
+ "--pie-border-gray": "#aaaaaa",
105
+ "--pie-black": "#ffffff",
106
+ "--pie-white": "#000000",
107
+ "--pie-focus-checked": "#ffff00",
108
+ "--pie-focus-checked-border": "#ffff00",
109
+ "--pie-focus-unchecked": "#666666",
110
+ "--pie-focus-unchecked-border": "#ffffff",
111
+ "--pie-blue-grey-100": "#2a2a2a",
112
+ "--pie-blue-grey-300": "#555555",
113
+ "--pie-blue-grey-600": "#999999",
114
+ "--pie-blue-grey-900": "#ffffff",
115
+ "--pie-font-scale": "1",
116
+ "--pie-button-bg": "#1f2937",
117
+ "--pie-button-border": "#535e6d",
118
+ "--pie-button-color": "#f9fafb",
119
+ "--pie-button-hover-bg": "#374151",
120
+ "--pie-button-hover-border": "#6b7280",
121
+ "--pie-button-hover-color": "#ffffff",
122
+ "--pie-button-active-bg": "#4b5563",
123
+ "--pie-button-focus-outline": "#93c5fd",
124
+ "--pie-fixed-hue-collapse": "0%",
125
+ };
126
+ const DARK_BASE_ACCESSIBILITY_VARS = {
127
+ "--pie-annotation-underline": "#9c89ec",
128
+ "--pie-annotation-underline-dark": "#9c89ec",
129
+ "--pie-tool-annotation-toolbar-border": "#949494",
130
+ };
131
+ const BASE_THEMES = deepFreeze({
132
+ light: { ...LIGHT_BASE_THEME, ...LIGHT_BASE_ACCESSIBILITY_VARS },
133
+ dark: { ...DARK_BASE_THEME, ...DARK_BASE_ACCESSIBILITY_VARS },
134
+ });
135
+ const BUILT_IN_COLOR_SCHEMES = deepFreeze([
136
+ {
137
+ id: "black-on-white",
138
+ name: "Black on White",
139
+ description: "High contrast for readability",
140
+ variables: {
141
+ "--pie-text": "#000000",
142
+ "--pie-disabled": "#666666",
143
+ "--pie-disabled-secondary": "#888888",
144
+ "--pie-correct": "#006600",
145
+ "--pie-correct-secondary": "#ccffcc",
146
+ "--pie-correct-tertiary": "#008800",
147
+ "--pie-correct-icon": "#004400",
148
+ "--pie-incorrect": "#cc0000",
149
+ "--pie-content-emphasis": "#cc0000",
150
+ "--pie-incorrect-secondary": "#ffcccc",
151
+ "--pie-incorrect-icon": "#990000",
152
+ "--pie-missing": "#cc0000",
153
+ "--pie-missing-icon": "#000099",
154
+ "--pie-primary": "#0000cc",
155
+ "--pie-primary-light": "#6666ff",
156
+ "--pie-primary-dark": "#000088",
157
+ "--pie-faded-primary": "#ccccff",
158
+ "--pie-secondary": "#cc0066",
159
+ "--pie-secondary-light": "#ff99cc",
160
+ "--pie-secondary-dark": "#990044",
161
+ "--pie-tertiary": "#006699",
162
+ "--pie-tertiary-light": "#99ccff",
163
+ "--pie-background": "#ffffff",
164
+ "--pie-background-dark": "#f5f5f5",
165
+ "--pie-secondary-background": "#eeeeee",
166
+ "--pie-dropdown-background": "#e0e0e0",
167
+ "--pie-border": "#000000",
168
+ "--pie-border-light": "#666666",
169
+ "--pie-border-dark": "#000000",
170
+ "--pie-border-gray": "#555555",
171
+ "--pie-black": "#000000",
172
+ "--pie-white": "#ffffff",
173
+ "--pie-focus-checked": "#0066ff",
174
+ "--pie-focus-checked-border": "#0000cc",
175
+ "--pie-focus-unchecked": "#cccccc",
176
+ "--pie-focus-unchecked-border": "#000000",
177
+ "--pie-blue-grey-100": "#f5f5f5",
178
+ "--pie-blue-grey-300": "#cccccc",
179
+ "--pie-blue-grey-600": "#666666",
180
+ "--pie-blue-grey-900": "#000000",
181
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
182
+ "--pie-annotation-underline": "#4221d5",
183
+ "--pie-annotation-underline-dark": "#4221d5",
184
+ "--pie-button-bg": "#ffffff",
185
+ "--pie-button-border": "#666666",
186
+ "--pie-button-color": "#000000",
187
+ "--pie-button-hover-bg": "#f5f5f5",
188
+ "--pie-button-hover-border": "#000000",
189
+ "--pie-button-hover-color": "#000000",
190
+ "--pie-button-active-bg": "#eeeeee",
191
+ "--pie-button-focus-outline": "#0000cc",
192
+ "--pie-fixed-hue-collapse": "100%",
193
+ },
194
+ },
195
+ {
196
+ id: "white-on-black",
197
+ name: "White on Black",
198
+ description: "Inverse high contrast",
199
+ variables: {
200
+ "--pie-text": "#ffffff",
201
+ "--pie-disabled": "#999999",
202
+ "--pie-disabled-secondary": "#777777",
203
+ "--pie-correct": "#00ff00",
204
+ "--pie-correct-secondary": "#003300",
205
+ "--pie-correct-tertiary": "#00cc00",
206
+ "--pie-correct-icon": "#00ff00",
207
+ "--pie-incorrect": "#ff3333",
208
+ "--pie-content-emphasis": "#ff3333",
209
+ "--pie-incorrect-secondary": "#330000",
210
+ "--pie-incorrect-icon": "#ff0000",
211
+ "--pie-missing": "#ff6666",
212
+ "--pie-missing-icon": "#6666ff",
213
+ "--pie-primary": "#ffff00",
214
+ "--pie-primary-light": "#ffff99",
215
+ "--pie-primary-dark": "#cccc00",
216
+ "--pie-faded-primary": "#666600",
217
+ "--pie-secondary": "#ff00ff",
218
+ "--pie-secondary-light": "#ff99ff",
219
+ "--pie-secondary-dark": "#cc00cc",
220
+ "--pie-tertiary": "#00ffff",
221
+ "--pie-tertiary-light": "#99ffff",
222
+ "--pie-background": "#000000",
223
+ "--pie-background-dark": "#1a1a1a",
224
+ "--pie-secondary-background": "#222222",
225
+ "--pie-dropdown-background": "#2a2a2a",
226
+ "--pie-border": "#ffffff",
227
+ "--pie-border-light": "#cccccc",
228
+ "--pie-border-dark": "#ffffff",
229
+ "--pie-border-gray": "#aaaaaa",
230
+ "--pie-black": "#ffffff",
231
+ "--pie-white": "#000000",
232
+ "--pie-focus-checked": "#ffff00",
233
+ "--pie-focus-checked-border": "#ffff00",
234
+ "--pie-focus-unchecked": "#666666",
235
+ "--pie-focus-unchecked-border": "#ffffff",
236
+ "--pie-blue-grey-100": "#2a2a2a",
237
+ "--pie-blue-grey-300": "#555555",
238
+ "--pie-blue-grey-600": "#999999",
239
+ "--pie-blue-grey-900": "#ffffff",
240
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
241
+ "--pie-annotation-underline": "#9c89ec",
242
+ "--pie-annotation-underline-dark": "#9c89ec",
243
+ "--pie-button-bg": "#000000",
244
+ "--pie-button-border": "#cccccc",
245
+ "--pie-button-color": "#ffffff",
246
+ "--pie-button-hover-bg": "#1a1a1a",
247
+ "--pie-button-hover-border": "#ffffff",
248
+ "--pie-button-hover-color": "#ffffff",
249
+ "--pie-button-active-bg": "#222222",
250
+ "--pie-button-focus-outline": "#ffff00",
251
+ "--pie-fixed-hue-collapse": "100%",
252
+ },
253
+ },
254
+ {
255
+ id: "rose-on-green",
256
+ name: "Rose on Green",
257
+ description: "Color blind friendly (protanopia/deuteranopia)",
258
+ variables: {
259
+ "--pie-text": "#3d0022",
260
+ "--pie-disabled": "#996677",
261
+ "--pie-disabled-secondary": "#bb8899",
262
+ "--pie-correct": "#004400",
263
+ "--pie-correct-secondary": "#aaffaa",
264
+ "--pie-correct-tertiary": "#006600",
265
+ "--pie-correct-icon": "#003300",
266
+ "--pie-incorrect": "#aa0044",
267
+ "--pie-content-emphasis": "#aa0044",
268
+ "--pie-incorrect-secondary": "#ffccdd",
269
+ "--pie-incorrect-icon": "#880033",
270
+ "--pie-missing": "#aa0044",
271
+ "--pie-missing-icon": "#440044",
272
+ "--pie-primary": "#660044",
273
+ "--pie-primary-light": "#cc6699",
274
+ "--pie-primary-dark": "#440033",
275
+ "--pie-faded-primary": "#ddbbcc",
276
+ "--pie-secondary": "#880055",
277
+ "--pie-secondary-light": "#dd99bb",
278
+ "--pie-secondary-dark": "#550033",
279
+ "--pie-tertiary": "#770044",
280
+ "--pie-tertiary-light": "#dd99bb",
281
+ "--pie-background": "#ccffcc",
282
+ "--pie-background-dark": "#aaeedd",
283
+ "--pie-secondary-background": "#99ddbb",
284
+ "--pie-dropdown-background": "#88cc99",
285
+ "--pie-border": "#3d0022",
286
+ "--pie-border-light": "#663344",
287
+ "--pie-border-dark": "#220011",
288
+ "--pie-border-gray": "#664455",
289
+ "--pie-black": "#3d0022",
290
+ "--pie-white": "#ccffcc",
291
+ "--pie-focus-checked": "#880055",
292
+ "--pie-focus-checked-border": "#660044",
293
+ "--pie-focus-unchecked": "#aaddbb",
294
+ "--pie-focus-unchecked-border": "#3d0022",
295
+ "--pie-blue-grey-100": "#ccffdd",
296
+ "--pie-blue-grey-300": "#99ddbb",
297
+ "--pie-blue-grey-600": "#668877",
298
+ "--pie-blue-grey-900": "#3d0022",
299
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
300
+ "--pie-annotation-underline": "#4221d5",
301
+ "--pie-annotation-underline-dark": "#4221d5",
302
+ "--pie-button-bg": "#ccffcc",
303
+ "--pie-button-border": "#663344",
304
+ "--pie-button-color": "#3d0022",
305
+ "--pie-button-hover-bg": "#aaeedd",
306
+ "--pie-button-hover-border": "#3d0022",
307
+ "--pie-button-hover-color": "#3d0022",
308
+ "--pie-button-active-bg": "#99ddbb",
309
+ "--pie-button-focus-outline": "#660044",
310
+ "--pie-fixed-hue-collapse": "100%",
311
+ },
312
+ },
313
+ {
314
+ id: "yellow-on-blue",
315
+ name: "Yellow on Blue",
316
+ description: "Strong contrast scheme",
317
+ variables: {
318
+ "--pie-text": "#ffff00",
319
+ "--pie-disabled": "#9999aa",
320
+ "--pie-disabled-secondary": "#aaaacc",
321
+ "--pie-correct": "#00ff00",
322
+ "--pie-correct-secondary": "#003333",
323
+ "--pie-correct-tertiary": "#00cc00",
324
+ "--pie-correct-icon": "#00ff00",
325
+ "--pie-incorrect": "#ff6666",
326
+ "--pie-content-emphasis": "#ff6666",
327
+ "--pie-incorrect-secondary": "#331111",
328
+ "--pie-incorrect-icon": "#ff3333",
329
+ "--pie-missing": "#ff6666",
330
+ "--pie-missing-icon": "#99ff99",
331
+ "--pie-primary": "#ffff66",
332
+ "--pie-primary-light": "#ffffaa",
333
+ "--pie-primary-dark": "#cccc00",
334
+ "--pie-faded-primary": "#666633",
335
+ "--pie-secondary": "#ffaa00",
336
+ "--pie-secondary-light": "#ffcc66",
337
+ "--pie-secondary-dark": "#cc8800",
338
+ "--pie-tertiary": "#ffee00",
339
+ "--pie-tertiary-light": "#ffff99",
340
+ "--pie-background": "#000066",
341
+ "--pie-background-dark": "#000055",
342
+ "--pie-secondary-background": "#000044",
343
+ "--pie-dropdown-background": "#000033",
344
+ "--pie-border": "#ffff00",
345
+ "--pie-border-light": "#aaaa66",
346
+ "--pie-border-dark": "#cccc00",
347
+ "--pie-border-gray": "#8888aa",
348
+ "--pie-black": "#ffff00",
349
+ "--pie-white": "#000066",
350
+ "--pie-focus-checked": "#ffff00",
351
+ "--pie-focus-checked-border": "#cccc00",
352
+ "--pie-focus-unchecked": "#333366",
353
+ "--pie-focus-unchecked-border": "#ffff00",
354
+ "--pie-blue-grey-100": "#000055",
355
+ "--pie-blue-grey-300": "#333377",
356
+ "--pie-blue-grey-600": "#6666aa",
357
+ "--pie-blue-grey-900": "#ffff00",
358
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
359
+ "--pie-annotation-underline": "#9c89ec",
360
+ "--pie-annotation-underline-dark": "#9c89ec",
361
+ "--pie-button-bg": "#000066",
362
+ "--pie-button-border": "#aaaa66",
363
+ "--pie-button-color": "#ffff00",
364
+ "--pie-button-hover-bg": "#000055",
365
+ "--pie-button-hover-border": "#ffff00",
366
+ "--pie-button-hover-color": "#ffff00",
367
+ "--pie-button-active-bg": "#000044",
368
+ "--pie-button-focus-outline": "#ffff66",
369
+ "--pie-fixed-hue-collapse": "100%",
370
+ },
371
+ },
372
+ {
373
+ id: "black-on-rose",
374
+ name: "Black on Rose",
375
+ description: "Warm tinted background",
376
+ variables: {
377
+ "--pie-text": "#000000",
378
+ "--pie-disabled": "#666666",
379
+ "--pie-disabled-secondary": "#888888",
380
+ "--pie-correct": "#006600",
381
+ "--pie-correct-secondary": "#ccffcc",
382
+ "--pie-correct-tertiary": "#007000",
383
+ "--pie-correct-icon": "#004400",
384
+ "--pie-incorrect": "#990000",
385
+ "--pie-content-emphasis": "#990000",
386
+ "--pie-incorrect-secondary": "#ffdddd",
387
+ "--pie-incorrect-icon": "#770000",
388
+ "--pie-missing": "#990000",
389
+ "--pie-missing-icon": "#000099",
390
+ "--pie-primary": "#880044",
391
+ "--pie-primary-light": "#dd6699",
392
+ "--pie-primary-dark": "#550033",
393
+ "--pie-faded-primary": "#ffccdd",
394
+ "--pie-secondary": "#aa0055",
395
+ "--pie-secondary-light": "#ff99cc",
396
+ "--pie-secondary-dark": "#770033",
397
+ "--pie-tertiary": "#990044",
398
+ "--pie-tertiary-light": "#ffaacc",
399
+ "--pie-background": "#ffccdd",
400
+ "--pie-background-dark": "#ffb3cc",
401
+ "--pie-secondary-background": "#ff99bb",
402
+ "--pie-dropdown-background": "#ff88aa",
403
+ "--pie-border": "#000000",
404
+ "--pie-border-light": "#555555",
405
+ "--pie-border-dark": "#000000",
406
+ "--pie-border-gray": "#444444",
407
+ "--pie-black": "#000000",
408
+ "--pie-white": "#ffccdd",
409
+ "--pie-focus-checked": "#880044",
410
+ "--pie-focus-checked-border": "#550033",
411
+ "--pie-focus-unchecked": "#ffddee",
412
+ "--pie-focus-unchecked-border": "#000000",
413
+ "--pie-blue-grey-100": "#ffeef5",
414
+ "--pie-blue-grey-300": "#ffccdd",
415
+ "--pie-blue-grey-600": "#cc6688",
416
+ "--pie-blue-grey-900": "#000000",
417
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
418
+ "--pie-annotation-underline": "#4221d5",
419
+ "--pie-annotation-underline-dark": "#4221d5",
420
+ "--pie-button-bg": "#ffccdd",
421
+ "--pie-button-border": "#555555",
422
+ "--pie-button-color": "#000000",
423
+ "--pie-button-hover-bg": "#ffb3cc",
424
+ "--pie-button-hover-border": "#000000",
425
+ "--pie-button-hover-color": "#000000",
426
+ "--pie-button-active-bg": "#ff99bb",
427
+ "--pie-button-focus-outline": "#880044",
428
+ "--pie-fixed-hue-collapse": "100%",
429
+ },
430
+ },
431
+ {
432
+ id: "light-gray-on-dark-gray",
433
+ name: "Light Gray on Dark Gray",
434
+ description: "Reduced brightness for light sensitivity",
435
+ variables: {
436
+ "--pie-text": "#e0e0e0",
437
+ "--pie-disabled": "#999999",
438
+ "--pie-disabled-secondary": "#888888",
439
+ "--pie-correct": "#00cc00",
440
+ "--pie-correct-secondary": "#003300",
441
+ "--pie-correct-tertiary": "#00bb00",
442
+ "--pie-correct-icon": "#00ff00",
443
+ "--pie-incorrect": "#ff6a6a",
444
+ "--pie-content-emphasis": "#ff6a6a",
445
+ "--pie-incorrect-secondary": "#331111",
446
+ "--pie-incorrect-icon": "#ff0000",
447
+ "--pie-missing": "#ff6a6a",
448
+ "--pie-missing-icon": "#6868ff",
449
+ "--pie-primary": "#aaaaaa",
450
+ "--pie-primary-light": "#cccccc",
451
+ "--pie-primary-dark": "#888888",
452
+ "--pie-faded-primary": "#555555",
453
+ "--pie-secondary": "#bbbbbb",
454
+ "--pie-secondary-light": "#dddddd",
455
+ "--pie-secondary-dark": "#999999",
456
+ "--pie-tertiary": "#cccccc",
457
+ "--pie-tertiary-light": "#eeeeee",
458
+ "--pie-background": "#333333",
459
+ "--pie-background-dark": "#2a2a2a",
460
+ "--pie-secondary-background": "#222222",
461
+ "--pie-dropdown-background": "#1a1a1a",
462
+ "--pie-border": "#e0e0e0",
463
+ "--pie-border-light": "#cccccc",
464
+ "--pie-border-dark": "#ffffff",
465
+ "--pie-border-gray": "#aaaaaa",
466
+ "--pie-black": "#e0e0e0",
467
+ "--pie-white": "#333333",
468
+ "--pie-focus-checked": "#cccccc",
469
+ "--pie-focus-checked-border": "#aaaaaa",
470
+ "--pie-focus-unchecked": "#555555",
471
+ "--pie-focus-unchecked-border": "#e0e0e0",
472
+ "--pie-blue-grey-100": "#2a2a2a",
473
+ "--pie-blue-grey-300": "#555555",
474
+ "--pie-blue-grey-600": "#999999",
475
+ "--pie-blue-grey-900": "#e0e0e0",
476
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
477
+ "--pie-annotation-underline": "#9c89ec",
478
+ "--pie-annotation-underline-dark": "#9c89ec",
479
+ "--pie-button-bg": "#333333",
480
+ "--pie-button-border": "#cccccc",
481
+ "--pie-button-color": "#e0e0e0",
482
+ "--pie-button-hover-bg": "#2a2a2a",
483
+ "--pie-button-hover-border": "#ffffff",
484
+ "--pie-button-hover-color": "#e0e0e0",
485
+ "--pie-button-active-bg": "#222222",
486
+ "--pie-button-focus-outline": "#aaaaaa",
487
+ "--pie-fixed-hue-collapse": "100%",
488
+ },
489
+ },
490
+ {
491
+ id: "grey-on-light-grey",
492
+ name: "Grey on Light Grey",
493
+ description: "Low-glare neutral palette",
494
+ variables: {
495
+ "--pie-text": "#4a4a4a",
496
+ "--pie-disabled": "#757575",
497
+ "--pie-disabled-secondary": "#8f8f8f",
498
+ "--pie-correct": "#145c1e",
499
+ "--pie-correct-secondary": "#dde9de",
500
+ "--pie-correct-tertiary": "#1a7526",
501
+ "--pie-correct-icon": "#0e3f15",
502
+ "--pie-incorrect": "#8c1c1c",
503
+ "--pie-content-emphasis": "#8c1c1c",
504
+ "--pie-incorrect-secondary": "#eddcdc",
505
+ "--pie-incorrect-icon": "#6f1616",
506
+ "--pie-missing": "#8c1c1c",
507
+ "--pie-missing-icon": "#33406b",
508
+ "--pie-primary": "#3d3d3d",
509
+ "--pie-primary-light": "#6f6f6f",
510
+ "--pie-primary-dark": "#2b2b2b",
511
+ "--pie-faded-primary": "#dcdcdc",
512
+ "--pie-secondary": "#4a4a4a",
513
+ "--pie-secondary-light": "#8f8f8f",
514
+ "--pie-secondary-dark": "#2b2b2b",
515
+ "--pie-tertiary": "#3d3d3d",
516
+ "--pie-tertiary-light": "#c4c4c4",
517
+ "--pie-background": "#ebebeb",
518
+ "--pie-background-dark": "#dcdcdc",
519
+ "--pie-secondary-background": "#d0d0d0",
520
+ "--pie-dropdown-background": "#c4c4c4",
521
+ "--pie-border": "#4a4a4a",
522
+ "--pie-border-light": "#7a7a7a",
523
+ "--pie-border-dark": "#2b2b2b",
524
+ "--pie-border-gray": "#6f6f6f",
525
+ "--pie-black": "#4a4a4a",
526
+ "--pie-white": "#ebebeb",
527
+ "--pie-focus-checked": "#6f6f6f",
528
+ "--pie-focus-checked-border": "#3d3d3d",
529
+ "--pie-focus-unchecked": "#e0e0e0",
530
+ "--pie-focus-unchecked-border": "#4a4a4a",
531
+ "--pie-blue-grey-100": "#f0f0f0",
532
+ "--pie-blue-grey-300": "#d0d0d0",
533
+ "--pie-blue-grey-600": "#6f6f6f",
534
+ "--pie-blue-grey-900": "#2b2b2b",
535
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
536
+ "--pie-annotation-underline": "#4221d5",
537
+ "--pie-annotation-underline-dark": "#4221d5",
538
+ "--pie-button-bg": "#ebebeb",
539
+ "--pie-button-border": "#7a7a7a",
540
+ "--pie-button-color": "#4a4a4a",
541
+ "--pie-button-hover-bg": "#dcdcdc",
542
+ "--pie-button-hover-border": "#4a4a4a",
543
+ "--pie-button-hover-color": "#4a4a4a",
544
+ "--pie-button-active-bg": "#d0d0d0",
545
+ "--pie-button-focus-outline": "#3d3d3d",
546
+ "--pie-fixed-hue-collapse": "100%",
547
+ },
548
+ },
549
+ {
550
+ id: "purple-on-light-green",
551
+ name: "Purple on Light Green",
552
+ description: "Color blind friendly, low-glare background",
553
+ variables: {
554
+ "--pie-text": "#8e2464",
555
+ "--pie-disabled": "#5f7266",
556
+ "--pie-disabled-secondary": "#7c8f83",
557
+ "--pie-correct": "#14591f",
558
+ "--pie-correct-secondary": "#d8ecdc",
559
+ "--pie-correct-tertiary": "#1a7328",
560
+ "--pie-correct-icon": "#0e3d16",
561
+ "--pie-incorrect": "#8c1c1c",
562
+ "--pie-content-emphasis": "#8c1c1c",
563
+ "--pie-incorrect-secondary": "#f0dcdc",
564
+ "--pie-incorrect-icon": "#6f1616",
565
+ "--pie-missing": "#8c1c1c",
566
+ "--pie-missing-icon": "#33406b",
567
+ "--pie-primary": "#6d1a4c",
568
+ "--pie-primary-light": "#b3608e",
569
+ "--pie-primary-dark": "#4f1237",
570
+ "--pie-faded-primary": "#b8dcc3",
571
+ "--pie-secondary": "#a02b72",
572
+ "--pie-secondary-light": "#c76d9d",
573
+ "--pie-secondary-dark": "#6d1a4c",
574
+ "--pie-tertiary": "#8e2464",
575
+ "--pie-tertiary-light": "#e2c6d5",
576
+ "--pie-background": "#cce8d4",
577
+ "--pie-background-dark": "#b8dcc3",
578
+ "--pie-secondary-background": "#a6d0b2",
579
+ "--pie-dropdown-background": "#94c4a1",
580
+ "--pie-border": "#8e2464",
581
+ "--pie-border-light": "#a85a86",
582
+ "--pie-border-dark": "#4f1237",
583
+ "--pie-border-gray": "#5f7266",
584
+ "--pie-black": "#8e2464",
585
+ "--pie-white": "#cce8d4",
586
+ "--pie-focus-checked": "#8e2464",
587
+ "--pie-focus-checked-border": "#6d1a4c",
588
+ "--pie-focus-unchecked": "#dcefe2",
589
+ "--pie-focus-unchecked-border": "#8e2464",
590
+ "--pie-blue-grey-100": "#e2f2e7",
591
+ "--pie-blue-grey-300": "#a6d0b2",
592
+ "--pie-blue-grey-600": "#5f7266",
593
+ "--pie-blue-grey-900": "#4f1237",
594
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
595
+ "--pie-annotation-underline": "#4221d5",
596
+ "--pie-annotation-underline-dark": "#4221d5",
597
+ "--pie-button-bg": "#cce8d4",
598
+ "--pie-button-border": "#a85a86",
599
+ "--pie-button-color": "#8e2464",
600
+ "--pie-button-hover-bg": "#b8dcc3",
601
+ "--pie-button-hover-border": "#8e2464",
602
+ "--pie-button-hover-color": "#8e2464",
603
+ "--pie-button-active-bg": "#a6d0b2",
604
+ "--pie-button-focus-outline": "#6d1a4c",
605
+ "--pie-fixed-hue-collapse": "100%",
606
+ },
607
+ },
608
+ {
609
+ id: "black-on-violet",
610
+ name: "Black on Violet",
611
+ description: "Cool tinted background",
612
+ variables: {
613
+ "--pie-text": "#000000",
614
+ "--pie-disabled": "#5c5c5c",
615
+ "--pie-disabled-secondary": "#7a7a7a",
616
+ "--pie-correct": "#0d4f16",
617
+ "--pie-correct-secondary": "#e0cfe6",
618
+ "--pie-correct-tertiary": "#0f4d17",
619
+ "--pie-correct-icon": "#093a0f",
620
+ "--pie-incorrect": "#7d1414",
621
+ "--pie-content-emphasis": "#7d1414",
622
+ "--pie-incorrect-secondary": "#eccfd0",
623
+ "--pie-incorrect-icon": "#5c0f0f",
624
+ "--pie-missing": "#7d1414",
625
+ "--pie-missing-icon": "#2b2b6b",
626
+ "--pie-primary": "#4a1259",
627
+ "--pie-primary-light": "#8e4fa1",
628
+ "--pie-primary-dark": "#330d3f",
629
+ "--pie-faded-primary": "#c795d3",
630
+ "--pie-secondary": "#6d1a7d",
631
+ "--pie-secondary-light": "#a95cb8",
632
+ "--pie-secondary-dark": "#4a1259",
633
+ "--pie-tertiary": "#4a1259",
634
+ "--pie-tertiary-light": "#e2cbe8",
635
+ "--pie-background": "#d4a9de",
636
+ "--pie-background-dark": "#c795d3",
637
+ "--pie-secondary-background": "#b982c8",
638
+ "--pie-dropdown-background": "#ac70bd",
639
+ "--pie-border": "#000000",
640
+ "--pie-border-light": "#4a4a4a",
641
+ "--pie-border-dark": "#000000",
642
+ "--pie-border-gray": "#4a4a4a",
643
+ "--pie-black": "#000000",
644
+ "--pie-white": "#d4a9de",
645
+ "--pie-focus-checked": "#4a1259",
646
+ "--pie-focus-checked-border": "#330d3f",
647
+ "--pie-focus-unchecked": "#e2cbe8",
648
+ "--pie-focus-unchecked-border": "#000000",
649
+ "--pie-blue-grey-100": "#ece0f0",
650
+ "--pie-blue-grey-300": "#c795d3",
651
+ "--pie-blue-grey-600": "#6d5c73",
652
+ "--pie-blue-grey-900": "#000000",
653
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
654
+ "--pie-annotation-underline": "#4221d5",
655
+ "--pie-annotation-underline-dark": "#4221d5",
656
+ "--pie-button-bg": "#d4a9de",
657
+ "--pie-button-border": "#4a4a4a",
658
+ "--pie-button-color": "#000000",
659
+ "--pie-button-hover-bg": "#c795d3",
660
+ "--pie-button-hover-border": "#000000",
661
+ "--pie-button-hover-color": "#000000",
662
+ "--pie-button-active-bg": "#b982c8",
663
+ "--pie-button-focus-outline": "#4a1259",
664
+ "--pie-fixed-hue-collapse": "100%",
665
+ },
666
+ },
667
+ {
668
+ id: "yellow-on-navy",
669
+ name: "Yellow on Navy",
670
+ description: "Strong contrast on a softened dark blue",
671
+ variables: {
672
+ "--pie-text": "#ffff55",
673
+ "--pie-disabled": "#9aa4bd",
674
+ "--pie-disabled-secondary": "#7d88a3",
675
+ "--pie-correct": "#7fe08a",
676
+ "--pie-correct-secondary": "#1d3a24",
677
+ "--pie-correct-tertiary": "#a0dda9",
678
+ "--pie-correct-icon": "#a8f0b0",
679
+ "--pie-incorrect": "#ffbebe",
680
+ "--pie-content-emphasis": "#ffbebe",
681
+ "--pie-incorrect-secondary": "#3d1d1d",
682
+ "--pie-incorrect-icon": "#ffb3b3",
683
+ "--pie-missing": "#ffbebe",
684
+ "--pie-missing-icon": "#b3c2ff",
685
+ "--pie-primary": "#ffff99",
686
+ "--pie-primary-light": "#ffffc2",
687
+ "--pie-primary-dark": "#e0e04a",
688
+ "--pie-faded-primary": "#2b4576",
689
+ "--pie-secondary": "#ffd95c",
690
+ "--pie-secondary-light": "#ffeaa0",
691
+ "--pie-secondary-dark": "#e0bb3d",
692
+ "--pie-tertiary": "#ffff99",
693
+ "--pie-tertiary-light": "#ffffcc",
694
+ "--pie-background": "#33508a",
695
+ "--pie-background-dark": "#2b4576",
696
+ "--pie-secondary-background": "#243a63",
697
+ "--pie-dropdown-background": "#1d2f50",
698
+ "--pie-border": "#ffff55",
699
+ "--pie-border-light": "#c2c266",
700
+ "--pie-border-dark": "#e0e04a",
701
+ "--pie-border-gray": "#9aa4bd",
702
+ "--pie-black": "#ffff55",
703
+ "--pie-white": "#33508a",
704
+ "--pie-focus-checked": "#ffff55",
705
+ "--pie-focus-checked-border": "#e0e04a",
706
+ "--pie-focus-unchecked": "#243a63",
707
+ "--pie-focus-unchecked-border": "#ffff55",
708
+ "--pie-blue-grey-100": "#2b4576",
709
+ "--pie-blue-grey-300": "#4a6aa8",
710
+ "--pie-blue-grey-600": "#9aa4bd",
711
+ "--pie-blue-grey-900": "#ffff55",
712
+ "--pie-tool-annotation-toolbar-border": "var(--pie-border)",
713
+ "--pie-annotation-underline": "var(--pie-primary)",
714
+ "--pie-annotation-underline-dark": "var(--pie-primary)",
715
+ "--pie-button-bg": "#33508a",
716
+ "--pie-button-border": "#c2c266",
717
+ "--pie-button-color": "#ffff55",
718
+ "--pie-button-hover-bg": "#2b4576",
719
+ "--pie-button-hover-border": "#ffff55",
720
+ "--pie-button-hover-color": "#ffff55",
721
+ "--pie-button-active-bg": "#243a63",
722
+ "--pie-button-focus-outline": "#ffff99",
723
+ "--pie-fixed-hue-collapse": "100%",
724
+ },
725
+ },
726
+ ]);
727
+ const BUILT_IN_SCHEMES_BY_ID = new Map(BUILT_IN_COLOR_SCHEMES.map((scheme) => [scheme.id, scheme]));
728
+ const DEFAULT_SCHEME_DESCRIPTOR = deepFreeze({
729
+ id: "default",
730
+ name: "Default",
731
+ description: "Standard PIE colors",
732
+ kind: "default",
733
+ preview: createPieColorSchemePreview({
734
+ ...LIGHT_BASE_THEME,
735
+ // The live light Base Theme intentionally reveals its host surface. A
736
+ // catalog swatch has no such surface, so composite it on white explicitly.
737
+ "--pie-background": "#ffffff",
738
+ }),
739
+ });
740
+ const REQUIRED_SCHEME_TOKENS = Object.freeze(Object.entries(PIE_THEME_SCHEME_PARTICIPATION)
741
+ .filter(([, participation]) => participation === "required")
742
+ .map(([token]) => token)
743
+ .sort());
744
+ const OPTIONAL_SCHEME_TOKENS = Object.freeze(Object.entries(PIE_THEME_SCHEME_PARTICIPATION)
745
+ .filter(([, participation]) => participation === "optional")
746
+ .map(([token]) => token)
747
+ .sort());
748
+ /**
749
+ * Named semantic relationships are the accessibility contract. Token names
750
+ * alone do not say whether a color is text, a fill, or a boundary.
751
+ */
752
+ const PIE_THEME_CONTRAST_RELATIONSHIPS = deepFreeze([
753
+ {
754
+ foreground: "--pie-text",
755
+ background: "--pie-background",
756
+ minimum: 4.5,
757
+ role: "ordinary text",
758
+ },
759
+ {
760
+ // Where a fixed hue collapses to: a component folding its own encoding
761
+ // into the palette lands on this surface with this ink, so the pair has
762
+ // to hold on its own and not only against the page.
763
+ foreground: "--pie-text",
764
+ background: "--pie-background-dark",
765
+ minimum: 4.5,
766
+ role: "recessed surface text",
767
+ },
768
+ {
769
+ foreground: "--pie-tertiary",
770
+ background: "--pie-background",
771
+ minimum: 4.5,
772
+ role: "link text",
773
+ },
774
+ {
775
+ foreground: "--pie-correct",
776
+ background: "--pie-background",
777
+ minimum: 4.5,
778
+ role: "correct feedback text",
779
+ },
780
+ {
781
+ foreground: "--pie-correct-tertiary",
782
+ background: "--pie-background",
783
+ minimum: 4.5,
784
+ role: "correct feedback text",
785
+ },
786
+ {
787
+ foreground: "--pie-incorrect",
788
+ background: "--pie-background",
789
+ minimum: 4.5,
790
+ role: "incorrect feedback text",
791
+ },
792
+ {
793
+ foreground: "--pie-missing",
794
+ background: "--pie-background",
795
+ minimum: 4.5,
796
+ role: "missing-response text",
797
+ },
798
+ {
799
+ foreground: "--pie-correct-icon",
800
+ background: "--pie-background",
801
+ minimum: 3,
802
+ role: "correct feedback icon",
803
+ },
804
+ {
805
+ foreground: "--pie-incorrect-icon",
806
+ background: "--pie-background",
807
+ minimum: 3,
808
+ role: "incorrect feedback icon",
809
+ },
810
+ {
811
+ foreground: "--pie-missing-icon",
812
+ background: "--pie-background",
813
+ minimum: 3,
814
+ role: "missing-response icon",
815
+ },
816
+ {
817
+ foreground: "--pie-border",
818
+ background: "--pie-background",
819
+ minimum: 3,
820
+ role: "control boundary",
821
+ },
822
+ {
823
+ foreground: "--pie-focus-checked-border",
824
+ background: "--pie-background",
825
+ minimum: 3,
826
+ role: "checked-control focus boundary",
827
+ },
828
+ {
829
+ foreground: "--pie-focus-unchecked-border",
830
+ background: "--pie-background",
831
+ minimum: 3,
832
+ role: "unchecked-control focus boundary",
833
+ },
834
+ {
835
+ foreground: "--pie-button-color",
836
+ background: "--pie-button-bg",
837
+ minimum: 4.5,
838
+ role: "button text",
839
+ },
840
+ {
841
+ foreground: "--pie-button-color",
842
+ background: "--pie-button-active-bg",
843
+ minimum: 4.5,
844
+ role: "active button text",
845
+ },
846
+ {
847
+ foreground: "--pie-button-border",
848
+ background: "--pie-background",
849
+ minimum: 3,
850
+ role: "button boundary",
851
+ },
852
+ {
853
+ foreground: "--pie-button-hover-color",
854
+ background: "--pie-button-hover-bg",
855
+ minimum: 4.5,
856
+ role: "hovered button text",
857
+ },
858
+ {
859
+ foreground: "--pie-button-hover-border",
860
+ background: "--pie-background",
861
+ minimum: 3,
862
+ role: "hovered button boundary",
863
+ },
864
+ {
865
+ foreground: "--pie-button-focus-outline",
866
+ background: "--pie-background",
867
+ minimum: 3,
868
+ role: "button focus indicator",
869
+ },
870
+ {
871
+ foreground: "--pie-button-focus-outline",
872
+ background: "--pie-button-bg",
873
+ minimum: 3,
874
+ role: "button focus indicator against its control",
875
+ },
876
+ {
877
+ foreground: "--pie-button-focus-outline",
878
+ background: "--pie-button-hover-bg",
879
+ minimum: 3,
880
+ role: "hovered button focus indicator",
881
+ },
882
+ {
883
+ foreground: "--pie-button-focus-outline",
884
+ background: "--pie-button-active-bg",
885
+ minimum: 3,
886
+ role: "active button focus indicator",
887
+ },
888
+ {
889
+ foreground: "--pie-annotation-underline",
890
+ background: "--pie-background",
891
+ minimum: 3,
892
+ role: "annotation underline",
893
+ },
894
+ {
895
+ foreground: "--pie-tool-annotation-toolbar-border",
896
+ background: "--pie-background",
897
+ minimum: 3,
898
+ role: "annotation toolbar boundary",
899
+ },
900
+ ]);
901
+ function parseOpaqueColor(value) {
902
+ const normalized = value.trim().toLowerCase();
903
+ if (normalized === "black")
904
+ return { r: 0, g: 0, b: 0 };
905
+ if (normalized === "white")
906
+ return { r: 255, g: 255, b: 255 };
907
+ if (normalized === "rgba(255, 255, 255, 0)") {
908
+ // The transparent light Base Theme is an externally observed behavior. Its
909
+ // effective contrast depends on the host backdrop and cannot be certified
910
+ // from the token value alone.
911
+ return null;
912
+ }
913
+ const hex = /^#([0-9a-f]{3}|[0-9a-f]{6})$/i.exec(normalized);
914
+ if (hex) {
915
+ const expanded = hex[1].length === 3
916
+ ? [...hex[1]].map((channel) => channel.repeat(2)).join("")
917
+ : hex[1];
918
+ const numeric = Number.parseInt(expanded, 16);
919
+ return {
920
+ r: (numeric >> 16) & 255,
921
+ g: (numeric >> 8) & 255,
922
+ b: numeric & 255,
923
+ };
924
+ }
925
+ const rgb = /^rgba?\(\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)(?:\s*,\s*(\d+(?:\.\d+)?))?\s*\)$/.exec(normalized);
926
+ if (!rgb || (rgb[4] !== undefined && Number.parseFloat(rgb[4]) !== 1)) {
927
+ return null;
928
+ }
929
+ const channels = rgb.slice(1, 4).map(Number);
930
+ if (channels.some((channel) => channel < 0 || channel > 255)) {
931
+ return null;
932
+ }
933
+ return { r: channels[0], g: channels[1], b: channels[2] };
934
+ }
935
+ function channelLuminance(channel) {
936
+ const value = channel / 255;
937
+ return value <= 0.04045 ? value / 12.92 : ((value + 0.055) / 1.055) ** 2.4;
938
+ }
939
+ function luminance(color) {
940
+ return (0.2126 * channelLuminance(color.r) +
941
+ 0.7152 * channelLuminance(color.g) +
942
+ 0.0722 * channelLuminance(color.b));
943
+ }
944
+ function contrastRatio(foreground, background) {
945
+ const a = luminance(foreground);
946
+ const b = luminance(background);
947
+ return (Math.max(a, b) + 0.05) / (Math.min(a, b) + 0.05);
948
+ }
949
+ function resolveColor(variables, token, seen = new Set()) {
950
+ if (seen.has(token))
951
+ return undefined;
952
+ seen.add(token);
953
+ const value = variables[token]?.trim();
954
+ if (!value)
955
+ return undefined;
956
+ const reference = /^var\(\s*(--pie-[a-z0-9-]+)\s*\)$/i.exec(value);
957
+ return reference
958
+ ? resolveColor(variables, reference[1], seen)
959
+ : value;
960
+ }
961
+ export function diagnoseThemeContrast(variables, schemeId, relevantTokens) {
962
+ const diagnostics = [];
963
+ for (const relationship of PIE_THEME_CONTRAST_RELATIONSHIPS) {
964
+ if (relevantTokens &&
965
+ !relevantTokens.has(relationship.foreground) &&
966
+ !relevantTokens.has(relationship.background)) {
967
+ continue;
968
+ }
969
+ const foregroundValue = resolveColor(variables, relationship.foreground);
970
+ const backgroundValue = resolveColor(variables, relationship.background);
971
+ const foreground = foregroundValue
972
+ ? parseOpaqueColor(foregroundValue)
973
+ : null;
974
+ const background = backgroundValue
975
+ ? parseOpaqueColor(backgroundValue)
976
+ : null;
977
+ if (!foreground || !background) {
978
+ diagnostics.push({
979
+ code: "contrast-unmeasurable",
980
+ severity: "warning",
981
+ message: `Could not measure ${relationship.role} contrast for ${relationship.foreground} against ${relationship.background}.`,
982
+ schemeId,
983
+ token: relationship.foreground,
984
+ });
985
+ continue;
986
+ }
987
+ const ratio = contrastRatio(foreground, background);
988
+ if (ratio < relationship.minimum) {
989
+ diagnostics.push({
990
+ code: "contrast-too-low",
991
+ severity: "warning",
992
+ message: `${relationship.role} contrast is ${ratio.toFixed(2)}:1; ${relationship.minimum}:1 is required.`,
993
+ schemeId,
994
+ token: relationship.foreground,
995
+ });
996
+ }
997
+ }
998
+ return Object.freeze(diagnostics);
999
+ }
1000
+ export function getBaseThemeVariables(baseTheme) {
1001
+ return BASE_THEMES[baseTheme];
1002
+ }
1003
+ export function listBuiltInColorSchemeDefinitions() {
1004
+ return BUILT_IN_COLOR_SCHEMES;
1005
+ }
1006
+ export function getBuiltInColorSchemeDefinition(id) {
1007
+ return BUILT_IN_SCHEMES_BY_ID.get(id);
1008
+ }
1009
+ export function getDefaultColorSchemeDescriptor() {
1010
+ return DEFAULT_SCHEME_DESCRIPTOR;
1011
+ }
1012
+ export function createPieColorSchemePreview(variables) {
1013
+ return deepFreeze({
1014
+ bg: variables["--pie-background"] ??
1015
+ variables["--pie-secondary-background"] ??
1016
+ "#ffffff",
1017
+ text: variables["--pie-text"] ?? "#000000",
1018
+ primary: variables["--pie-primary"] ?? "#3f51b5",
1019
+ });
1020
+ }
1021
+ export function getSchemeParticipation(token) {
1022
+ return PIE_THEME_SCHEME_PARTICIPATION[token];
1023
+ }
1024
+ export function getRequiredSchemeTokens() {
1025
+ return REQUIRED_SCHEME_TOKENS;
1026
+ }
1027
+ export function getOptionalSchemeTokens() {
1028
+ return OPTIONAL_SCHEME_TOKENS;
1029
+ }
1030
+ export function createBuiltInColorSchemeDescriptor(definition) {
1031
+ return deepFreeze({
1032
+ id: definition.id,
1033
+ name: definition.name,
1034
+ description: definition.description,
1035
+ kind: "built-in",
1036
+ preview: createPieColorSchemePreview(definition.variables),
1037
+ });
1038
+ }
1039
+ function validateBuiltInDefinitions() {
1040
+ const required = new Set(REQUIRED_SCHEME_TOKENS);
1041
+ const ids = new Set();
1042
+ const failures = [];
1043
+ for (const scheme of BUILT_IN_COLOR_SCHEMES) {
1044
+ if (ids.has(scheme.id)) {
1045
+ failures.push(`duplicate built-in id ${scheme.id}`);
1046
+ }
1047
+ ids.add(scheme.id);
1048
+ const actual = new Set(Object.keys(scheme.variables));
1049
+ const missing = [...required].filter((token) => !actual.has(token));
1050
+ const extra = [...actual].filter((token) => !required.has(token));
1051
+ if (missing.length > 0) {
1052
+ failures.push(`${scheme.id} missing: ${missing.join(", ")}`);
1053
+ }
1054
+ if (extra.length > 0) {
1055
+ failures.push(`${scheme.id} has non-required tokens: ${extra.join(", ")}`);
1056
+ }
1057
+ for (const diagnostic of diagnoseThemeContrast(scheme.variables, scheme.id)) {
1058
+ failures.push(`${scheme.id}: ${diagnostic.message}`);
1059
+ }
1060
+ }
1061
+ return failures;
1062
+ }
1063
+ function validateBaseThemes() {
1064
+ const failures = [];
1065
+ for (const baseTheme of ["light", "dark"]) {
1066
+ const measurableVariables = baseTheme === "light"
1067
+ ? { ...BASE_THEMES.light, "--pie-background": "#ffffff" }
1068
+ : BASE_THEMES.dark;
1069
+ for (const diagnostic of diagnoseThemeContrast(measurableVariables, `${baseTheme}-base`)) {
1070
+ failures.push(`${baseTheme}: ${diagnostic.message}`);
1071
+ }
1072
+ }
1073
+ return failures;
1074
+ }
1075
+ /** Build-time invariant check; browser entries only read the frozen definitions. */
1076
+ export function assertCanonicalThemeDefinitions() {
1077
+ const failures = [...validateBaseThemes(), ...validateBuiltInDefinitions()];
1078
+ if (failures.length > 0) {
1079
+ throw new Error(`Invalid canonical PIE theme definitions:\n- ${failures.join("\n- ")}`);
1080
+ }
1081
+ }