muigui 0.0.10 → 0.0.13

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.
@@ -9,6 +9,11 @@ const hexToUint32RGB = v => (parseInt(v.substring(1, 3), 16) << 16) |
9
9
  (parseInt(v.substring(3, 5), 16) << 8 ) |
10
10
  (parseInt(v.substring(5, 7), 16) );
11
11
  const uint32RGBToHex = v => `#${(Math.round(v)).toString(16).padStart(6, '0')}`;
12
+ const hexToUint32RGBA = v => (parseInt(v.substring(1, 3), 16) * 2 ** 24) +
13
+ (parseInt(v.substring(3, 5), 16) * 2 ** 16) +
14
+ (parseInt(v.substring(5, 7), 16) * 2 ** 8) +
15
+ (parseInt(v.substring(7, 9), 16) );
16
+ const uint32RGBAToHex = v => `#${(Math.round(v)).toString(16).padStart(8, '0')}`;
12
17
 
13
18
  export const hexToUint8RGB = v => [
14
19
  parseInt(v.substring(1, 3), 16),
@@ -17,16 +22,35 @@ export const hexToUint8RGB = v => [
17
22
  ];
18
23
  export const uint8RGBToHex = v => `#${Array.from(v).map(v => v.toString(16).padStart(2, '0')).join('')}`;
19
24
 
25
+ export const hexToUint8RGBA = v => [
26
+ parseInt(v.substring(1, 3), 16),
27
+ parseInt(v.substring(3, 5), 16),
28
+ parseInt(v.substring(5, 7), 16),
29
+ parseInt(v.substring(7, 9), 16),
30
+ ];
31
+ export const uint8RGBAToHex = v => `#${Array.from(v).map(v => v.toString(16).padStart(2, '0')).join('')}`;
32
+
20
33
  export const hexToFloatRGB = v => hexToUint8RGB(v).map(v => f3(v / 255));
21
34
  export const floatRGBToHex = v => uint8RGBToHex(Array.from(v).map(v => Math.round(clamp(v * 255, 0, 255))));
22
35
 
36
+ export const hexToFloatRGBA = v => hexToUint8RGBA(v).map(v => f3(v / 255));
37
+ export const floatRGBAToHex = v => uint8RGBAToHex(Array.from(v).map(v => Math.round(clamp(v * 255, 0, 255))));
38
+
39
+ const scaleAndClamp = v => clamp(Math.round(v * 255), 0, 255).toString(16).padStart(2, '0');
40
+
23
41
  const hexToObjectRGB = v => ({
24
42
  r: parseInt(v.substring(1, 3), 16) / 255,
25
43
  g: parseInt(v.substring(3, 5), 16) / 255,
26
44
  b: parseInt(v.substring(5, 7), 16) / 255,
27
45
  });
28
- const scaleAndClamp = v => clamp(Math.round(v * 255), 0, 255).toString(16).padStart(2, '0');
29
46
  const objectRGBToHex = v => `#${scaleAndClamp(v.r)}${scaleAndClamp(v.g)}${scaleAndClamp(v.b)}`;
47
+ const hexToObjectRGBA = v => ({
48
+ r: parseInt(v.substring(1, 3), 16) / 255,
49
+ g: parseInt(v.substring(3, 5), 16) / 255,
50
+ b: parseInt(v.substring(5, 7), 16) / 255,
51
+ a: parseInt(v.substring(7, 9), 16) / 255,
52
+ });
53
+ const objectRGBAToHex = v => `#${scaleAndClamp(v.r)}${scaleAndClamp(v.g)}${scaleAndClamp(v.b)}${scaleAndClamp(v.a)}`;
30
54
 
31
55
  const hexToCssRGB = v => `rgb(${hexToUint8RGB(v).join(', ')})`;
32
56
  const cssRGBRegex = /^\s*rgb\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*\)\s*$/;
@@ -34,14 +58,23 @@ const cssRGBToHex = v => {
34
58
  const m = cssRGBRegex.exec(v);
35
59
  return uint8RGBToHex([m[1], m[2], m[3]].map(v => parseInt(v)));
36
60
  };
37
- const cssRGBARegex = /^\s*rgba\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*\)\s*$/;
61
+ const hexToCssRGBA = v => `rgba(${hexToUint8RGBA(v).map((v, i) => i === 3 ? v / 255 : v).join(', ')})`;
62
+ const cssRGBARegex = /^\s*rgba\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+\.\d+|\d+)\s*\)\s*$/;
63
+ const cssRGBAToHex = v => {
64
+ const m = cssRGBARegex.exec(v);
65
+ return uint8RGBAToHex([m[1], m[2], m[3], m[4]].map((v, i) => i === 3 ? (parseFloat(v) * 255 | 0) : parseInt(v)));
66
+ };
38
67
 
39
68
  const hexToCssHSL = v => {
40
69
  const hsl = rgbUint8ToHsl(hexToUint8RGB(v)).map(v => f0(v));
41
70
  return `hsl(${hsl[0]}, ${hsl[1]}%, ${hsl[2]}%)`;
42
71
  };
43
- const cssHSLRegex = /^\s*hsl\(\s*(\d+)(?:deg|)\s*,\s*(\d+)%\s*,\s*(\d+)%\s*\)\s*$/;
44
- const cssHSLARegex = /^\s*hsl\(\s*(\d+)(?:deg|)\s*,\s*(\d+)%\s*,\s*(\d+)%\s*,\s*(\d+)%\s*\)\s*$/;
72
+ const hexToCssHSLA = v => {
73
+ const hsla = rgbaUint8ToHsla(hexToUint8RGBA(v)).map((v, i) => i === 3 ? f3(v) : f0(v));
74
+ return `hsl(${hsla[0]} ${hsla[1]}% ${hsla[2]}% / ${hsla[3]})`;
75
+ };
76
+ const cssHSLRegex = /^\s*hsl\(\s*(\d+)(?:deg|)\s*(?:,|)\s*(\d+)%\s*(?:,|)\s*(\d+)%\s*\)\s*$/;
77
+ const cssHSLARegex = /^\s*hsl\(\s*(\d+)(?:deg|)\s*(?:,|)\s*(\d+)%\s*(?:,|)\s*(\d+)%\s*\/\s*(\d+\.\d+|\d+)\s*\)\s*$/;
45
78
 
46
79
  const hex3DigitTo6Digit = v => `${v[0]}${v[0]}${v[1]}${v[1]}${v[2]}${v[2]}`;
47
80
  const cssHSLToHex = v => {
@@ -49,6 +82,11 @@ const cssHSLToHex = v => {
49
82
  const rgb = hslToRgbUint8([m[1], m[2], m[3]].map(v => parseFloat(v)));
50
83
  return uint8RGBToHex(rgb);
51
84
  };
85
+ const cssHSLAToHex = v => {
86
+ const m = cssHSLARegex.exec(v);
87
+ const rgba = hslaToRgbaUint8([m[1], m[2], m[3], m[4]].map(v => parseFloat(v)));
88
+ return uint8RGBAToHex(rgba);
89
+ };
52
90
 
53
91
  const euclideanModulo = (v, n) => ((v % n) + n) % n;
54
92
 
@@ -67,6 +105,11 @@ export function hslToRgbUint8([h, s, l]) {
67
105
  return [f(0), f(8), f(4)].map(v => Math.round(v * 255));
68
106
  }
69
107
 
108
+ export function hslaToRgbaUint8([h, s, l, a]) {
109
+ const rgb = hslToRgbUint8([h, s, l]);
110
+ return [...rgb, a * 255 | 0];
111
+ }
112
+
70
113
  export function rgbFloatToHsl01([r, g, b]) {
71
114
  const max = Math.max(r, g, b);
72
115
  const min = Math.min(r, g, b);
@@ -90,11 +133,21 @@ export function rgbFloatToHsl01([r, g, b]) {
90
133
  return [h / 6, s, l];
91
134
  }
92
135
 
136
+ export function rgbaFloatToHsla01([r, g, b, a]) {
137
+ const hsl = rgbFloatToHsl01([r, g, b]);
138
+ return [...hsl, a];
139
+ }
140
+
93
141
  export const rgbUint8ToHsl = (rgb) => {
94
142
  const [h, s, l] = rgbFloatToHsl01(rgb.map(v => v / 255));
95
143
  return [h * 360, s * 100, l * 100];
96
144
  };
97
145
 
146
+ export const rgbaUint8ToHsla = (rgba) => {
147
+ const [h, s, l, a] = rgbaFloatToHsla01(rgba.map(v => v / 255));
148
+ return [h * 360, s * 100, l * 100, a];
149
+ };
150
+
98
151
  export function hsv01ToRGBFloat([hue, sat, val]) {
99
152
  sat = clamp(sat, 0, 1);
100
153
  val = clamp(val, 0, 1);
@@ -103,6 +156,11 @@ export function hsv01ToRGBFloat([hue, sat, val]) {
103
156
  );
104
157
  }
105
158
 
159
+ export function hsva01ToRGBAFloat([hue, sat, val, alpha]) {
160
+ const rgb = hsv01ToRGBFloat([hue, sat, val]);
161
+ return [...rgb, alpha];
162
+ }
163
+
106
164
  const round3 = v => Math.round(v * 1000) / 1000;
107
165
 
108
166
  export function rgbFloatToHSV01([r, g, b]) {
@@ -120,8 +178,13 @@ export function rgbFloatToHSV01([r, g, b]) {
120
178
  ].map(round3);
121
179
  }
122
180
 
123
- window.hsv01ToRGBFloat = hsv01ToRGBFloat;
124
- window.rgbFloatToHSV01 = rgbFloatToHSV01;
181
+ export function rgbaFloatToHSVA01([r, g, b, a]) {
182
+ const hsv = rgbFloatToHSV01([r, g, b]);
183
+ return [...hsv, a];
184
+ }
185
+
186
+ // window.hsv01ToRGBFloat = hsv01ToRGBFloat;
187
+ // window.rgbFloatToHSV01 = rgbFloatToHSV01;
125
188
 
126
189
  // Yea, meh!
127
190
  export const hasAlpha = format => format.endsWith('a') || format.startsWith('hex8');
@@ -199,6 +262,13 @@ function fixHex6(v) {
199
262
  //return fix(v.trim());
200
263
  }
201
264
 
265
+ function fixHex8(v) {
266
+ return v.trim(v);
267
+ //const formatInfo = guessStringColorFormat(v.trim());
268
+ //const fix = formatInfo ? formatInfo.fix : v => v;
269
+ //return fix(v.trim());
270
+ }
271
+
202
272
  function hex6ToHex3(hex6) {
203
273
  return (hex6[1] === hex6[2] &&
204
274
  hex6[3] === hex6[4] &&
@@ -234,6 +304,19 @@ const strToRGBObject = (s) => {
234
304
  }
235
305
  };
236
306
 
307
+ const strToRGBAObject = (s) => {
308
+ try {
309
+ const json = s.replace(/([a-z])/g, '"$1"');
310
+ const rgba = JSON.parse(json);
311
+ if (Number.isNaN(rgba.r) || Number.isNaN(rgba.g) || Number.isNaN(rgba.b) || Number.isNaN(rgba.a)) {
312
+ throw new Error('not {r, g, b, a}');
313
+ }
314
+ return [true, rgba];
315
+ } catch (e) {
316
+ return [false];
317
+ }
318
+ };
319
+
237
320
  const strToCssRGB = s => {
238
321
  const m = cssRGBRegex.exec(s);
239
322
  if (!m) {
@@ -244,6 +327,16 @@ const strToCssRGB = s => {
244
327
  return [!outOfRange, `rgb(${v.join(', ')})`];
245
328
  };
246
329
 
330
+ const strToCssRGBA = s => {
331
+ const m = cssRGBARegex.exec(s);
332
+ if (!m) {
333
+ return [false];
334
+ }
335
+ const v = [m[1], m[2], m[3], m[4]].map((v, i) => i === 3 ? parseFloat(v) : parseInt(v));
336
+ const outOfRange = v.find(v => v > 255);
337
+ return [!outOfRange, `rgba(${v.join(', ')})`];
338
+ };
339
+
247
340
  const strToCssHSL = s => {
248
341
  const m = cssHSLRegex.exec(s);
249
342
  if (!m) {
@@ -254,9 +347,22 @@ const strToCssHSL = s => {
254
347
  return [!outOfRange, `hsl(${v[0]}, ${v[1]}%, ${v[2]}%)`];
255
348
  };
256
349
 
350
+ const strToCssHSLA = s => {
351
+ const m = cssHSLARegex.exec(s);
352
+ if (!m) {
353
+ return [false];
354
+ }
355
+ const v = [m[1], m[2], m[3], m[4]].map(v => parseFloat(v));
356
+ const outOfRange = v.find(v => Number.isNaN(v));
357
+ return [!outOfRange, `hsl(${v[0]} ${v[1]}% ${v[2]}% / ${v[3]})`];
358
+ };
359
+
257
360
  const rgbObjectToStr = rgb => {
258
361
  return `{r:${f3(rgb.r)}, g:${f3(rgb.g)}, b:${f3(rgb.b)}}`;
259
362
  };
363
+ const rgbaObjectToStr = rgba => {
364
+ return `{r:${f3(rgba.r)}, g:${f3(rgba.g)}, b:${f3(rgba.b)}}, a:${f3(rgba.a)}}`;
365
+ };
260
366
 
261
367
  const strTo3IntsRE = /^\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*$/;
262
368
  const strTo3Ints = s => {
@@ -269,6 +375,17 @@ const strTo3Ints = s => {
269
375
  return [!outOfRange, v];
270
376
  };
271
377
 
378
+ const strTo4IntsRE = /^\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*$/;
379
+ const strTo4Ints = s => {
380
+ const m = strTo4IntsRE.exec(s);
381
+ if (!m) {
382
+ return [false];
383
+ }
384
+ const v = [m[1], m[2], m[3], m[4]].map(v => parseInt(v));
385
+ const outOfRange = v.find(v => v > 255);
386
+ return [!outOfRange, v];
387
+ };
388
+
272
389
  const strTo3Floats = s => {
273
390
  const numbers = s.split(',').map(s => s.trim());
274
391
  const v = numbers.map(v => parseFloat(v));
@@ -280,6 +397,17 @@ const strTo3Floats = s => {
280
397
  return [badNdx < 0, v.map(v => f3(v))];
281
398
  };
282
399
 
400
+ const strTo4Floats = s => {
401
+ const numbers = s.split(',').map(s => s.trim());
402
+ const v = numbers.map(v => parseFloat(v));
403
+ if (v.length !== 4) {
404
+ return [false];
405
+ }
406
+ // Note: using isNaN not Number.isNaN
407
+ const badNdx = numbers.findIndex(v => isNaN(v));
408
+ return [badNdx < 0, v.map(v => f3(v))];
409
+ };
410
+
283
411
  const strToUint32RGBRegex = /^\s*(?:0x){0,1}([0-9a-z]{1,6})\s*$/i;
284
412
  const strToUint32RGB = s => {
285
413
  const m = strToUint32RGBRegex.exec(s);
@@ -289,8 +417,19 @@ const strToUint32RGB = s => {
289
417
  return [true, parseInt(m[1], 16)];
290
418
  };
291
419
 
292
- const hexRE = /^\s*#[a-f0-9]{6}\s*$|^\s*#[a-f0-9]{3}\s*$/i;
293
- const hexNoHashRE = /^\s*[a-f0-9]{6}\s*$/i;
420
+ const strToUint32RGBARegex = /^\s*(?:0x){0,1}([0-9a-z]{1,8})\s*$/i;
421
+ const strToUint32RGBA = s => {
422
+ const m = strToUint32RGBARegex.exec(s);
423
+ if (!m) {
424
+ return [false];
425
+ }
426
+ return [true, parseInt(m[1], 16)];
427
+ };
428
+
429
+ const hex6RE = /^\s*#[a-f0-9]{6}\s*$|^\s*#[a-f0-9]{3}\s*$/i;
430
+ const hexNoHash6RE = /^\s*[a-f0-9]{6}\s*$/i;
431
+ const hex8RE = /^\s*#[a-f0-9]{8}\s*$/i;
432
+ const hexNoHash8RE = /^\s*[a-f0-9]{8}\s*$/i;
294
433
 
295
434
  // For each format converter
296
435
  //
@@ -328,7 +467,17 @@ export const colorFormatConverters = {
328
467
  to: fixHex6,
329
468
  },
330
469
  text: {
331
- from: v => [hexRE.test(v), v.trim()],
470
+ from: v => [hex6RE.test(v), v.trim()],
471
+ to: v => v,
472
+ },
473
+ },
474
+ 'hex8': {
475
+ color: {
476
+ from: v => [true, v],
477
+ to: fixHex8,
478
+ },
479
+ text: {
480
+ from: v => [hex8RE.test(v), v.trim()],
332
481
  to: v => v,
333
482
  },
334
483
  },
@@ -338,7 +487,7 @@ export const colorFormatConverters = {
338
487
  to: hex3ToHex6,
339
488
  },
340
489
  text: {
341
- from: v => [hexRE.test(v), hex6ToHex3(v.trim())],
490
+ from: v => [hex6RE.test(v), hex6ToHex3(v.trim())],
342
491
  to: v => v,
343
492
  },
344
493
  },
@@ -348,7 +497,17 @@ export const colorFormatConverters = {
348
497
  to: v => `#${fixHex6(v)}`,
349
498
  },
350
499
  text: {
351
- from: v => [hexNoHashRE.test(v), v.trim()],
500
+ from: v => [hexNoHash6RE.test(v), v.trim()],
501
+ to: v => v,
502
+ },
503
+ },
504
+ 'hex8-no-hash': {
505
+ color: {
506
+ from: v => [true, v.substring(1)],
507
+ to: v => `#${fixHex8(v)}`,
508
+ },
509
+ text: {
510
+ from: v => [hexNoHash8RE.test(v), v.trim()],
352
511
  to: v => v,
353
512
  },
354
513
  },
@@ -358,7 +517,7 @@ export const colorFormatConverters = {
358
517
  to: hex3ToHex6,
359
518
  },
360
519
  text: {
361
- from: v => [hexNoHashRE.test(v), hex6ToHex3(v.trim())],
520
+ from: v => [hexNoHash6RE.test(v), hex6ToHex3(v.trim())],
362
521
  to: v => v,
363
522
  },
364
523
  },
@@ -372,6 +531,16 @@ export const colorFormatConverters = {
372
531
  to: v => `0x${v.toString(16).padStart(6, '0')}`,
373
532
  },
374
533
  },
534
+ 'uint32-rgba': {
535
+ color: {
536
+ from: v => [true, hexToUint32RGBA(v)],
537
+ to: uint32RGBAToHex,
538
+ },
539
+ text: {
540
+ from: v => strToUint32RGBA(v),
541
+ to: v => `0x${v.toString(16).padStart(8, '0')}`,
542
+ },
543
+ },
375
544
  'uint8-rgb': {
376
545
  color: {
377
546
  from: v => [true, hexToUint8RGB(v)],
@@ -382,6 +551,16 @@ export const colorFormatConverters = {
382
551
  to: v => v.join(', '),
383
552
  },
384
553
  },
554
+ 'uint8-rgba': {
555
+ color: {
556
+ from: v => [true, hexToUint8RGBA(v)],
557
+ to: uint8RGBAToHex,
558
+ },
559
+ text: {
560
+ from: strTo4Ints,
561
+ to: v => v.join(', '),
562
+ },
563
+ },
385
564
  'float-rgb': {
386
565
  color: {
387
566
  from: v => [true, hexToFloatRGB(v)],
@@ -393,6 +572,61 @@ export const colorFormatConverters = {
393
572
  to: v => Array.from(v).map(v => f3(v)).join(', '),
394
573
  },
395
574
  },
575
+ 'float-rgba': {
576
+ color: {
577
+ from: v => [true, hexToFloatRGBA(v)],
578
+ to: floatRGBAToHex,
579
+ },
580
+ text: {
581
+ from: strTo4Floats,
582
+ // need Array.from because map of Float32Array makes a Float32Array
583
+ to: v => Array.from(v).map(v => f3(v)).join(', '),
584
+ },
585
+ },
586
+ 'float-hsv': {
587
+ color: {
588
+ from: v => [true, rgbFloatToHSV01(hexToFloatRGB(v))],
589
+ to: v => hsv01ToRGBFloat(floatRGBToHex(v)),
590
+ },
591
+ text: {
592
+ from: strTo3Floats,
593
+ // need Array.from because map of Float32Array makes a Float32Array
594
+ to: v => Array.from(v).map(v => f3(v)).join(', '),
595
+ },
596
+ },
597
+ 'float-hsva': {
598
+ color: {
599
+ from: v => [true, rgbaFloatToHSVA01(hexToFloatRGB(v))],
600
+ to: v => hsva01ToRGBAFloat(floatRGBToHex(v)),
601
+ },
602
+ text: {
603
+ from: strTo4Floats,
604
+ // need Array.from because map of Float32Array makes a Float32Array
605
+ to: v => Array.from(v).map(v => f3(v)).join(', '),
606
+ },
607
+ },
608
+ //'float-hsl': {
609
+ // color: {
610
+ // from: v => [true, rgbFloatToHsl01(hexToFloatRGB(v))],
611
+ // to: v => hsl01ToRGBFloat(floatRGBToHex(v)),
612
+ // },
613
+ // text: {
614
+ // from: strTo3Floats,
615
+ // // need Array.from because map of Float32Array makes a Float32Array
616
+ // to: v => Array.from(v).map(v => f3(v)).join(', '),
617
+ // },
618
+ //},
619
+ //'float-hsla': {
620
+ // color: {
621
+ // from: v => [true, hexToFloatRGBA(v)],
622
+ // to: floatRGBAToHex,
623
+ // },
624
+ // text: {
625
+ // from: strTo4Floats,
626
+ // // need Array.from because map of Float32Array makes a Float32Array
627
+ // to: v => Array.from(v).map(v => f3(v)).join(', '),
628
+ // },
629
+ //},
396
630
  'object-rgb': {
397
631
  color: {
398
632
  from: v => [true, hexToObjectRGB(v)],
@@ -403,6 +637,16 @@ export const colorFormatConverters = {
403
637
  to: rgbObjectToStr,
404
638
  },
405
639
  },
640
+ 'object-rgba': {
641
+ color: {
642
+ from: v => [true, hexToObjectRGBA(v)],
643
+ to: objectRGBAToHex,
644
+ },
645
+ text: {
646
+ from: strToRGBAObject,
647
+ to: rgbaObjectToStr,
648
+ },
649
+ },
406
650
  'css-rgb': {
407
651
  color: {
408
652
  from: v => [true, hexToCssRGB(v)],
@@ -413,6 +657,16 @@ export const colorFormatConverters = {
413
657
  to: v => strToCssRGB(v)[1],
414
658
  },
415
659
  },
660
+ 'css-rgba': {
661
+ color: {
662
+ from: v => [true, hexToCssRGBA(v)],
663
+ to: cssRGBAToHex,
664
+ },
665
+ text: {
666
+ from: strToCssRGBA,
667
+ to: v => strToCssRGBA(v)[1],
668
+ },
669
+ },
416
670
  'css-hsl': {
417
671
  color: {
418
672
  from: v => [true, hexToCssHSL(v)],
@@ -423,4 +677,14 @@ export const colorFormatConverters = {
423
677
  to: v => strToCssHSL(v)[1],
424
678
  },
425
679
  },
680
+ 'css-hsla': {
681
+ color: {
682
+ from: v => [true, hexToCssHSLA(v)],
683
+ to: cssHSLAToHex,
684
+ },
685
+ text: {
686
+ from: strToCssHSLA,
687
+ to: v => strToCssHSLA(v)[1],
688
+ },
689
+ },
426
690
  };
package/src/libs/elem.js CHANGED
@@ -29,4 +29,9 @@ export function addElem(tag, parent, attrs = {}, children = []) {
29
29
  const elem = createElem(tag, attrs, children);
30
30
  parent.appendChild(elem);
31
31
  return elem;
32
- }
32
+ }
33
+
34
+ let nextId = 0;
35
+ export function getNewId() {
36
+ return `muigui-id-${nextId++}`;
37
+ }
@@ -0,0 +1,42 @@
1
+ const darkColors = {
2
+ main: '#ddd',
3
+ };
4
+ const lightColors = {
5
+ main: '#333',
6
+ };
7
+
8
+ const darkMatcher = window.matchMedia('(prefers-color-scheme: dark)');
9
+
10
+ let colors;
11
+ let isDarkMode;
12
+
13
+ function update() {
14
+ isDarkMode = darkMatcher.matches;
15
+ colors = isDarkMode ? darkColors : lightColors;
16
+ }
17
+ darkMatcher.addEventListener('change', update);
18
+ update();
19
+
20
+ export function graph(canvas, data, {
21
+ min = -1,
22
+ max = 1,
23
+ interval = 16,
24
+ color,
25
+ }) {
26
+ const ctx = canvas.getContext('2d');
27
+
28
+ function render() {
29
+ const {width, height} = canvas;
30
+ ctx.clearRect(0, 0, width, height);
31
+ ctx.beginPath();
32
+ const range = max - min;
33
+ for (let i = 0; i < data.length; ++i) {
34
+ const x = i * width / data.length;
35
+ const y = (data[i] - min) * height / range;
36
+ ctx.lineTo(x, y);
37
+ }
38
+ ctx.strokeStyle = color || colors.main;
39
+ ctx.stroke();
40
+ }
41
+ setInterval(render, interval);
42
+ }
@@ -10,7 +10,7 @@ const keyDirections = {
10
10
 
11
11
  // This probably needs to be global
12
12
  export function addKeyboardEvents(elem, {onDown = noop, onUp = noop}) {
13
- const keyDown = function(event) {
13
+ const keyDown = function (event) {
14
14
  const mult = event.shiftKey ? 10 : 1;
15
15
  const [dx, dy] = (keyDirections[event.key] || [0, 0]).map(v => v * mult);
16
16
  const fn = event.type === 'keydown' ? onDown : onUp;
@@ -25,7 +25,7 @@ export function addKeyboardEvents(elem, {onDown = noop, onUp = noop}) {
25
25
  elem.addEventListener('keydown', keyDown);
26
26
  elem.addEventListener('keyup', keyDown);
27
27
 
28
- return function() {
28
+ return function () {
29
29
  elem.removeEventListener('keydown', keyDown);
30
30
  elem.removeEventListener('keyup', keyDown);
31
31
  };
@@ -0,0 +1,5 @@
1
+ export function monitor(label, object, property, {interval = 200} = {}) {
2
+ setInterval(() => {
3
+ label.text(JSON.stringify(object[property], null, 2));
4
+ }, interval);
5
+ }
package/src/libs/touch.js CHANGED
@@ -17,7 +17,7 @@ export function computeRelativePosition(elem, event, start) {
17
17
 
18
18
  export function addTouchEvents(elem, {onDown = noop, onMove = noop, onUp = noop}) {
19
19
  let start;
20
- const pointerMove = function(event) {
20
+ const pointerMove = function (event) {
21
21
  const e = {
22
22
  type: 'move',
23
23
  ...computeRelativePosition(elem, event, start),
@@ -25,7 +25,7 @@ export function addTouchEvents(elem, {onDown = noop, onMove = noop, onUp = noop}
25
25
  onMove(e);
26
26
  };
27
27
 
28
- const pointerUp = function(event) {
28
+ const pointerUp = function (event) {
29
29
  elem.releasePointerCapture(event.pointerId);
30
30
  elem.removeEventListener('pointermove', pointerMove);
31
31
  elem.removeEventListener('pointerup', pointerUp);
@@ -35,7 +35,7 @@ export function addTouchEvents(elem, {onDown = noop, onMove = noop, onUp = noop}
35
35
  onUp('up');
36
36
  };
37
37
 
38
- const pointerDown = function(event) {
38
+ const pointerDown = function (event) {
39
39
  elem.addEventListener('pointermove', pointerMove);
40
40
  elem.addEventListener('pointerup', pointerUp);
41
41
  elem.setPointerCapture(event.pointerId);
@@ -50,7 +50,7 @@ export function addTouchEvents(elem, {onDown = noop, onMove = noop, onUp = noop}
50
50
 
51
51
  elem.addEventListener('pointerdown', pointerDown);
52
52
 
53
- return function() {
53
+ return function () {
54
54
  elem.removeEventListener('pointerdown', pointerDown);
55
55
  };
56
56
  }
package/src/libs/wheel.js CHANGED
@@ -1,6 +1,6 @@
1
1
  export function createWheelHelper() {
2
2
  let wheelAccum = 0;
3
- return function(e, step, wheelScale = 5) {
3
+ return function (e, step, wheelScale = 5) {
4
4
  wheelAccum -= e.deltaY * step / wheelScale;
5
5
  const wheelSteps = Math.floor(Math.abs(wheelAccum) / step) * Math.sign(wheelAccum);
6
6
  const delta = wheelSteps * step;
package/src/muigui.js CHANGED
@@ -61,6 +61,10 @@ export class GUIFolder extends Folder {
61
61
  addLabel(text) {
62
62
  return this.addController(new Label(text));
63
63
  }
64
+ addButton(name, fn) {
65
+ const o = {fn};
66
+ return this.add(o, 'fn').name(name);
67
+ }
64
68
  }
65
69
 
66
70
  class MuiguiElement extends HTMLElement {
@@ -73,7 +77,7 @@ class MuiguiElement extends HTMLElement {
73
77
  customElements.define('muigui-element', MuiguiElement);
74
78
 
75
79
  const baseStyleSheet = new CSSStyleSheet();
76
- baseStyleSheet.replaceSync(css.default);
80
+ //baseStyleSheet.replaceSync(css.default);
77
81
  const userStyleSheet = new CSSStyleSheet();
78
82
 
79
83
  function makeStyleSheetUpdater(styleSheet) {
@@ -100,6 +104,11 @@ function makeStyleSheetUpdater(styleSheet) {
100
104
  const updateBaseStyle = makeStyleSheetUpdater(baseStyleSheet);
101
105
  const updateUserStyle = makeStyleSheetUpdater(userStyleSheet);
102
106
 
107
+ function getTheme(name) {
108
+ const { include, css: cssStr } = css.themes[name];
109
+ return `${include.map(m => css[m]).join('\n')} : css.default}\n${cssStr || ''}`;
110
+ }
111
+
103
112
  export class GUI extends GUIFolder {
104
113
  static converters = converters;
105
114
  static mapRange = mapRange;
@@ -131,13 +140,14 @@ export class GUI extends GUIFolder {
131
140
  }
132
141
  if (parent) {
133
142
  const muiguiElement = createElem('muigui-element');
134
- muiguiElement.shadowRoot.adoptedStyleSheets = [baseStyleSheet, userStyleSheet, this.#localStyleSheet];
143
+ muiguiElement.shadowRoot.adoptedStyleSheets = [this.#localStyleSheet, baseStyleSheet, userStyleSheet];
135
144
  muiguiElement.shadow.appendChild(this.domElement);
136
145
  parent.appendChild(muiguiElement);
137
146
  }
138
147
  if (title) {
139
148
  this.title(title);
140
149
  }
150
+ this.#localStyleSheet.replaceSync(css.default);
141
151
  this.domElement.classList.add('muigui', 'muigui-colors');
142
152
  }
143
153
  setStyle(css) {
@@ -155,8 +165,11 @@ export class GUI extends GUIFolder {
155
165
  static getUserStyleSheet() {
156
166
  return userStyleSheet;
157
167
  }
168
+ setTheme(name) {
169
+ this.setStyle(getTheme(name));
170
+ }
158
171
  static setTheme(name) {
159
- GUI.setBaseStyles(`${css.default}\n${css.themes[name] || ''}`);
172
+ GUI.setBaseStyles(getTheme(name));
160
173
  }
161
174
  }
162
175