@5even7/dlc-ui 0.2.18 → 0.2.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/progress.cjs CHANGED
@@ -175,9 +175,9 @@ function _unsupportedIterableToArray(r, a) {
175
175
  }
176
176
  }
177
177
 
178
- /**
179
- * Tiny event emitter. Accepts any event name so the API stays open for
180
- * future events (hover, click, custom) without breaking changes.
178
+ /**
179
+ * Tiny event emitter. Accepts any event name so the API stays open for
180
+ * future events (hover, click, custom) without breaking changes.
181
181
  */
182
182
  function createEmitter() {
183
183
  // Plain object storage (no Map/Set) so the legacy build has no API
@@ -227,9 +227,9 @@ function createEmitter() {
227
227
 
228
228
  var UNIT_PATTERN = /^[\d.]+(?:px|%|vw|vh|vmin|vmax|em|rem)$/;
229
229
 
230
- /**
231
- * Normalize a size option to a CSS length string.
232
- * Accepts numbers (treated as px) or strings with px/%, vw/vh/vmin/vmax, em/rem.
230
+ /**
231
+ * Normalize a size option to a CSS length string.
232
+ * Accepts numbers (treated as px) or strings with px/%, vw/vh/vmin/vmax, em/rem.
233
233
  */
234
234
  function parseSize(value) {
235
235
  if (typeof value === 'number') {
@@ -275,10 +275,10 @@ function effectiveDprCap(quality) {
275
275
  return Math.max(0.5, dprCapFor(quality) * normalizedScale);
276
276
  }
277
277
 
278
- /**
279
- * Merge defaults < preset < user. Unknown user keys are preserved so the
280
- * component API can grow (new props, cssVars, callbacks) without a breaking
281
- * change.
278
+ /**
279
+ * Merge defaults < preset < user. Unknown user keys are preserved so the
280
+ * component API can grow (new props, cssVars, callbacks) without a breaking
281
+ * change.
282
282
  */
283
283
  function normalizeOptions(defaults, preset, user) {
284
284
  // undefined means "not provided" (e.g. Vue $props with unset props):
@@ -296,9 +296,9 @@ function normalizeOptions(defaults, preset, user) {
296
296
  return _objectSpread2(_objectSpread2(_objectSpread2({}, defaults), presetOptions), userOptions);
297
297
  }
298
298
 
299
- /**
300
- * 公共色板:NC-01~NC-06 的四色组(底色 / 主色 / 辅色 / 高光色)。
301
- * Capsule 预置与 dlc-color 等组件共用,新增色板只改这里。
299
+ /**
300
+ * 公共色板:NC-01~NC-06 的四色组(底色 / 主色 / 辅色 / 高光色)。
301
+ * Capsule 预置与 dlc-color 等组件共用,新增色板只改这里。
302
302
  */
303
303
  var PALETTES$1 = {
304
304
  original: ['#FFF3EA', '#F5B27A', '#F67BC6', '#A978E8'],
@@ -309,9 +309,9 @@ var PALETTES$1 = {
309
309
  plus: ['#FFF0E6', '#F6C26B', '#F98A64', '#E86D74']
310
310
  };
311
311
 
312
- /**
313
- * Capsule 预置:仅星云材质 NC-01~NC-06(NC-07~09 aurora 已移除)。
314
- * 颜色引用公共色板,seed/speed 决定形态与流速。
312
+ /**
313
+ * Capsule 预置:仅星云材质 NC-01~NC-06(NC-07~09 aurora 已移除)。
314
+ * 颜色引用公共色板,seed/speed 决定形态与流速。
315
315
  */
316
316
  var CAPSULE_PRESETS = [{
317
317
  id: 'original',
@@ -473,10 +473,16 @@ var COPY = {
473
473
 
474
474
  /**
475
475
  * Color helpers. `normalizeColor` converts any supported CSS color
476
- * (hex / named / rgb() / rgba()) into a 6-digit hex string, so renderers can
477
- * keep working with #rrggbb only. rgba() alpha is intentionally dropped:
478
- * the WebGL shader has no per-color alpha channel, and the component is
479
- * opaque by design — use component-level `opacity` for transparency.
476
+ * (hex / named / rgb() / rgba() / hsl() / hsla()) into a 6-digit hex string,
477
+ * so renderers can keep working with #rrggbb only. rgba()/hsla() alpha is
478
+ * intentionally dropped: the WebGL shader has no per-color alpha channel, and
479
+ * the component is opaque by design — use component-level `opacity` for
480
+ * transparency.
481
+ *
482
+ * `normalizeColorWithAlpha` keeps the alpha channel: it returns a 6-digit hex
483
+ * when alpha is 1, an 8-digit #rrggbbaa hex when alpha < 1, and the literal
484
+ * string 'transparent' for `transparent`. Use it for renderers (e.g. SVG)
485
+ * that can represent per-color transparency.
480
486
  */
481
487
 
482
488
  var NAMED_COLORS = {
@@ -632,48 +638,161 @@ var NAMED_COLORS = {
632
638
  function clampChannel(value) {
633
639
  return Math.min(255, Math.max(0, Math.round(value)));
634
640
  }
635
- function normalizeRgbArgs(args) {
636
- var parts = args.split(/[,\s/]+/).filter(Boolean);
641
+ function clampUnit(value) {
642
+ return Math.min(1, Math.max(0, value));
643
+ }
644
+ function hexPair(value) {
645
+ var text = clampChannel(value).toString(16);
646
+ return text.length === 1 ? "0".concat(text) : text;
647
+ }
648
+
649
+ /**
650
+ * Parse the argument list of rgb()/rgba()/hsl()/hsla() (comma syntax or
651
+ * modern space + slash syntax). Returns { parts, alpha } where alpha is 1 when
652
+ * omitted. Returns null when the argument list cannot be parsed.
653
+ */
654
+ function parseFunctionArgs(args) {
655
+ var parts = args.split(/[,\s]+/).map(function (part) {
656
+ return part.trim();
657
+ }).filter(function (part) {
658
+ return part !== '' && part !== '/';
659
+ });
637
660
  if (parts.length < 3) return null;
638
- var to255 = function to255(value) {
639
- if (typeof value !== 'string' || !value) return null;
640
- if (value.charAt(value.length - 1) === '%') return clampChannel(parseFloat(value) / 100 * 255);
641
- var number = Number(value);
642
- return Number.isFinite(number) ? clampChannel(number) : null;
643
- };
644
- var red = to255(parts[0]);
645
- var green = to255(parts[1]);
646
- var blue = to255(parts[2]);
647
- if (red === null || green === null || blue === null) return null;
648
- var hex = function hex(n) {
649
- var text = n.toString(16);
650
- return text.length === 1 ? "0".concat(text) : text;
661
+ var alpha = 1;
662
+ if (parts.length >= 4) {
663
+ var alphaText = parts.pop().trim();
664
+ if (alphaText.endsWith('%')) {
665
+ var percent = parseFloat(alphaText);
666
+ if (!Number.isFinite(percent)) return null;
667
+ alpha = clampUnit(percent / 100);
668
+ } else {
669
+ var number = Number(alphaText);
670
+ if (!Number.isFinite(number)) return null;
671
+ alpha = clampUnit(number);
672
+ }
673
+ }
674
+ return {
675
+ parts: parts,
676
+ alpha: alpha
651
677
  };
652
- return "#".concat(hex(red)).concat(hex(green)).concat(hex(blue));
678
+ }
679
+ function parseChannel(value) {
680
+ if (typeof value !== 'string' || value === '') return null;
681
+ var text = value.trim();
682
+ if (text.endsWith('%')) return clampChannel(parseFloat(text) / 100 * 255);
683
+ var number = Number(text);
684
+ return Number.isFinite(number) ? clampChannel(number) : null;
685
+ }
686
+ function parsePercent(value) {
687
+ if (typeof value !== 'string' || value === '') return null;
688
+ var text = value.trim();
689
+ if (!text.endsWith('%')) return null;
690
+ var number = parseFloat(text);
691
+ return Number.isFinite(number) ? Math.min(100, Math.max(0, number)) : null;
692
+ }
693
+ function parseHue(value) {
694
+ if (typeof value !== 'string' || value === '') return null;
695
+ var number = parseFloat(value);
696
+ return Number.isFinite(number) ? number : null;
697
+ }
698
+
699
+ /** Standard HSL -> RGB. h in degrees, s/l in 0..100, returns r/g/b in 0..255. */
700
+ function hslToRgb(h, s, l) {
701
+ var hue = (h % 360 + 360) % 360 / 360;
702
+ var saturation = s / 100;
703
+ var lightness = l / 100;
704
+ var chroma = (1 - Math.abs(2 * lightness - 1)) * saturation;
705
+ var section = hue * 6;
706
+ var x = chroma * (1 - Math.abs(section % 2 - 1));
707
+ var red = 0;
708
+ var green = 0;
709
+ var blue = 0;
710
+ if (section < 1) {
711
+ red = chroma;
712
+ green = x;
713
+ } else if (section < 2) {
714
+ red = x;
715
+ green = chroma;
716
+ } else if (section < 3) {
717
+ green = chroma;
718
+ blue = x;
719
+ } else if (section < 4) {
720
+ green = x;
721
+ blue = chroma;
722
+ } else if (section < 5) {
723
+ red = x;
724
+ blue = chroma;
725
+ } else {
726
+ red = chroma;
727
+ blue = x;
728
+ }
729
+ var match = lightness - chroma / 2;
730
+ return [Math.round((red + match) * 255), Math.round((green + match) * 255), Math.round((blue + match) * 255)];
653
731
  }
654
732
 
655
733
  /**
656
- * Convert any supported CSS color into `#rrggbb`. Returns null when the
657
- * value cannot be parsed. Supports: #rgb / #rrggbb (case-insensitive),
658
- * CSS named colors, rgb() / rgba() with comma or modern space syntax,
659
- * including percentages. Alpha in rgba() is ignored.
734
+ * Parse any supported CSS color. When keepAlpha is true the alpha channel is
735
+ * preserved (8-digit hex for alpha < 1); when false it is dropped. 'transparent'
736
+ * is only preserved when keepAlpha is true.
660
737
  */
661
- function normalizeColor(value) {
738
+ function parseColor(value, keepAlpha) {
662
739
  if (typeof value !== 'string') return null;
663
740
  var input = value.trim();
664
741
  if (!input) return null;
665
742
  var lower = input.toLowerCase();
666
743
  if (NAMED_COLORS[lower]) return NAMED_COLORS[lower];
667
- if (/^#([0-9a-f]{3}|[0-9a-f]{6})$/i.test(input)) {
668
- var hex = input.slice(1).toLowerCase();
669
- if (hex.length === 3) return "#".concat(hex.split('').map(function (c) {
670
- return c + c;
671
- }).join(''));
672
- return "#".concat(hex);
744
+ // #rgb / #rgba / #rrggbb / #rrggbbaa,以及无 # 前缀的 6/8 位 hex(dicebear 习惯)
745
+ var hexMatch = input.match(/^#?([0-9a-f]{3,8})$/i);
746
+ if (hexMatch) {
747
+ var _hex = hexMatch[1].toLowerCase();
748
+ if (_hex.length === 3 || _hex.length === 4) {
749
+ _hex = _hex.split('').map(function (c) {
750
+ return c + c;
751
+ }).join('');
752
+ }
753
+ return "#".concat(_hex.slice(0, 6));
673
754
  }
674
- var match = input.match(/^rgba?\((.*)\)$/i);
675
- if (match) return normalizeRgbArgs(match[1]);
676
- return null;
755
+ var funcMatch = input.match(/^(rgba?|hsla?)\(([^)]*)\)$/i);
756
+ if (!funcMatch) return null;
757
+ var kind = funcMatch[1].toLowerCase();
758
+ var parsed = parseFunctionArgs(funcMatch[2]);
759
+ if (!parsed) return null;
760
+ var parts = parsed.parts;
761
+ parsed.alpha;
762
+ var red;
763
+ var green;
764
+ var blue;
765
+ if (kind === 'rgb' || kind === 'rgba') {
766
+ if (parts.length !== 3) return null;
767
+ red = parseChannel(parts[0]);
768
+ green = parseChannel(parts[1]);
769
+ blue = parseChannel(parts[2]);
770
+ if (red === null || green === null || blue === null) return null;
771
+ } else {
772
+ if (parts.length !== 3) return null;
773
+ var hue = parseHue(parts[0]);
774
+ var saturation = parsePercent(parts[1]);
775
+ var lightness = parsePercent(parts[2]);
776
+ if (hue === null || saturation === null || lightness === null) return null;
777
+ var _hslToRgb = hslToRgb(hue, saturation, lightness);
778
+ var _hslToRgb2 = _slicedToArray(_hslToRgb, 3);
779
+ red = _hslToRgb2[0];
780
+ green = _hslToRgb2[1];
781
+ blue = _hslToRgb2[2];
782
+ }
783
+ var hex = "#".concat(hexPair(red)).concat(hexPair(green)).concat(hexPair(blue));
784
+ return hex;
785
+ }
786
+
787
+ /**
788
+ * Convert any supported CSS color into `#rrggbb`. Returns null when the
789
+ * value cannot be parsed. Supports: #rgb / #rgba / #rrggbb / #rrggbbaa
790
+ * (case-insensitive), bare 6/8-digit hex, CSS named colors, rgb() / rgba() /
791
+ * hsl() / hsla() with comma or modern space syntax, including percentages.
792
+ * Alpha is ignored.
793
+ */
794
+ function normalizeColor(value) {
795
+ return parseColor(value);
677
796
  }
678
797
  function hexToRgba(color) {
679
798
  var alpha = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 1;
@@ -686,10 +805,10 @@ function hexToRgba(color) {
686
805
  return "rgba(".concat(red, ", ").concat(green, ", ").concat(blue, ", ").concat(alpha, ")");
687
806
  }
688
807
 
689
- /**
690
- * Document-level shared rAF scheduler. Every component instance subscribes
691
- * its own frame callback; the whole page runs ONE animation loop (like the
692
- * original demo), which avoids jank from many competing rAF loops.
808
+ /**
809
+ * Document-level shared rAF scheduler. Every component instance subscribes
810
+ * its own frame callback; the whole page runs ONE animation loop (like the
811
+ * original demo), which avoids jank from many competing rAF loops.
693
812
  */
694
813
  var subscribers = [];
695
814
  var running = false;
@@ -766,9 +885,9 @@ function subscribeScheduler(onFrame, isPaused) {
766
885
  };
767
886
  }
768
887
 
769
- /**
770
- * Gates drawing on "element intersects viewport AND the page tab is visible".
771
- * Falls back to always-visible when IntersectionObserver is unavailable.
888
+ /**
889
+ * Gates drawing on "element intersects viewport AND the page tab is visible".
890
+ * Falls back to always-visible when IntersectionObserver is unavailable.
772
891
  */
773
892
  function createVisibilityGuard(element) {
774
893
  var onChange = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : null;
@@ -1195,15 +1314,15 @@ function getProgressReferenceAtlas(id) {
1195
1314
  return CACHE[id];
1196
1315
  }
1197
1316
 
1198
- /**
1199
- * Attach a WebGL2 fluid overlay to a progress capsule root.
1200
- *
1201
- * @param {object} params
1202
- * @param {HTMLElement} params.root progress capsule root element
1203
- * @param {HTMLCanvasElement} params.canvas 2D fallback canvas (kept beneath)
1204
- * @param {object} params.preset progress preset
1205
- * @param {() => number} params.getProgress reads the current progress value
1206
- * @returns {{ update(flowTime: number): void, setDprCap(cap: number): void, dispose(): void } | null}
1317
+ /**
1318
+ * Attach a WebGL2 fluid overlay to a progress capsule root.
1319
+ *
1320
+ * @param {object} params
1321
+ * @param {HTMLElement} params.root progress capsule root element
1322
+ * @param {HTMLCanvasElement} params.canvas 2D fallback canvas (kept beneath)
1323
+ * @param {object} params.preset progress preset
1324
+ * @param {() => number} params.getProgress reads the current progress value
1325
+ * @returns {{ update(flowTime: number): void, setDprCap(cap: number): void, dispose(): void } | null}
1207
1326
  */
1208
1327
  function attachProgressFlowOverlay(_ref) {
1209
1328
  var root = _ref.root,
@@ -2083,16 +2202,16 @@ var ProgressCapsuleController = /*#__PURE__*/function () {
2083
2202
  }]);
2084
2203
  }();
2085
2204
 
2086
- /**
2087
- * Mount a fluid progress capsule into `container`.
2088
- *
2089
- * Options: preset (literary name), width, height, value/modelValue, min, max,
2090
- * step, draggable, keyboard, direction, precision/formatValue, colors,
2091
- * edgeStyle, textRatio (0-100, text region
2092
- * width in percent), text (HTML string or DOM nodes for the text slot),
2093
- * colorContent (HTML string or DOM nodes for the color slot),
2094
- * showValue (show/hide the right-side percentage), quality, renderScale,
2095
- * powerPreference, fps, paused/static, respectReducedMotion, cssVars.
2205
+ /**
2206
+ * Mount a fluid progress capsule into `container`.
2207
+ *
2208
+ * Options: preset (literary name), width, height, value/modelValue, min, max,
2209
+ * step, draggable, keyboard, direction, precision/formatValue, colors,
2210
+ * edgeStyle, textRatio (0-100, text region
2211
+ * width in percent), text (HTML string or DOM nodes for the text slot),
2212
+ * colorContent (HTML string or DOM nodes for the color slot),
2213
+ * showValue (show/hide the right-side percentage), quality, renderScale,
2214
+ * powerPreference, fps, paused/static, respectReducedMotion, cssVars.
2096
2215
  */
2097
2216
  function createProgressCapsule(container) {
2098
2217
  var _options$preset, _merged$min, _merged$max;