@projectwallace/css-analyzer 9.5.0 → 9.6.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,87 +1,10 @@
1
- import { n as isSupportsBrowserhack, t as isMediaBrowserhack } from "./atrules-CskmpIdJ.js";
2
- import { n as unquote, r as KeywordSet, t as endsWith } from "./string-utils-olNNcOlY.js";
3
- import { a as getComplexity, i as getCombinators, n as calculateForAST, o as isAccessibility, s as isPrefixed, t as calculate } from "./specificity-svLpcKkT.js";
4
- import { a as colorKeywords, i as colorFunctions, n as isValueReset, o as namedColors, r as keywords, s as systemColors, t as isIe9Hack } from "./browserhacks-eP_e1D5u.js";
5
- import { ATTRIBUTE_SELECTOR, AT_RULE, BLOCK, CONTAINER_QUERY, DECLARATION, DIMENSION, FUNCTION, HASH, IDENTIFIER, LAYER_NAME, MEDIA_FEATURE, NUMBER, OPERATOR, PSEUDO_CLASS_SELECTOR, PSEUDO_ELEMENT_SELECTOR, SELECTOR, SELECTOR_LIST, SKIP, STYLE_RULE, SUPPORTS_QUERY, TYPE_SELECTOR, URL, is_custom, is_vendor_prefixed, parse, str_starts_with, walk } from "@projectwallace/css-parser";
6
- //#region src/values/destructure-font-shorthand.ts
7
- const SYSTEM_FONTS = new KeywordSet([
8
- "caption",
9
- "icon",
10
- "menu",
11
- "message-box",
12
- "small-caption",
13
- "status-bar"
14
- ]);
15
- const SIZE_KEYWORDS = new KeywordSet([
16
- "xx-small",
17
- "x-small",
18
- "small",
19
- "medium",
20
- "large",
21
- "x-large",
22
- "xx-large",
23
- "xxx-large",
24
- "smaller",
25
- "larger"
26
- ]);
27
- const COMMA = 44;
28
- const SLASH = 47;
29
- function destructure(value, cb) {
30
- let font_family = [void 0, void 0];
31
- let font_size;
32
- let line_height;
33
- if (value.first_child.type === FUNCTION && value.first_child.name?.toLowerCase() === "var") return null;
34
- let prev;
35
- for (let node of value.children) {
36
- let next = node.next_sibling;
37
- if (node.type === IDENTIFIER && keywords.has(node.name)) cb({
38
- type: "keyword",
39
- value: node.name
40
- });
41
- if (next && next.type === OPERATOR && next.text.charCodeAt(0) === SLASH) {
42
- font_size = node.text;
43
- prev = node;
44
- continue;
45
- }
46
- if (prev?.type === OPERATOR && prev.text.charCodeAt(0) === SLASH) {
47
- line_height = node.text;
48
- prev = node;
49
- continue;
50
- }
51
- if (next?.type === OPERATOR && next.text.charCodeAt(0) === COMMA && !font_family[0]) {
52
- font_family[0] = node;
53
- if (!font_size && prev) font_size = prev.text;
54
- prev = node;
55
- continue;
56
- }
57
- if (node.next_sibling === null) {
58
- font_family[1] = node;
59
- if (!font_size && !font_family[0] && prev) font_size = prev.text;
60
- prev = node;
61
- continue;
62
- }
63
- if (node.type === NUMBER) {
64
- prev = node;
65
- continue;
66
- }
67
- if (node.type === IDENTIFIER) {
68
- let name = node.name;
69
- if (name && SIZE_KEYWORDS.has(name)) {
70
- font_size = name;
71
- prev = node;
72
- continue;
73
- }
74
- }
75
- prev = node;
76
- }
77
- let family = font_family[0] || font_family[1] ? value.text.substring((font_family?.[0] || font_family?.[1] || { start: value.start }).start - value.start, font_family[1] ? font_family[1].end - value.start : value.text.length) : null;
78
- return {
79
- font_size,
80
- line_height,
81
- font_family: family
82
- };
83
- }
84
- //#endregion
1
+ import { n as isSupportsBrowserhack, t as isMediaBrowserhack } from "./atrules-Bnb0wvNR.js";
2
+ import { t as KeywordSet } from "./keyword-set-qSyAMR9o.js";
3
+ import { n as unquote, t as endsWith } from "./string-utils-C97yyuqE.js";
4
+ import { a as getComplexity, i as getCombinators, n as calculateForAST, o as isAccessibility, s as isPrefixed, t as calculate } from "./specificity-DKo9lvB5.js";
5
+ import { a as keywords, c as namedColors, i as isValueReset, l as systemColors, n as SYSTEM_FONTS, o as colorFunctions, r as destructure, s as colorKeywords, t as isIe9Hack } from "./browserhacks-BtVwVqdU.js";
6
+ import { a as shorthand_properties, i as isHack, n as basename, r as border_radius_properties, t as SPACING_RESET_PROPERTIES } from "./property-utils-B3n9KkA9.js";
7
+ import { SKIP, is_atrule, is_atrule_prelude, is_attribute_selector, is_container_query, is_custom, is_declaration, is_dimension, is_function, is_hash, is_identifier, is_layer_name, is_media_feature, is_operator, is_pseudo_class_selector, is_pseudo_element_selector, is_raw, is_rule, is_selector, is_selector_list, is_supports_query, is_type_selector, is_url, is_vendor_prefixed, parse, str_starts_with, walk } from "@projectwallace/css-parser";
85
8
  //#region src/values/animations.ts
86
9
  const TIMING_KEYWORDS = new KeywordSet([
87
10
  "linear",
@@ -93,38 +16,35 @@ const TIMING_KEYWORDS = new KeywordSet([
93
16
  "step-end"
94
17
  ]);
95
18
  const TIMING_FUNCTION_VALUES = new KeywordSet(["cubic-bezier", "steps"]);
96
- function analyzeAnimation(children, cb) {
19
+ function analyzeAnimation(value, cb) {
97
20
  let durationFound = false;
98
- for (let child of children) {
99
- let type = child.type;
100
- let name = child.name;
101
- if (type === OPERATOR) durationFound = false;
102
- else if (type === DIMENSION && durationFound === false) {
103
- durationFound = true;
104
- cb({
105
- type: "duration",
106
- value: child
107
- });
108
- } else if (type === IDENTIFIER && name) {
109
- if (TIMING_KEYWORDS.has(name)) cb({
110
- type: "fn",
111
- value: child
112
- });
113
- else if (keywords.has(name)) cb({
114
- type: "keyword",
115
- value: child
116
- });
117
- } else if (type === FUNCTION && name && TIMING_FUNCTION_VALUES.has(name)) cb({
21
+ for (let node of value) if (is_operator(node)) durationFound = false;
22
+ else if (is_dimension(node) && durationFound === false) {
23
+ durationFound = true;
24
+ cb({
25
+ type: "duration",
26
+ value: node
27
+ });
28
+ } else if (is_identifier(node)) {
29
+ if (TIMING_KEYWORDS.has(node.name)) cb({
118
30
  type: "fn",
119
- value: child
31
+ value: node
120
32
  });
121
- }
33
+ else if (keywords.has(node.name)) cb({
34
+ type: "keyword",
35
+ value: node
36
+ });
37
+ } else if (is_function(node) && TIMING_FUNCTION_VALUES.has(node.name)) cb({
38
+ type: "fn",
39
+ value: node
40
+ });
122
41
  }
123
42
  //#endregion
124
43
  //#region src/values/vendor-prefix.ts
125
- function isValuePrefixed(node, on_value) {
126
- walk(node, function(child) {
127
- if (child.is_vendor_prefixed) on_value(child.name || child.text);
44
+ function isValuePrefixed(value, on_value) {
45
+ walk(value, function(node) {
46
+ if (node.is_vendor_prefixed) if (is_identifier(node) || is_function(node)) on_value(node.name);
47
+ else on_value(node.text);
128
48
  });
129
49
  }
130
50
  //#endregion
@@ -315,63 +235,11 @@ function getEmbedType(embed) {
315
235
  return embed.substring(start, semicolon);
316
236
  }
317
237
  //#endregion
318
- //#region src/properties/property-utils.ts
319
- const SPACING_RESET_PROPERTIES = new Set([
320
- "margin",
321
- "margin-block",
322
- "margin-inline",
323
- "margin-top",
324
- "margin-block-start",
325
- "margin-block-end",
326
- "margin-inline-end",
327
- "margin-inline-end",
328
- "margin-right",
329
- "margin-bottom",
330
- "margin-left",
331
- "padding",
332
- "padding-block",
333
- "padding-inline",
334
- "padding-top",
335
- "padding-right",
336
- "padding-bottom",
337
- "padding-left",
338
- "padding-block-start",
339
- "padding-block-end",
340
- "padding-inline-start",
341
- "padding-inline-end"
342
- ]);
343
- const border_radius_properties = new KeywordSet([
344
- "border-radius",
345
- "border-top-left-radius",
346
- "border-top-right-radius",
347
- "border-bottom-right-radius",
348
- "border-bottom-left-radius",
349
- "border-start-start-radius",
350
- "border-start-end-radius",
351
- "border-end-end-radius",
352
- "border-end-start-radius"
353
- ]);
354
- /**
355
- * @see https://github.com/csstree/csstree/blob/master/lib/utils/names.js#L69
356
- */
357
- function isHack(property) {
358
- if (is_custom(property) || is_vendor_prefixed(property)) return false;
359
- let code = property.charCodeAt(0);
360
- return code === 47 || code === 42 || code === 95 || code === 43 || code === 38 || code === 36 || code === 35;
361
- }
362
- /**
363
- * Get the normalized basename for a property with a vendor prefix
364
- * @returns The property name without vendor prefix
365
- */
366
- function basename(property) {
367
- if (is_custom(property)) return property;
368
- if (is_vendor_prefixed(property)) return property.slice(property.indexOf("-", 2) + 1).toLowerCase();
369
- if (isHack(property)) return property.slice(1).toLowerCase();
370
- return property.toLowerCase();
371
- }
372
- //#endregion
373
238
  //#region src/vendor-prefix.ts
374
- /** Kept for backwards compatibility */
239
+ /**
240
+ * Kept for backwards compatibility
241
+ * @deprecated Will be removed in next major version
242
+ * */
375
243
  function hasVendorPrefix(keyword) {
376
244
  return is_vendor_prefixed(keyword);
377
245
  }
@@ -466,6 +334,7 @@ function analyzeInternal(css, options, useLocations) {
466
334
  let propertyHacks = new Collection(useLocations);
467
335
  let propertyVendorPrefixes = new Collection(useLocations);
468
336
  let customProperties = new Collection(useLocations);
337
+ let shorthands = new Collection(useLocations);
469
338
  let propertyComplexities = new AggregateCollection();
470
339
  let valueComplexities = new AggregateCollection();
471
340
  let vendorPrefixedValues = new Collection(useLocations);
@@ -498,7 +367,7 @@ function analyzeInternal(css, options, useLocations) {
498
367
  walk(ast, (node, depth) => {
499
368
  if (keyframesDepth >= 0 && depth <= keyframesDepth) keyframesDepth = -1;
500
369
  let inKeyframes = keyframesDepth >= 0 && depth > keyframesDepth;
501
- if (node.type === AT_RULE) {
370
+ if (is_atrule(node)) {
502
371
  let atruleLoc = toLoc(node);
503
372
  atruleNesting.push(depth);
504
373
  uniqueAtruleNesting.p(depth, atruleLoc);
@@ -507,12 +376,12 @@ function analyzeInternal(css, options, useLocations) {
507
376
  if (normalized_name === "font-face") {
508
377
  let descriptors = Object.create(null);
509
378
  if (useLocations) fontfaces_with_loc.p(node.start, toLoc(node));
510
- let block = node.children.find((child) => child.type === BLOCK);
511
- for (let descriptor of block?.children || []) if (descriptor.type === DECLARATION && descriptor.value) descriptors[descriptor.property] = descriptor.value.text;
379
+ let block = node.block;
380
+ for (let descriptor of block?.children || []) if (is_declaration(descriptor) && descriptor.value) descriptors[descriptor.property] = descriptor.value.text;
512
381
  atRuleComplexities.push(1);
513
382
  fontfaces.push(descriptors);
514
383
  }
515
- if (node.prelude === null || node.prelude === void 0) {
384
+ if (!node.has_prelude) {
516
385
  if (normalized_name === "layer") {
517
386
  layers.p("<anonymous>", toLoc(node));
518
387
  atRuleComplexities.push(2);
@@ -542,14 +411,16 @@ function analyzeInternal(css, options, useLocations) {
542
411
  } else if (normalized_name === "layer") for (let layer of node.prelude.text.split(",").map((s) => s.trim())) layers.p(layer, toLoc(node));
543
412
  else if (normalized_name === "import") {
544
413
  imports.p(node.prelude.text, toLoc(node));
545
- if (node.prelude.has_children) {
546
- for (let child of node.prelude) if (child.type === SUPPORTS_QUERY && typeof child.value === "string") supports.p(child.value, toLoc(child));
547
- else if (child.type === LAYER_NAME && typeof child.value === "string") layers.p(child.value, toLoc(child));
414
+ if (is_atrule_prelude(node.prelude) && node.prelude.has_children) {
415
+ for (let child of node.prelude) if (is_supports_query(child)) supports.p(child.value, toLoc(child));
416
+ else if (is_layer_name(child) && child.value) layers.p(child.value, toLoc(child));
548
417
  }
549
418
  } else if (normalized_name === "container") {
550
- containers.p(node.prelude.text, toLoc(node));
551
- if (node.prelude.first_child?.type === CONTAINER_QUERY) {
552
- if (node.prelude.first_child.first_child?.type === IDENTIFIER) containerNames.p(node.prelude.first_child.first_child.text, toLoc(node));
419
+ let { prelude } = node;
420
+ containers.p(prelude.text, toLoc(node));
421
+ if (is_atrule_prelude(prelude) && is_container_query(prelude.first_child)) {
422
+ let container_name = prelude.first_child.first_child;
423
+ if (container_name && is_identifier(container_name)) containerNames.p(container_name.text, toLoc(node));
553
424
  }
554
425
  } else if (normalized_name === "property") registeredProperties.p(node.prelude.text, toLoc(node));
555
426
  else if (normalized_name === "function") {
@@ -560,19 +431,19 @@ function analyzeInternal(css, options, useLocations) {
560
431
  else if (normalized_name === "scope") scopes.p(node.prelude.text, toLoc(node));
561
432
  atRuleComplexities.push(complexity);
562
433
  }
563
- } else if (node.type === STYLE_RULE) if (inKeyframes && node.prelude) {
564
- if (node.prelude.type === SELECTOR_LIST && node.prelude.children.length > 0) for (let keyframe_selector of node.prelude.children) keyframeSelectors.p(keyframe_selector.text, toLoc(keyframe_selector));
434
+ } else if (is_rule(node)) if (inKeyframes && node.has_prelude) {
435
+ if (is_selector_list(node.prelude) && node.prelude.child_count > 0) for (let keyframe_selector of node.prelude) keyframeSelectors.p(keyframe_selector.text, toLoc(keyframe_selector));
565
436
  } else {
566
437
  totalRules++;
567
438
  if (node.block?.is_empty) emptyRules++;
568
439
  let numSelectors = 0;
569
440
  let numDeclarations = 0;
570
441
  let loc = toLoc(node);
571
- if (node.prelude) {
572
- for (const selector of node.prelude.children) if (selector.type === SELECTOR) numSelectors++;
442
+ if (node.has_prelude && is_selector_list(node.prelude)) {
443
+ for (const selector of node.prelude) if (is_selector(selector)) numSelectors++;
573
444
  }
574
445
  if (node.block) {
575
- for (const declaration of node.block.children) if (declaration.type === DECLARATION) numDeclarations++;
446
+ for (const declaration of node.block) if (is_declaration(declaration)) numDeclarations++;
576
447
  }
577
448
  ruleSizes.push(numSelectors + numDeclarations);
578
449
  uniqueRuleSize.p(numSelectors + numDeclarations, loc);
@@ -583,7 +454,7 @@ function analyzeInternal(css, options, useLocations) {
583
454
  ruleNesting.push(depth);
584
455
  uniqueRuleNesting.p(depth, loc);
585
456
  }
586
- else if (node.type === SELECTOR) {
457
+ else if (is_selector(node)) {
587
458
  if (inKeyframes) return SKIP;
588
459
  let loc = toLoc(node);
589
460
  selectorNesting.push(depth > 0 ? depth - 1 : 0);
@@ -599,10 +470,10 @@ function analyzeInternal(css, options, useLocations) {
599
470
  a11y.p(a11y_selector, loc);
600
471
  });
601
472
  walk(node, (child) => {
602
- if (child.type === ATTRIBUTE_SELECTOR) attributeSelectors.p(child.name?.toLowerCase() ?? "", loc);
603
- else if (child.type === TYPE_SELECTOR && child.name?.includes("-")) customElementSelectors.p(child.name.toLowerCase(), loc);
604
- else if (child.type === PSEUDO_CLASS_SELECTOR) pseudoClasses.p(child.name?.toLowerCase() ?? "", loc);
605
- else if (child.type === PSEUDO_ELEMENT_SELECTOR) pseudoElements.p(child.name?.toLowerCase() ?? "", loc);
473
+ if (is_attribute_selector(child)) attributeSelectors.p(child.name.toLowerCase(), loc);
474
+ else if (is_type_selector(child) && !child.name.startsWith("--") && child.name.includes("-")) customElementSelectors.p(child.name.toLowerCase(), loc);
475
+ else if (is_pseudo_class_selector(child)) pseudoClasses.p(child.name.toLowerCase(), loc);
476
+ else if (is_pseudo_element_selector(child)) pseudoElements.p(child.name.toLowerCase(), loc);
606
477
  });
607
478
  getCombinators(node, (combinator) => {
608
479
  let name = combinator.name.trim() === "" ? " " : combinator.name;
@@ -621,9 +492,10 @@ function analyzeInternal(css, options, useLocations) {
621
492
  specificities.push(specificity);
622
493
  if (sa > 0) ids.p(node.text, loc);
623
494
  return SKIP;
624
- } else if (node.type === DECLARATION) {
495
+ } else if (is_declaration(node)) {
625
496
  totalDeclarations++;
626
- uniqueDeclarations.add(node.text);
497
+ let declaration = node.text;
498
+ uniqueDeclarations.add(declaration);
627
499
  let loc = toLoc(node);
628
500
  let declarationDepth = depth > 0 ? depth - 1 : 0;
629
501
  declarationNesting.push(declarationDepth);
@@ -631,7 +503,7 @@ function analyzeInternal(css, options, useLocations) {
631
503
  let complexity = 1;
632
504
  if (node.is_important) {
633
505
  complexity++;
634
- if (!node.text.toLowerCase().includes("!important")) valueBrowserhacks.p("!ie", toLoc(node.value));
506
+ if (!declaration.toLowerCase().includes("!important")) valueBrowserhacks.p("!ie", toLoc(node.value));
635
507
  if (inKeyframes) {
636
508
  importantsInKeyframes++;
637
509
  complexity++;
@@ -656,8 +528,11 @@ function analyzeInternal(css, options, useLocations) {
656
528
  propertyHacks.p(property.charAt(0), propertyLoc);
657
529
  propertyComplexities.push(2);
658
530
  } else propertyComplexities.push(1);
531
+ if (shorthand_properties.has(normalizedProperty)) shorthands.p(property, propertyLoc);
659
532
  {
660
533
  let value = node.value;
534
+ if (!value) return;
535
+ if (is_raw(value)) return;
661
536
  let { text } = value;
662
537
  let valueLoc = toLoc(value);
663
538
  let complexity = 1;
@@ -686,8 +561,8 @@ function analyzeInternal(css, options, useLocations) {
686
561
  return SKIP;
687
562
  } else if (normalizedProperty === "font") {
688
563
  if (!SYSTEM_FONTS.has(text)) {
689
- let result = destructure(value, function(item) {
690
- if (item.type === "keyword") valueKeywords.p(item.value.toLowerCase(), valueLoc);
564
+ let result = destructure(value, function(keyword) {
565
+ valueKeywords.p(keyword.toLowerCase(), valueLoc);
691
566
  });
692
567
  if (!result) return SKIP;
693
568
  let { font_size, line_height, font_family } = result;
@@ -709,91 +584,86 @@ function analyzeInternal(css, options, useLocations) {
709
584
  if (normalized.includes("var(")) lineHeights.p(text, valueLoc);
710
585
  else lineHeights.p(normalized, valueLoc);
711
586
  } else if (normalizedProperty === "transition" || normalizedProperty === "animation") {
712
- analyzeAnimation(value.children, function(item) {
587
+ analyzeAnimation(value, function(item) {
713
588
  if (item.type === "fn") timingFunctions.p(item.value.text.toLowerCase(), valueLoc);
714
589
  else if (item.type === "duration") durations.p(item.value.text.toLowerCase(), valueLoc);
715
590
  else if (item.type === "keyword") valueKeywords.p(item.value.text.toLowerCase(), valueLoc);
716
591
  });
717
592
  return SKIP;
718
593
  } else if (normalizedProperty === "animation-duration" || normalizedProperty === "transition-duration") {
719
- for (let child of value.children) if (child.type !== OPERATOR) {
594
+ for (let child of value.children) if (!is_operator(child)) {
720
595
  let text = child.text;
721
596
  if (/var\(/i.test(text)) durations.p(text, valueLoc);
722
597
  else durations.p(text.toLowerCase(), valueLoc);
723
598
  }
724
599
  } else if (normalizedProperty === "transition-timing-function" || normalizedProperty === "animation-timing-function") {
725
- for (let child of value.children) if (child.type !== OPERATOR) timingFunctions.p(child.text, valueLoc);
600
+ for (let child of value.children) if (!is_operator(child)) timingFunctions.p(child.text, valueLoc);
726
601
  } else if (normalizedProperty === "container-name") containerNames.p(text, valueLoc);
727
602
  else if (normalizedProperty === "container") {
728
- if (value.first_child?.type === IDENTIFIER) containerNames.p(value.first_child.text, valueLoc);
603
+ if (value.first_child && is_identifier(value.first_child)) containerNames.p(value.first_child.text, valueLoc);
729
604
  } else if (border_radius_properties.has(normalizedProperty)) borderRadiuses.push(text, property, valueLoc);
730
605
  else if (normalizedProperty === "text-shadow") textShadows.p(text, valueLoc);
731
606
  else if (normalizedProperty === "box-shadow") boxShadows.p(text, valueLoc);
732
607
  let valueHasIe9Hack = isIe9Hack(value);
733
608
  walk(value, (valueNode) => {
734
- switch (valueNode.type) {
735
- case DIMENSION: {
736
- let unit = valueNode.unit?.toLowerCase() ?? "";
737
- let loc = toLoc(valueNode);
738
- units.push(unit, property, loc);
739
- return SKIP;
609
+ if (is_dimension(valueNode)) {
610
+ let unit = valueNode.unit.toLowerCase();
611
+ let loc = toLoc(valueNode);
612
+ units.push(unit, property, loc);
613
+ return SKIP;
614
+ }
615
+ if (is_hash(valueNode)) {
616
+ let hashText = valueNode.text;
617
+ if (!hashText || !hashText.startsWith("#")) return SKIP;
618
+ let hashValue = hashText.toLowerCase();
619
+ if (valueHasIe9Hack && !hashValue.endsWith("\\9")) hashValue = hashValue + "\\9";
620
+ let hexLength = hashValue.length - 1;
621
+ if (endsWith("\\9", hashValue)) hexLength = hexLength - 2;
622
+ let hashLoc = toLoc(valueNode);
623
+ colors.push(hashValue, property, hashLoc);
624
+ colorFormats.p(`hex` + hexLength, hashLoc);
625
+ return SKIP;
626
+ }
627
+ if (is_identifier(valueNode)) {
628
+ let identifierText = valueNode.text;
629
+ let identifierLoc = toLoc(valueNode);
630
+ if (normalizedProperty === "font" || normalizedProperty === "font-family") return SKIP;
631
+ if (keywords.has(identifierText)) valueKeywords.p(identifierText.toLowerCase(), identifierLoc);
632
+ let nodeLen = identifierText.length;
633
+ if (nodeLen > 20 || nodeLen < 3) return SKIP;
634
+ if (colorKeywords.has(identifierText)) {
635
+ let colorKeyword = identifierText.toLowerCase();
636
+ colors.push(colorKeyword, property, identifierLoc);
637
+ colorFormats.p(colorKeyword, identifierLoc);
638
+ return;
740
639
  }
741
- case HASH: {
742
- let hashText = valueNode.text;
743
- if (!hashText || !hashText.startsWith("#")) return SKIP;
744
- let hashValue = hashText.toLowerCase();
745
- if (valueHasIe9Hack && !hashValue.endsWith("\\9")) hashValue = hashValue + "\\9";
746
- let hexLength = hashValue.length - 1;
747
- if (endsWith("\\9", hashValue)) hexLength = hexLength - 2;
748
- let hashLoc = toLoc(valueNode);
749
- colors.push(hashValue, property, hashLoc);
750
- colorFormats.p(`hex` + hexLength, hashLoc);
751
- return SKIP;
640
+ if (namedColors.has(identifierText)) {
641
+ colors.push(identifierText.toLowerCase(), property, identifierLoc);
642
+ colorFormats.p("named", identifierLoc);
643
+ return;
752
644
  }
753
- case IDENTIFIER: {
754
- let identifierText = valueNode.text;
755
- let identifierLoc = toLoc(valueNode);
756
- if (normalizedProperty === "font" || normalizedProperty === "font-family") return SKIP;
757
- if (keywords.has(identifierText)) valueKeywords.p(identifierText.toLowerCase(), identifierLoc);
758
- let nodeLen = identifierText.length;
759
- if (nodeLen > 20 || nodeLen < 3) return SKIP;
760
- if (colorKeywords.has(identifierText)) {
761
- let colorKeyword = identifierText.toLowerCase();
762
- colors.push(colorKeyword, property, identifierLoc);
763
- colorFormats.p(colorKeyword, identifierLoc);
764
- return;
765
- }
766
- if (namedColors.has(identifierText)) {
767
- colors.push(identifierText.toLowerCase(), property, identifierLoc);
768
- colorFormats.p("named", identifierLoc);
769
- return;
770
- }
771
- if (systemColors.has(identifierText)) {
772
- colors.push(identifierText.toLowerCase(), property, identifierLoc);
773
- colorFormats.p("system", identifierLoc);
774
- return;
775
- }
776
- return SKIP;
645
+ if (systemColors.has(identifierText)) {
646
+ colors.push(identifierText.toLowerCase(), property, identifierLoc);
647
+ colorFormats.p("system", identifierLoc);
648
+ return;
777
649
  }
778
- case FUNCTION: {
779
- let funcName = valueNode.name;
780
- let funcLoc = toLoc(valueNode);
781
- if (colorFunctions.has(funcName)) {
782
- colors.push(valueNode.text, property, funcLoc);
783
- colorFormats.p(funcName.toLowerCase(), funcLoc);
784
- return;
785
- }
786
- if (endsWith("gradient", funcName)) {
787
- gradients.p(valueNode.text, funcLoc);
788
- return;
789
- }
650
+ return SKIP;
651
+ }
652
+ if (is_function(valueNode)) {
653
+ let funcName = valueNode.name;
654
+ let funcLoc = toLoc(valueNode);
655
+ if (colorFunctions.has(funcName)) {
656
+ colors.push(valueNode.text, property, funcLoc);
657
+ colorFormats.p(funcName.toLowerCase(), funcLoc);
658
+ return;
790
659
  }
660
+ if (endsWith("gradient", funcName)) gradients.p(valueNode.text, funcLoc);
791
661
  }
792
662
  });
793
663
  }
794
- } else if (node.type === URL) {
664
+ } else if (is_url(node)) {
795
665
  let { value } = node;
796
- let embed = unquote(value || "");
666
+ let embed = unquote(value ?? "");
797
667
  if (str_starts_with(embed, "data:")) {
798
668
  let size = embed.length;
799
669
  let type = getEmbedType(embed);
@@ -820,8 +690,8 @@ function analyzeInternal(css, options, useLocations) {
820
690
  embedTypes.unique.set(type, item);
821
691
  }
822
692
  }
823
- } else if (node.type === MEDIA_FEATURE) {
824
- if (node.property) mediaFeatures.p(node.property.toLowerCase(), toLoc(node));
693
+ } else if (is_media_feature(node)) {
694
+ mediaFeatures.p(node.property?.toLowerCase(), toLoc(node));
825
695
  return SKIP;
826
696
  }
827
697
  });
@@ -962,6 +832,7 @@ function analyzeInternal(css, options, useLocations) {
962
832
  ratio: ratio(customProperties.size(), properties.size()),
963
833
  importants: assign(importantCustomProperties.c(), { ratio: ratio(importantCustomProperties.size(), customProperties.size()) })
964
834
  }),
835
+ shorthands: assign(shorthands.c(), { ratio: ratio(shorthands.size(), properties.size()) }),
965
836
  browserhacks: assign(propertyHacks.c(), { ratio: ratio(propertyHacks.size(), properties.size()) }),
966
837
  complexity: propertyComplexity
967
838
  }),
@@ -0,0 +1,11 @@
1
+ //#region src/keyword-set.d.ts
2
+ /**
3
+ * @description A Set-like construct to search CSS keywords in a case-insensitive way
4
+ */
5
+ declare class KeywordSet {
6
+ set: Set<string>;
7
+ constructor(items: Lowercase<string>[]);
8
+ has(item: string): boolean;
9
+ }
10
+ //#endregion
11
+ export { KeywordSet as t };
@@ -0,0 +1,16 @@
1
+ //#region src/keyword-set.ts
2
+ /**
3
+ * @description A Set-like construct to search CSS keywords in a case-insensitive way
4
+ */
5
+ var KeywordSet = class {
6
+ set;
7
+ constructor(items) {
8
+ /** @type {Set<string>} */
9
+ this.set = new Set(items);
10
+ }
11
+ has(item) {
12
+ return this.set.has(item.toLowerCase());
13
+ }
14
+ };
15
+ //#endregion
16
+ export { KeywordSet as t };
@@ -0,0 +1,2 @@
1
+ import { a as shorthand_properties, i as isHack, n as basename, r as border_radius_properties, t as SPACING_RESET_PROPERTIES } from "../property-utils-MKX6iGvg.js";
2
+ export { basename, border_radius_properties, isHack as is_property_hack, shorthand_properties, SPACING_RESET_PROPERTIES as spacing_reset_properties };
@@ -0,0 +1,2 @@
1
+ import { a as shorthand_properties, i as isHack, n as basename, r as border_radius_properties, t as SPACING_RESET_PROPERTIES } from "../property-utils-B3n9KkA9.js";
2
+ export { basename, border_radius_properties, isHack as is_property_hack, shorthand_properties, SPACING_RESET_PROPERTIES as spacing_reset_properties };