css-has-pseudo 0.6.0 → 0.10.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,21 @@
1
1
  # Changes to CSS Has Pseudo
2
2
 
3
+ ### 0.10.0 (December 11, 2018)
4
+
5
+ - Fixed an issue where inaccessible rules would crash the library
6
+
7
+ ### 0.9.0 (November 26, 2018)
8
+
9
+ - Improved CLI usage
10
+
11
+ ### 0.8.0 (November 26, 2018)
12
+
13
+ - Fixed an issue where attribute names were not being properly encoded
14
+
15
+ ### 0.7.0 (November 25, 2018)
16
+
17
+ - Replaced `setImmediate` with `requestAnimationFrame` for future compatibility
18
+
3
19
  ### 0.6.0 (November 25, 2018)
4
20
 
5
21
  - Fixed an issue where nested rules were not supported
package/browser.js CHANGED
@@ -1 +1 @@
1
- function cssHasPseudo(n){var t=[],e=n.createElement("x");function r(){t.forEach(function(t){var r=[];Array.prototype.forEach.call(n.querySelectorAll(t.n),function(u){var i=Array.prototype.indexOf.call(u.parentNode.children,u)+1,o=t.t.map(function(n){return t.n+":nth-child("+i+") "+n}).join(),c=u.parentNode.querySelector(o);(t.e?!c:c)&&(r.push(u),e.innerHTML="<x "+t.r+">",u.setAttributeNode(e.children[0].attributes[0].cloneNode()),n.documentElement.style.zoom=1,n.documentElement.style.zoom=null)}),t.u.forEach(function(e){-1===r.indexOf(e)&&(e.removeAttribute(t.r),n.documentElement.style.zoom=1,n.documentElement.style.zoom=null)}),t.u=r})}function u(n){Array.prototype.forEach.call(n.cssRules||[],function(n){if(n.selectorText){var e=decodeURIComponent(n.selectorText.replace(/\\(.)/g,"$1")).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);if(e){var r=":"+(e[2]?"not-":"")+"has("+e[3].replace(/%3A/g,":").replace(/%5B/g,"[").replace(/%5D/g,"]").replace(/%2C/g,",")+")";t.push({i:n,n:e[1],e:e[2],t:e[3].split(/\s*,\s*/),r:r,u:[]})}}else u(n)})}Array.prototype.forEach.call(n.styleSheets,u),r(),new MutationObserver(function(e){e.forEach(function(e){Array.prototype.forEach.call(e.addedNodes||[],function(n){1===n.nodeType&&n.sheet&&u(n.sheet)}),Array.prototype.push.apply(t,t.splice(0).filter(function(t){return t.i.parentStyleSheet&&t.i.parentStyleSheet.ownerNode&&n.documentElement.contains(t.i.parentStyleSheet.ownerNode)})),r()})}).observe(n,{childList:!0,subtree:!0}),n.addEventListener("focus",function(){return setImmediate(r)},!0),n.addEventListener("blur",function(){return setImmediate(r)},!0),n.addEventListener("input",function(){return setImmediate(r)})}
1
+ function cssHasPseudo(n){var t=[],e=n.createElement("x");function o(){requestAnimationFrame(function(){t.forEach(function(t){var o=[];[].forEach.call(n.querySelectorAll(t.n),function(u){var i=[].indexOf.call(u.parentNode.children,u)+1,c=t.t.map(function(n){return t.n+":nth-child("+i+") "+n}).join(),r=u.parentNode.querySelector(c);(t.e?!r:r)&&(o.push(u),e.innerHTML="<x "+t.o+">",u.setAttributeNode(e.children[0].attributes[0].cloneNode()),n.documentElement.style.zoom=1,n.documentElement.style.zoom=null)}),t.u.forEach(function(e){-1===o.indexOf(e)&&(e.removeAttribute(t.o),n.documentElement.style.zoom=1,n.documentElement.style.zoom=null)}),t.u=o})})}function u(n){try{[].forEach.call(n.cssRules||[],function(n){if(n.selectorText){var e=decodeURIComponent(n.selectorText.replace(/\\(.)/g,"$1")).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);if(e){var o=":"+(e[2]?"not-":"")+"has("+encodeURIComponent(e[3]).replace(/%3A/g,":").replace(/%5B/g,"[").replace(/%5D/g,"]").replace(/%2C/g,",")+")";t.push({i:n,n:e[1],e:e[2],t:e[3].split(/\s*,\s*/),o:o,u:[]})}}else u(n)})}catch(n){}}[].forEach.call(n.styleSheets,u),o(),new MutationObserver(function(e){e.forEach(function(e){[].forEach.call(e.addedNodes||[],function(n){1===n.nodeType&&n.sheet&&u(n.sheet)}),[].push.apply(t,t.splice(0).filter(function(t){return t.i.parentStyleSheet&&t.i.parentStyleSheet.ownerNode&&n.documentElement.contains(t.i.parentStyleSheet.ownerNode)})),o()})}).observe(n,{childList:!0,subtree:!0}),n.addEventListener("focus",o,!0),n.addEventListener("blur",o,!0),n.addEventListener("input",o)}
package/cli.js CHANGED
@@ -45,12 +45,6 @@ function checkIfParentIsNot(selector) {
45
45
  return Object(Object(selector.parent).parent).type === 'pseudo' && selector.parent.parent.value === ':not';
46
46
  }
47
47
 
48
- if (process.argv.length < 3) {
49
- console.log(['CSS Has Pseudo\n', ' Transforms CSS with :has {}\n', 'Usage:\n', ' css-has-pseudo source.css transformed.css', ' css-has-pseudo --in=source.css --out=transformed.css --opts={}', ' echo "body:has(:focus) {}" | css-has-pseudo\n'].join('\n'));
50
- process.exit(0);
51
- } // get process and plugin options from the command line
52
-
53
-
54
48
  const fileRegExp = /^[\w\/.]+$/;
55
49
  const argRegExp = /^--(\w+)=("|')?(.+)\2$/;
56
50
  const relaxedJsonPropRegExp = /(['"])?([a-z0-9A-Z_]+)(['"])?:/g;
@@ -77,6 +71,11 @@ const argo = process.argv.slice(2).reduce((object, arg) => {
77
71
  }); // get css from command line arguments or stdin
78
72
 
79
73
  (argo.from === '<stdin>' ? getStdin() : readFile(argo.from)).then(css => {
74
+ if (argo.from === '<stdin>' && !css) {
75
+ console.log(['CSS Has Pseudo\n', ' Transforms CSS with :has {}\n', 'Usage:\n', ' css-has-pseudo source.css transformed.css', ' css-has-pseudo --from=source.css --to=transformed.css --opts={}', ' echo "body:has(:focus) {}" | css-has-pseudo\n'].join('\n'));
76
+ process.exit(0);
77
+ }
78
+
80
79
  const pluginOpts = JSON.parse(argo.opts.replace(relaxedJsonPropRegExp, '"$2": ').replace(relaxedJsonValueRegExp, '$1"$2"$3'));
81
80
  const processOptions = Object.assign({
82
81
  from: argo.from,
@@ -91,11 +90,21 @@ const argo = process.argv.slice(2).reduce((object, arg) => {
91
90
  } else {
92
91
  return writeFile(argo.to, result.css).then(() => `CSS was written to "${argo.to}"`);
93
92
  }
93
+ }).catch(error => {
94
+ if (Object(error).name === 'CssSyntaxError') {
95
+ throw new Error(`PostCSS had trouble reading the file (${error.reason} on line ${error.line}, column ${error.column}).`);
96
+ }
97
+
98
+ if (Object(error).errno === -2) {
99
+ throw new Error(`Sorry, "${error.path}" could not be read.`);
100
+ }
101
+
102
+ throw error;
94
103
  }).then(result => {
95
104
  console.log(result);
96
105
  process.exit(0);
97
106
  }, error => {
98
- console.error(error);
107
+ console.error(Object(error).message || 'Something bad happened and we don’t even know what it was.');
99
108
  process.exit(1);
100
109
  });
101
110
 
package/index.js CHANGED
@@ -5,12 +5,12 @@ function cssHasPseudo(document) {
5
5
 
6
6
  const attributeElement = document.createElement('x'); // walk all stylesheets to collect observed css rules
7
7
 
8
- Array.prototype.forEach.call(document.styleSheets, walkStyleSheet);
8
+ [].forEach.call(document.styleSheets, walkStyleSheet);
9
9
  transformObservedItems(); // observe DOM modifications that affect selectors
10
10
 
11
11
  const mutationObserver = new MutationObserver(mutationsList => {
12
12
  mutationsList.forEach(mutation => {
13
- Array.prototype.forEach.call(mutation.addedNodes || [], node => {
13
+ [].forEach.call(mutation.addedNodes || [], node => {
14
14
  // walk stylesheets to collect observed css rules
15
15
  if (node.nodeType === 1 && node.sheet) {
16
16
  walkStyleSheet(node.sheet);
@@ -26,76 +26,82 @@ function cssHasPseudo(document) {
26
26
  subtree: true
27
27
  }); // observe DOM events that affect pseudo-selectors
28
28
 
29
- document.addEventListener('focus', () => setImmediate(transformObservedItems), true);
30
- document.addEventListener('blur', () => setImmediate(transformObservedItems), true);
31
- document.addEventListener('input', () => setImmediate(transformObservedItems)); // transform observed css rules
29
+ document.addEventListener('focus', transformObservedItems, true);
30
+ document.addEventListener('blur', transformObservedItems, true);
31
+ document.addEventListener('input', transformObservedItems); // transform observed css rules
32
32
 
33
33
  function transformObservedItems() {
34
- observedItems.forEach(item => {
35
- const nodes = [];
36
- Array.prototype.forEach.call(document.querySelectorAll(item.scopeSelector), element => {
37
- const nthChild = Array.prototype.indexOf.call(element.parentNode.children, element) + 1;
38
- const relativeSelectors = item.relativeSelectors.map(relativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector).join(); // find any relative :has element from the :scope element
39
-
40
- const relativeElement = element.parentNode.querySelector(relativeSelectors);
41
- const shouldElementMatch = item.isNot ? !relativeElement : relativeElement;
42
-
43
- if (shouldElementMatch) {
44
- // memorize the node
45
- nodes.push(element); // set an attribute with an irregular attribute name
46
- // document.createAttribute() doesn't support special characters
47
-
48
- attributeElement.innerHTML = '<x ' + item.attributeName + '>';
49
- element.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode()); // trigger a style refresh in IE and Edge
50
-
51
- document.documentElement.style.zoom = 1;
52
- document.documentElement.style.zoom = null;
53
- }
54
- }); // remove the encoded attribute from all nodes that no longer match them
55
-
56
- item.nodes.forEach(node => {
57
- if (nodes.indexOf(node) === -1) {
58
- node.removeAttribute(item.attributeName); // trigger a style refresh in IE and Edge
59
-
60
- document.documentElement.style.zoom = 1;
61
- document.documentElement.style.zoom = null;
62
- }
63
- }); // update the
64
-
65
- item.nodes = nodes;
34
+ requestAnimationFrame(() => {
35
+ observedItems.forEach(item => {
36
+ const nodes = [];
37
+ [].forEach.call(document.querySelectorAll(item.scopeSelector), element => {
38
+ const nthChild = [].indexOf.call(element.parentNode.children, element) + 1;
39
+ const relativeSelectors = item.relativeSelectors.map(relativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector).join(); // find any relative :has element from the :scope element
40
+
41
+ const relativeElement = element.parentNode.querySelector(relativeSelectors);
42
+ const shouldElementMatch = item.isNot ? !relativeElement : relativeElement;
43
+
44
+ if (shouldElementMatch) {
45
+ // memorize the node
46
+ nodes.push(element); // set an attribute with an irregular attribute name
47
+ // document.createAttribute() doesn't support special characters
48
+
49
+ attributeElement.innerHTML = '<x ' + item.attributeName + '>';
50
+ element.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode()); // trigger a style refresh in IE and Edge
51
+
52
+ document.documentElement.style.zoom = 1;
53
+ document.documentElement.style.zoom = null;
54
+ }
55
+ }); // remove the encoded attribute from all nodes that no longer match them
56
+
57
+ item.nodes.forEach(node => {
58
+ if (nodes.indexOf(node) === -1) {
59
+ node.removeAttribute(item.attributeName); // trigger a style refresh in IE and Edge
60
+
61
+ document.documentElement.style.zoom = 1;
62
+ document.documentElement.style.zoom = null;
63
+ }
64
+ }); // update the
65
+
66
+ item.nodes = nodes;
67
+ });
66
68
  });
67
69
  } // remove any observed cssrules that no longer apply
68
70
 
69
71
 
70
72
  function cleanupObservedCssRules() {
71
- Array.prototype.push.apply(observedItems, observedItems.splice(0).filter(item => item.rule.parentStyleSheet && item.rule.parentStyleSheet.ownerNode && document.documentElement.contains(item.rule.parentStyleSheet.ownerNode)));
73
+ [].push.apply(observedItems, observedItems.splice(0).filter(item => item.rule.parentStyleSheet && item.rule.parentStyleSheet.ownerNode && document.documentElement.contains(item.rule.parentStyleSheet.ownerNode)));
72
74
  } // walk a stylesheet to collect observed css rules
73
75
 
74
76
 
75
77
  function walkStyleSheet(styleSheet) {
76
- // walk a css rule to collect observed css rules
77
- Array.prototype.forEach.call(styleSheet.cssRules || [], rule => {
78
- if (rule.selectorText) {
79
- // decode the selector text in all browsers to:
80
- // [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative
81
- const selectors = decodeURIComponent(rule.selectorText.replace(/\\(.)/g, '$1')).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);
82
-
83
- if (selectors) {
84
- const attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' + // encode a :has() pseudo selector as an attribute name
85
- selectors[3].replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') + ')';
86
- observedItems.push({
87
- rule,
88
- scopeSelector: selectors[1],
89
- isNot: selectors[2],
90
- relativeSelectors: selectors[3].split(/\s*,\s*/),
91
- attributeName,
92
- nodes: []
93
- });
78
+ try {
79
+ // walk a css rule to collect observed css rules
80
+ [].forEach.call(styleSheet.cssRules || [], rule => {
81
+ if (rule.selectorText) {
82
+ // decode the selector text in all browsers to:
83
+ // [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative
84
+ const selectors = decodeURIComponent(rule.selectorText.replace(/\\(.)/g, '$1')).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);
85
+
86
+ if (selectors) {
87
+ const attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' + // encode a :has() pseudo selector as an attribute name
88
+ encodeURIComponent(selectors[3]).replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') + ')';
89
+ observedItems.push({
90
+ rule,
91
+ scopeSelector: selectors[1],
92
+ isNot: selectors[2],
93
+ relativeSelectors: selectors[3].split(/\s*,\s*/),
94
+ attributeName,
95
+ nodes: []
96
+ });
97
+ }
98
+ } else {
99
+ walkStyleSheet(rule);
94
100
  }
95
- } else {
96
- walkStyleSheet(rule);
97
- }
98
- });
101
+ });
102
+ } catch (error) {
103
+ /* do nothing and continue */
104
+ }
99
105
  }
100
106
  }
101
107
 
package/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["src/browser.js"],"sourcesContent":["export default function cssHasPseudo(document) {\n\tconst observedItems = [];\n\n\t// document.createAttribute() doesn't support `:` in the name. innerHTML does\n\tconst attributeElement = document.createElement('x');\n\n\t// walk all stylesheets to collect observed css rules\n\tArray.prototype.forEach.call(document.styleSheets, walkStyleSheet);\n\ttransformObservedItems();\n\n\t// observe DOM modifications that affect selectors\n\tconst mutationObserver = new MutationObserver(mutationsList => {\n\t\tmutationsList.forEach(mutation => {\n\t\t\tArray.prototype.forEach.call(mutation.addedNodes || [], node => {\n\t\t\t\t// walk stylesheets to collect observed css rules\n\t\t\t\tif (node.nodeType === 1 && node.sheet) {\n\t\t\t\t\twalkStyleSheet(node.sheet);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// transform observed css rules\n\t\t\tcleanupObservedCssRules();\n\t\t\ttransformObservedItems();\n\t\t});\n\t});\n\n\tmutationObserver.observe(document, { childList: true, subtree: true });\n\n\t// observe DOM events that affect pseudo-selectors\n\tdocument.addEventListener('focus', () => setImmediate(transformObservedItems), true);\n\tdocument.addEventListener('blur', () => setImmediate(transformObservedItems), true);\n\tdocument.addEventListener('input', () => setImmediate(transformObservedItems));\n\n\t// transform observed css rules\n\tfunction transformObservedItems() {\n\t\tobservedItems.forEach(\n\t\t\titem => {\n\t\t\t\tconst nodes = [];\n\n\t\t\t\tArray.prototype.forEach.call(\n\t\t\t\t\tdocument.querySelectorAll(item.scopeSelector),\n\t\t\t\t\telement => {\n\t\t\t\t\t\tconst nthChild = Array.prototype.indexOf.call(element.parentNode.children, element) + 1;\n\t\t\t\t\t\tconst relativeSelectors = item.relativeSelectors.map(\n\t\t\t\t\t\t\trelativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector\n\t\t\t\t\t\t).join();\n\n\t\t\t\t\t\t// find any relative :has element from the :scope element\n\t\t\t\t\t\tconst relativeElement = element.parentNode.querySelector(relativeSelectors);\n\n\t\t\t\t\t\tconst shouldElementMatch = item.isNot ? !relativeElement : relativeElement;\n\n\t\t\t\t\t\tif (shouldElementMatch) {\n\t\t\t\t\t\t\t// memorize the node\n\t\t\t\t\t\t\tnodes.push(element);\n\n\t\t\t\t\t\t\t// set an attribute with an irregular attribute name\n\t\t\t\t\t\t\t// document.createAttribute() doesn't support special characters\n\t\t\t\t\t\t\tattributeElement.innerHTML = '<x ' + item.attributeName + '>';\n\n\t\t\t\t\t\t\telement.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode());\n\n\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t);\n\n\t\t\t\t// remove the encoded attribute from all nodes that no longer match them\n\t\t\t\titem.nodes.forEach(node => {\n\t\t\t\t\tif (nodes.indexOf(node) === -1) {\n\t\t\t\t\t\tnode.removeAttribute(item.attributeName);\n\n\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\t// update the\n\t\t\t\titem.nodes = nodes;\n\t\t\t}\n\t\t);\n\t}\n\n\t// remove any observed cssrules that no longer apply\n\tfunction cleanupObservedCssRules() {\n\t\tArray.prototype.push.apply(\n\t\t\tobservedItems,\n\t\t\tobservedItems.splice(0).filter(\n\t\t\t\titem => item.rule.parentStyleSheet &&\n\t\t\t\t\titem.rule.parentStyleSheet.ownerNode &&\n\t\t\t\t\tdocument.documentElement.contains(item.rule.parentStyleSheet.ownerNode)\n\t\t\t)\n\t\t);\n\t}\n\n\t// walk a stylesheet to collect observed css rules\n\tfunction walkStyleSheet(styleSheet) {\n\t\t// walk a css rule to collect observed css rules\n\t\tArray.prototype.forEach.call(styleSheet.cssRules || [], rule => {\n\t\t\tif (rule.selectorText) {\n\t\t\t\t// decode the selector text in all browsers to:\n\t\t\t\t// [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative\n\t\t\t\tconst selectors = decodeURIComponent(rule.selectorText.replace(/\\\\(.)/g, '$1')).match(/^(.*?)\\[:(not-)?has\\((.+?)\\)\\](.*?)$/);\n\n\t\t\t\tif (selectors) {\n\t\t\t\t\tconst attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' +\n\t\t\t\t\t\t// encode a :has() pseudo selector as an attribute name\n\t\t\t\t\t\tselectors[3].replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') +\n\t\t\t\t\t')';\n\n\t\t\t\t\tobservedItems.push({\n\t\t\t\t\t\trule,\n\t\t\t\t\t\tscopeSelector: selectors[1],\n\t\t\t\t\t\tisNot: selectors[2],\n\t\t\t\t\t\trelativeSelectors: selectors[3].split(/\\s*,\\s*/),\n\t\t\t\t\t\tattributeName,\n\t\t\t\t\t\tnodes: []\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\twalkStyleSheet(rule);\n\t\t\t}\n\t\t});\n\t}\n}\n"],"names":["cssHasPseudo","document","observedItems","attributeElement","createElement","Array","prototype","forEach","call","styleSheets","walkStyleSheet","transformObservedItems","mutationObserver","MutationObserver","mutationsList","mutation","addedNodes","node","nodeType","sheet","cleanupObservedCssRules","observe","childList","subtree","addEventListener","setImmediate","item","nodes","querySelectorAll","scopeSelector","element","nthChild","indexOf","parentNode","children","relativeSelectors","map","relativeSelector","join","relativeElement","querySelector","shouldElementMatch","isNot","push","innerHTML","attributeName","setAttributeNode","attributes","cloneNode","documentElement","style","zoom","removeAttribute","apply","splice","filter","rule","parentStyleSheet","ownerNode","contains","styleSheet","cssRules","selectorText","selectors","decodeURIComponent","replace","match","split"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sources":["src/browser.js"],"sourcesContent":["export default function cssHasPseudo(document) {\n\tconst observedItems = [];\n\n\t// document.createAttribute() doesn't support `:` in the name. innerHTML does\n\tconst attributeElement = document.createElement('x');\n\n\t// walk all stylesheets to collect observed css rules\n\t[].forEach.call(document.styleSheets, walkStyleSheet);\n\ttransformObservedItems();\n\n\t// observe DOM modifications that affect selectors\n\tconst mutationObserver = new MutationObserver(mutationsList => {\n\t\tmutationsList.forEach(mutation => {\n\t\t\t[].forEach.call(mutation.addedNodes || [], node => {\n\t\t\t\t// walk stylesheets to collect observed css rules\n\t\t\t\tif (node.nodeType === 1 && node.sheet) {\n\t\t\t\t\twalkStyleSheet(node.sheet);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// transform observed css rules\n\t\t\tcleanupObservedCssRules();\n\t\t\ttransformObservedItems();\n\t\t});\n\t});\n\n\tmutationObserver.observe(document, { childList: true, subtree: true });\n\n\t// observe DOM events that affect pseudo-selectors\n\tdocument.addEventListener('focus', transformObservedItems, true);\n\tdocument.addEventListener('blur', transformObservedItems, true);\n\tdocument.addEventListener('input', transformObservedItems);\n\n\t// transform observed css rules\n\tfunction transformObservedItems() {\n\t\trequestAnimationFrame(() => {\n\t\t\tobservedItems.forEach(\n\t\t\t\titem => {\n\t\t\t\t\tconst nodes = [];\n\n\t\t\t\t\t[].forEach.call(\n\t\t\t\t\t\tdocument.querySelectorAll(item.scopeSelector),\n\t\t\t\t\t\telement => {\n\t\t\t\t\t\t\tconst nthChild = [].indexOf.call(element.parentNode.children, element) + 1;\n\t\t\t\t\t\t\tconst relativeSelectors = item.relativeSelectors.map(\n\t\t\t\t\t\t\t\trelativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector\n\t\t\t\t\t\t\t).join();\n\n\t\t\t\t\t\t\t// find any relative :has element from the :scope element\n\t\t\t\t\t\t\tconst relativeElement = element.parentNode.querySelector(relativeSelectors);\n\n\t\t\t\t\t\t\tconst shouldElementMatch = item.isNot ? !relativeElement : relativeElement;\n\n\t\t\t\t\t\t\tif (shouldElementMatch) {\n\t\t\t\t\t\t\t\t// memorize the node\n\t\t\t\t\t\t\t\tnodes.push(element);\n\n\t\t\t\t\t\t\t\t// set an attribute with an irregular attribute name\n\t\t\t\t\t\t\t\t// document.createAttribute() doesn't support special characters\n\t\t\t\t\t\t\t\tattributeElement.innerHTML = '<x ' + item.attributeName + '>';\n\n\t\t\t\t\t\t\t\telement.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode());\n\n\t\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t);\n\n\t\t\t\t\t// remove the encoded attribute from all nodes that no longer match them\n\t\t\t\t\titem.nodes.forEach(node => {\n\t\t\t\t\t\tif (nodes.indexOf(node) === -1) {\n\t\t\t\t\t\t\tnode.removeAttribute(item.attributeName);\n\n\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\n\t\t\t\t\t// update the\n\t\t\t\t\titem.nodes = nodes;\n\t\t\t\t}\n\t\t\t);\n\t\t});\n\t}\n\n\t// remove any observed cssrules that no longer apply\n\tfunction cleanupObservedCssRules() {\n\t\t[].push.apply(\n\t\t\tobservedItems,\n\t\t\tobservedItems.splice(0).filter(\n\t\t\t\titem => item.rule.parentStyleSheet &&\n\t\t\t\t\titem.rule.parentStyleSheet.ownerNode &&\n\t\t\t\t\tdocument.documentElement.contains(item.rule.parentStyleSheet.ownerNode)\n\t\t\t)\n\t\t);\n\t}\n\n\t// walk a stylesheet to collect observed css rules\n\tfunction walkStyleSheet(styleSheet) {\n\t\ttry {\n\t\t\t// walk a css rule to collect observed css rules\n\t\t\t[].forEach.call(styleSheet.cssRules || [], rule => {\n\t\t\t\tif (rule.selectorText) {\n\t\t\t\t\t// decode the selector text in all browsers to:\n\t\t\t\t\t// [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative\n\t\t\t\t\tconst selectors = decodeURIComponent(rule.selectorText.replace(/\\\\(.)/g, '$1')).match(/^(.*?)\\[:(not-)?has\\((.+?)\\)\\](.*?)$/);\n\n\t\t\t\t\tif (selectors) {\n\t\t\t\t\t\tconst attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' +\n\t\t\t\t\t\t\t// encode a :has() pseudo selector as an attribute name\n\t\t\t\t\t\t\tencodeURIComponent(selectors[3]).replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') +\n\t\t\t\t\t\t')';\n\n\t\t\t\t\t\tobservedItems.push({\n\t\t\t\t\t\t\trule,\n\t\t\t\t\t\t\tscopeSelector: selectors[1],\n\t\t\t\t\t\t\tisNot: selectors[2],\n\t\t\t\t\t\t\trelativeSelectors: selectors[3].split(/\\s*,\\s*/),\n\t\t\t\t\t\t\tattributeName,\n\t\t\t\t\t\t\tnodes: []\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\twalkStyleSheet(rule);\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (error) {\n\t\t\t/* do nothing and continue */\n\t\t}\n\t}\n}\n"],"names":["cssHasPseudo","document","observedItems","attributeElement","createElement","forEach","call","styleSheets","walkStyleSheet","transformObservedItems","mutationObserver","MutationObserver","mutationsList","mutation","addedNodes","node","nodeType","sheet","cleanupObservedCssRules","observe","childList","subtree","addEventListener","requestAnimationFrame","item","nodes","querySelectorAll","scopeSelector","element","nthChild","indexOf","parentNode","children","relativeSelectors","map","relativeSelector","join","relativeElement","querySelector","shouldElementMatch","isNot","push","innerHTML","attributeName","setAttributeNode","attributes","cloneNode","documentElement","style","zoom","removeAttribute","apply","splice","filter","rule","parentStyleSheet","ownerNode","contains","styleSheet","cssRules","selectorText","selectors","decodeURIComponent","replace","match","encodeURIComponent","split","error"],"mappings":"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"}
package/index.mjs CHANGED
@@ -3,12 +3,12 @@ function cssHasPseudo(document) {
3
3
 
4
4
  const attributeElement = document.createElement('x'); // walk all stylesheets to collect observed css rules
5
5
 
6
- Array.prototype.forEach.call(document.styleSheets, walkStyleSheet);
6
+ [].forEach.call(document.styleSheets, walkStyleSheet);
7
7
  transformObservedItems(); // observe DOM modifications that affect selectors
8
8
 
9
9
  const mutationObserver = new MutationObserver(mutationsList => {
10
10
  mutationsList.forEach(mutation => {
11
- Array.prototype.forEach.call(mutation.addedNodes || [], node => {
11
+ [].forEach.call(mutation.addedNodes || [], node => {
12
12
  // walk stylesheets to collect observed css rules
13
13
  if (node.nodeType === 1 && node.sheet) {
14
14
  walkStyleSheet(node.sheet);
@@ -24,76 +24,82 @@ function cssHasPseudo(document) {
24
24
  subtree: true
25
25
  }); // observe DOM events that affect pseudo-selectors
26
26
 
27
- document.addEventListener('focus', () => setImmediate(transformObservedItems), true);
28
- document.addEventListener('blur', () => setImmediate(transformObservedItems), true);
29
- document.addEventListener('input', () => setImmediate(transformObservedItems)); // transform observed css rules
27
+ document.addEventListener('focus', transformObservedItems, true);
28
+ document.addEventListener('blur', transformObservedItems, true);
29
+ document.addEventListener('input', transformObservedItems); // transform observed css rules
30
30
 
31
31
  function transformObservedItems() {
32
- observedItems.forEach(item => {
33
- const nodes = [];
34
- Array.prototype.forEach.call(document.querySelectorAll(item.scopeSelector), element => {
35
- const nthChild = Array.prototype.indexOf.call(element.parentNode.children, element) + 1;
36
- const relativeSelectors = item.relativeSelectors.map(relativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector).join(); // find any relative :has element from the :scope element
37
-
38
- const relativeElement = element.parentNode.querySelector(relativeSelectors);
39
- const shouldElementMatch = item.isNot ? !relativeElement : relativeElement;
40
-
41
- if (shouldElementMatch) {
42
- // memorize the node
43
- nodes.push(element); // set an attribute with an irregular attribute name
44
- // document.createAttribute() doesn't support special characters
45
-
46
- attributeElement.innerHTML = '<x ' + item.attributeName + '>';
47
- element.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode()); // trigger a style refresh in IE and Edge
48
-
49
- document.documentElement.style.zoom = 1;
50
- document.documentElement.style.zoom = null;
51
- }
52
- }); // remove the encoded attribute from all nodes that no longer match them
53
-
54
- item.nodes.forEach(node => {
55
- if (nodes.indexOf(node) === -1) {
56
- node.removeAttribute(item.attributeName); // trigger a style refresh in IE and Edge
57
-
58
- document.documentElement.style.zoom = 1;
59
- document.documentElement.style.zoom = null;
60
- }
61
- }); // update the
62
-
63
- item.nodes = nodes;
32
+ requestAnimationFrame(() => {
33
+ observedItems.forEach(item => {
34
+ const nodes = [];
35
+ [].forEach.call(document.querySelectorAll(item.scopeSelector), element => {
36
+ const nthChild = [].indexOf.call(element.parentNode.children, element) + 1;
37
+ const relativeSelectors = item.relativeSelectors.map(relativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector).join(); // find any relative :has element from the :scope element
38
+
39
+ const relativeElement = element.parentNode.querySelector(relativeSelectors);
40
+ const shouldElementMatch = item.isNot ? !relativeElement : relativeElement;
41
+
42
+ if (shouldElementMatch) {
43
+ // memorize the node
44
+ nodes.push(element); // set an attribute with an irregular attribute name
45
+ // document.createAttribute() doesn't support special characters
46
+
47
+ attributeElement.innerHTML = '<x ' + item.attributeName + '>';
48
+ element.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode()); // trigger a style refresh in IE and Edge
49
+
50
+ document.documentElement.style.zoom = 1;
51
+ document.documentElement.style.zoom = null;
52
+ }
53
+ }); // remove the encoded attribute from all nodes that no longer match them
54
+
55
+ item.nodes.forEach(node => {
56
+ if (nodes.indexOf(node) === -1) {
57
+ node.removeAttribute(item.attributeName); // trigger a style refresh in IE and Edge
58
+
59
+ document.documentElement.style.zoom = 1;
60
+ document.documentElement.style.zoom = null;
61
+ }
62
+ }); // update the
63
+
64
+ item.nodes = nodes;
65
+ });
64
66
  });
65
67
  } // remove any observed cssrules that no longer apply
66
68
 
67
69
 
68
70
  function cleanupObservedCssRules() {
69
- Array.prototype.push.apply(observedItems, observedItems.splice(0).filter(item => item.rule.parentStyleSheet && item.rule.parentStyleSheet.ownerNode && document.documentElement.contains(item.rule.parentStyleSheet.ownerNode)));
71
+ [].push.apply(observedItems, observedItems.splice(0).filter(item => item.rule.parentStyleSheet && item.rule.parentStyleSheet.ownerNode && document.documentElement.contains(item.rule.parentStyleSheet.ownerNode)));
70
72
  } // walk a stylesheet to collect observed css rules
71
73
 
72
74
 
73
75
  function walkStyleSheet(styleSheet) {
74
- // walk a css rule to collect observed css rules
75
- Array.prototype.forEach.call(styleSheet.cssRules || [], rule => {
76
- if (rule.selectorText) {
77
- // decode the selector text in all browsers to:
78
- // [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative
79
- const selectors = decodeURIComponent(rule.selectorText.replace(/\\(.)/g, '$1')).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);
80
-
81
- if (selectors) {
82
- const attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' + // encode a :has() pseudo selector as an attribute name
83
- selectors[3].replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') + ')';
84
- observedItems.push({
85
- rule,
86
- scopeSelector: selectors[1],
87
- isNot: selectors[2],
88
- relativeSelectors: selectors[3].split(/\s*,\s*/),
89
- attributeName,
90
- nodes: []
91
- });
76
+ try {
77
+ // walk a css rule to collect observed css rules
78
+ [].forEach.call(styleSheet.cssRules || [], rule => {
79
+ if (rule.selectorText) {
80
+ // decode the selector text in all browsers to:
81
+ // [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative
82
+ const selectors = decodeURIComponent(rule.selectorText.replace(/\\(.)/g, '$1')).match(/^(.*?)\[:(not-)?has\((.+?)\)\](.*?)$/);
83
+
84
+ if (selectors) {
85
+ const attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' + // encode a :has() pseudo selector as an attribute name
86
+ encodeURIComponent(selectors[3]).replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') + ')';
87
+ observedItems.push({
88
+ rule,
89
+ scopeSelector: selectors[1],
90
+ isNot: selectors[2],
91
+ relativeSelectors: selectors[3].split(/\s*,\s*/),
92
+ attributeName,
93
+ nodes: []
94
+ });
95
+ }
96
+ } else {
97
+ walkStyleSheet(rule);
92
98
  }
93
- } else {
94
- walkStyleSheet(rule);
95
- }
96
- });
99
+ });
100
+ } catch (error) {
101
+ /* do nothing and continue */
102
+ }
97
103
  }
98
104
  }
99
105
 
package/index.mjs.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.mjs","sources":["src/browser.js"],"sourcesContent":["export default function cssHasPseudo(document) {\n\tconst observedItems = [];\n\n\t// document.createAttribute() doesn't support `:` in the name. innerHTML does\n\tconst attributeElement = document.createElement('x');\n\n\t// walk all stylesheets to collect observed css rules\n\tArray.prototype.forEach.call(document.styleSheets, walkStyleSheet);\n\ttransformObservedItems();\n\n\t// observe DOM modifications that affect selectors\n\tconst mutationObserver = new MutationObserver(mutationsList => {\n\t\tmutationsList.forEach(mutation => {\n\t\t\tArray.prototype.forEach.call(mutation.addedNodes || [], node => {\n\t\t\t\t// walk stylesheets to collect observed css rules\n\t\t\t\tif (node.nodeType === 1 && node.sheet) {\n\t\t\t\t\twalkStyleSheet(node.sheet);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// transform observed css rules\n\t\t\tcleanupObservedCssRules();\n\t\t\ttransformObservedItems();\n\t\t});\n\t});\n\n\tmutationObserver.observe(document, { childList: true, subtree: true });\n\n\t// observe DOM events that affect pseudo-selectors\n\tdocument.addEventListener('focus', () => setImmediate(transformObservedItems), true);\n\tdocument.addEventListener('blur', () => setImmediate(transformObservedItems), true);\n\tdocument.addEventListener('input', () => setImmediate(transformObservedItems));\n\n\t// transform observed css rules\n\tfunction transformObservedItems() {\n\t\tobservedItems.forEach(\n\t\t\titem => {\n\t\t\t\tconst nodes = [];\n\n\t\t\t\tArray.prototype.forEach.call(\n\t\t\t\t\tdocument.querySelectorAll(item.scopeSelector),\n\t\t\t\t\telement => {\n\t\t\t\t\t\tconst nthChild = Array.prototype.indexOf.call(element.parentNode.children, element) + 1;\n\t\t\t\t\t\tconst relativeSelectors = item.relativeSelectors.map(\n\t\t\t\t\t\t\trelativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector\n\t\t\t\t\t\t).join();\n\n\t\t\t\t\t\t// find any relative :has element from the :scope element\n\t\t\t\t\t\tconst relativeElement = element.parentNode.querySelector(relativeSelectors);\n\n\t\t\t\t\t\tconst shouldElementMatch = item.isNot ? !relativeElement : relativeElement;\n\n\t\t\t\t\t\tif (shouldElementMatch) {\n\t\t\t\t\t\t\t// memorize the node\n\t\t\t\t\t\t\tnodes.push(element);\n\n\t\t\t\t\t\t\t// set an attribute with an irregular attribute name\n\t\t\t\t\t\t\t// document.createAttribute() doesn't support special characters\n\t\t\t\t\t\t\tattributeElement.innerHTML = '<x ' + item.attributeName + '>';\n\n\t\t\t\t\t\t\telement.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode());\n\n\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t);\n\n\t\t\t\t// remove the encoded attribute from all nodes that no longer match them\n\t\t\t\titem.nodes.forEach(node => {\n\t\t\t\t\tif (nodes.indexOf(node) === -1) {\n\t\t\t\t\t\tnode.removeAttribute(item.attributeName);\n\n\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\t// update the\n\t\t\t\titem.nodes = nodes;\n\t\t\t}\n\t\t);\n\t}\n\n\t// remove any observed cssrules that no longer apply\n\tfunction cleanupObservedCssRules() {\n\t\tArray.prototype.push.apply(\n\t\t\tobservedItems,\n\t\t\tobservedItems.splice(0).filter(\n\t\t\t\titem => item.rule.parentStyleSheet &&\n\t\t\t\t\titem.rule.parentStyleSheet.ownerNode &&\n\t\t\t\t\tdocument.documentElement.contains(item.rule.parentStyleSheet.ownerNode)\n\t\t\t)\n\t\t);\n\t}\n\n\t// walk a stylesheet to collect observed css rules\n\tfunction walkStyleSheet(styleSheet) {\n\t\t// walk a css rule to collect observed css rules\n\t\tArray.prototype.forEach.call(styleSheet.cssRules || [], rule => {\n\t\t\tif (rule.selectorText) {\n\t\t\t\t// decode the selector text in all browsers to:\n\t\t\t\t// [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative\n\t\t\t\tconst selectors = decodeURIComponent(rule.selectorText.replace(/\\\\(.)/g, '$1')).match(/^(.*?)\\[:(not-)?has\\((.+?)\\)\\](.*?)$/);\n\n\t\t\t\tif (selectors) {\n\t\t\t\t\tconst attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' +\n\t\t\t\t\t\t// encode a :has() pseudo selector as an attribute name\n\t\t\t\t\t\tselectors[3].replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') +\n\t\t\t\t\t')';\n\n\t\t\t\t\tobservedItems.push({\n\t\t\t\t\t\trule,\n\t\t\t\t\t\tscopeSelector: selectors[1],\n\t\t\t\t\t\tisNot: selectors[2],\n\t\t\t\t\t\trelativeSelectors: selectors[3].split(/\\s*,\\s*/),\n\t\t\t\t\t\tattributeName,\n\t\t\t\t\t\tnodes: []\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\twalkStyleSheet(rule);\n\t\t\t}\n\t\t});\n\t}\n}\n"],"names":["cssHasPseudo","document","observedItems","attributeElement","createElement","Array","prototype","forEach","call","styleSheets","walkStyleSheet","transformObservedItems","mutationObserver","MutationObserver","mutationsList","mutation","addedNodes","node","nodeType","sheet","cleanupObservedCssRules","observe","childList","subtree","addEventListener","setImmediate","item","nodes","querySelectorAll","scopeSelector","element","nthChild","indexOf","parentNode","children","relativeSelectors","map","relativeSelector","join","relativeElement","querySelector","shouldElementMatch","isNot","push","innerHTML","attributeName","setAttributeNode","attributes","cloneNode","documentElement","style","zoom","removeAttribute","apply","splice","filter","rule","parentStyleSheet","ownerNode","contains","styleSheet","cssRules","selectorText","selectors","decodeURIComponent","replace","match","split"],"mappings":"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"}
1
+ {"version":3,"file":"index.mjs","sources":["src/browser.js"],"sourcesContent":["export default function cssHasPseudo(document) {\n\tconst observedItems = [];\n\n\t// document.createAttribute() doesn't support `:` in the name. innerHTML does\n\tconst attributeElement = document.createElement('x');\n\n\t// walk all stylesheets to collect observed css rules\n\t[].forEach.call(document.styleSheets, walkStyleSheet);\n\ttransformObservedItems();\n\n\t// observe DOM modifications that affect selectors\n\tconst mutationObserver = new MutationObserver(mutationsList => {\n\t\tmutationsList.forEach(mutation => {\n\t\t\t[].forEach.call(mutation.addedNodes || [], node => {\n\t\t\t\t// walk stylesheets to collect observed css rules\n\t\t\t\tif (node.nodeType === 1 && node.sheet) {\n\t\t\t\t\twalkStyleSheet(node.sheet);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// transform observed css rules\n\t\t\tcleanupObservedCssRules();\n\t\t\ttransformObservedItems();\n\t\t});\n\t});\n\n\tmutationObserver.observe(document, { childList: true, subtree: true });\n\n\t// observe DOM events that affect pseudo-selectors\n\tdocument.addEventListener('focus', transformObservedItems, true);\n\tdocument.addEventListener('blur', transformObservedItems, true);\n\tdocument.addEventListener('input', transformObservedItems);\n\n\t// transform observed css rules\n\tfunction transformObservedItems() {\n\t\trequestAnimationFrame(() => {\n\t\t\tobservedItems.forEach(\n\t\t\t\titem => {\n\t\t\t\t\tconst nodes = [];\n\n\t\t\t\t\t[].forEach.call(\n\t\t\t\t\t\tdocument.querySelectorAll(item.scopeSelector),\n\t\t\t\t\t\telement => {\n\t\t\t\t\t\t\tconst nthChild = [].indexOf.call(element.parentNode.children, element) + 1;\n\t\t\t\t\t\t\tconst relativeSelectors = item.relativeSelectors.map(\n\t\t\t\t\t\t\t\trelativeSelector => item.scopeSelector + ':nth-child(' + nthChild + ') ' + relativeSelector\n\t\t\t\t\t\t\t).join();\n\n\t\t\t\t\t\t\t// find any relative :has element from the :scope element\n\t\t\t\t\t\t\tconst relativeElement = element.parentNode.querySelector(relativeSelectors);\n\n\t\t\t\t\t\t\tconst shouldElementMatch = item.isNot ? !relativeElement : relativeElement;\n\n\t\t\t\t\t\t\tif (shouldElementMatch) {\n\t\t\t\t\t\t\t\t// memorize the node\n\t\t\t\t\t\t\t\tnodes.push(element);\n\n\t\t\t\t\t\t\t\t// set an attribute with an irregular attribute name\n\t\t\t\t\t\t\t\t// document.createAttribute() doesn't support special characters\n\t\t\t\t\t\t\t\tattributeElement.innerHTML = '<x ' + item.attributeName + '>';\n\n\t\t\t\t\t\t\t\telement.setAttributeNode(attributeElement.children[0].attributes[0].cloneNode());\n\n\t\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t);\n\n\t\t\t\t\t// remove the encoded attribute from all nodes that no longer match them\n\t\t\t\t\titem.nodes.forEach(node => {\n\t\t\t\t\t\tif (nodes.indexOf(node) === -1) {\n\t\t\t\t\t\t\tnode.removeAttribute(item.attributeName);\n\n\t\t\t\t\t\t\t// trigger a style refresh in IE and Edge\n\t\t\t\t\t\t\tdocument.documentElement.style.zoom = 1; document.documentElement.style.zoom = null;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\n\t\t\t\t\t// update the\n\t\t\t\t\titem.nodes = nodes;\n\t\t\t\t}\n\t\t\t);\n\t\t});\n\t}\n\n\t// remove any observed cssrules that no longer apply\n\tfunction cleanupObservedCssRules() {\n\t\t[].push.apply(\n\t\t\tobservedItems,\n\t\t\tobservedItems.splice(0).filter(\n\t\t\t\titem => item.rule.parentStyleSheet &&\n\t\t\t\t\titem.rule.parentStyleSheet.ownerNode &&\n\t\t\t\t\tdocument.documentElement.contains(item.rule.parentStyleSheet.ownerNode)\n\t\t\t)\n\t\t);\n\t}\n\n\t// walk a stylesheet to collect observed css rules\n\tfunction walkStyleSheet(styleSheet) {\n\t\ttry {\n\t\t\t// walk a css rule to collect observed css rules\n\t\t\t[].forEach.call(styleSheet.cssRules || [], rule => {\n\t\t\t\tif (rule.selectorText) {\n\t\t\t\t\t// decode the selector text in all browsers to:\n\t\t\t\t\t// [1] = :scope, [2] = :not(:has), [3] = :has relative, [4] = :scope relative\n\t\t\t\t\tconst selectors = decodeURIComponent(rule.selectorText.replace(/\\\\(.)/g, '$1')).match(/^(.*?)\\[:(not-)?has\\((.+?)\\)\\](.*?)$/);\n\n\t\t\t\t\tif (selectors) {\n\t\t\t\t\t\tconst attributeName = ':' + (selectors[2] ? 'not-' : '') + 'has(' +\n\t\t\t\t\t\t\t// encode a :has() pseudo selector as an attribute name\n\t\t\t\t\t\t\tencodeURIComponent(selectors[3]).replace(/%3A/g, ':').replace(/%5B/g, '[').replace(/%5D/g, ']').replace(/%2C/g, ',') +\n\t\t\t\t\t\t')';\n\n\t\t\t\t\t\tobservedItems.push({\n\t\t\t\t\t\t\trule,\n\t\t\t\t\t\t\tscopeSelector: selectors[1],\n\t\t\t\t\t\t\tisNot: selectors[2],\n\t\t\t\t\t\t\trelativeSelectors: selectors[3].split(/\\s*,\\s*/),\n\t\t\t\t\t\t\tattributeName,\n\t\t\t\t\t\t\tnodes: []\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\twalkStyleSheet(rule);\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (error) {\n\t\t\t/* do nothing and continue */\n\t\t}\n\t}\n}\n"],"names":["cssHasPseudo","document","observedItems","attributeElement","createElement","forEach","call","styleSheets","walkStyleSheet","transformObservedItems","mutationObserver","MutationObserver","mutationsList","mutation","addedNodes","node","nodeType","sheet","cleanupObservedCssRules","observe","childList","subtree","addEventListener","requestAnimationFrame","item","nodes","querySelectorAll","scopeSelector","element","nthChild","indexOf","parentNode","children","relativeSelectors","map","relativeSelector","join","relativeElement","querySelector","shouldElementMatch","isNot","push","innerHTML","attributeName","setAttributeNode","attributes","cloneNode","documentElement","style","zoom","removeAttribute","apply","splice","filter","rule","parentStyleSheet","ownerNode","contains","styleSheet","cssRules","selectorText","selectors","decodeURIComponent","replace","match","encodeURIComponent","split","error"],"mappings":"AAAe,SAASA,YAAT,CAAsBC,QAAtB,EAAgC;QACxCC,aAAa,GAAG,EAAtB,CAD8C;;QAIxCC,gBAAgB,GAAGF,QAAQ,CAACG,aAAT,CAAuB,GAAvB,CAAzB,CAJ8C;;KAO3CC,OAAH,CAAWC,IAAX,CAAgBL,QAAQ,CAACM,WAAzB,EAAsCC,cAAtC;EACAC,sBAAsB,GARwB;;QAWxCC,gBAAgB,GAAG,IAAIC,gBAAJ,CAAqBC,aAAa,IAAI;IAC9DA,aAAa,CAACP,OAAd,CAAsBQ,QAAQ,IAAI;SAC9BR,OAAH,CAAWC,IAAX,CAAgBO,QAAQ,CAACC,UAAT,IAAuB,EAAvC,EAA2CC,IAAI,IAAI;;YAE9CA,IAAI,CAACC,QAAL,KAAkB,CAAlB,IAAuBD,IAAI,CAACE,KAAhC,EAAuC;UACtCT,cAAc,CAACO,IAAI,CAACE,KAAN,CAAd;;OAHF,EADiC;;MASjCC,uBAAuB;MACvBT,sBAAsB;KAVvB;GADwB,CAAzB;EAeAC,gBAAgB,CAACS,OAAjB,CAAyBlB,QAAzB,EAAmC;IAAEmB,SAAS,EAAE,IAAb;IAAmBC,OAAO,EAAE;GAA/D,EA1B8C;;EA6B9CpB,QAAQ,CAACqB,gBAAT,CAA0B,OAA1B,EAAmCb,sBAAnC,EAA2D,IAA3D;EACAR,QAAQ,CAACqB,gBAAT,CAA0B,MAA1B,EAAkCb,sBAAlC,EAA0D,IAA1D;EACAR,QAAQ,CAACqB,gBAAT,CAA0B,OAA1B,EAAmCb,sBAAnC,EA/B8C;;WAkCrCA,sBAAT,GAAkC;IACjCc,qBAAqB,CAAC,MAAM;MAC3BrB,aAAa,CAACG,OAAd,CACCmB,IAAI,IAAI;cACDC,KAAK,GAAG,EAAd;WAEGpB,OAAH,CAAWC,IAAX,CACCL,QAAQ,CAACyB,gBAAT,CAA0BF,IAAI,CAACG,aAA/B,CADD,EAECC,OAAO,IAAI;gBACJC,QAAQ,GAAG,GAAGC,OAAH,CAAWxB,IAAX,CAAgBsB,OAAO,CAACG,UAAR,CAAmBC,QAAnC,EAA6CJ,OAA7C,IAAwD,CAAzE;gBACMK,iBAAiB,GAAGT,IAAI,CAACS,iBAAL,CAAuBC,GAAvB,CACzBC,gBAAgB,IAAIX,IAAI,CAACG,aAAL,GAAqB,aAArB,GAAqCE,QAArC,GAAgD,IAAhD,GAAuDM,gBADlD,EAExBC,IAFwB,EAA1B,CAFU;;gBAOJC,eAAe,GAAGT,OAAO,CAACG,UAAR,CAAmBO,aAAnB,CAAiCL,iBAAjC,CAAxB;gBAEMM,kBAAkB,GAAGf,IAAI,CAACgB,KAAL,GAAa,CAACH,eAAd,GAAgCA,eAA3D;;cAEIE,kBAAJ,EAAwB;;YAEvBd,KAAK,CAACgB,IAAN,CAAWb,OAAX,EAFuB;;;YAMvBzB,gBAAgB,CAACuC,SAAjB,GAA6B,QAAQlB,IAAI,CAACmB,aAAb,GAA6B,GAA1D;YAEAf,OAAO,CAACgB,gBAAR,CAAyBzC,gBAAgB,CAAC6B,QAAjB,CAA0B,CAA1B,EAA6Ba,UAA7B,CAAwC,CAAxC,EAA2CC,SAA3C,EAAzB,EARuB;;YAWvB7C,QAAQ,CAAC8C,eAAT,CAAyBC,KAAzB,CAA+BC,IAA/B,GAAsC,CAAtC;YAAyChD,QAAQ,CAAC8C,eAAT,CAAyBC,KAAzB,CAA+BC,IAA/B,GAAsC,IAAtC;;SAxB5C,EAHO;;QAiCPzB,IAAI,CAACC,KAAL,CAAWpB,OAAX,CAAmBU,IAAI,IAAI;cACtBU,KAAK,CAACK,OAAN,CAAcf,IAAd,MAAwB,CAAC,CAA7B,EAAgC;YAC/BA,IAAI,CAACmC,eAAL,CAAqB1B,IAAI,CAACmB,aAA1B,EAD+B;;YAI/B1C,QAAQ,CAAC8C,eAAT,CAAyBC,KAAzB,CAA+BC,IAA/B,GAAsC,CAAtC;YAAyChD,QAAQ,CAAC8C,eAAT,CAAyBC,KAAzB,CAA+BC,IAA/B,GAAsC,IAAtC;;SAL3C,EAjCO;;QA2CPzB,IAAI,CAACC,KAAL,GAAaA,KAAb;OA5CF;KADoB,CAArB;GAnC6C;;;WAuFrCP,uBAAT,GAAmC;OAC/BuB,IAAH,CAAQU,KAAR,CACCjD,aADD,EAECA,aAAa,CAACkD,MAAd,CAAqB,CAArB,EAAwBC,MAAxB,CACC7B,IAAI,IAAIA,IAAI,CAAC8B,IAAL,CAAUC,gBAAV,IACP/B,IAAI,CAAC8B,IAAL,CAAUC,gBAAV,CAA2BC,SADpB,IAEPvD,QAAQ,CAAC8C,eAAT,CAAyBU,QAAzB,CAAkCjC,IAAI,CAAC8B,IAAL,CAAUC,gBAAV,CAA2BC,SAA7D,CAHF,CAFD;GAxF6C;;;WAmGrChD,cAAT,CAAwBkD,UAAxB,EAAoC;QAC/B;;SAEArD,OAAH,CAAWC,IAAX,CAAgBoD,UAAU,CAACC,QAAX,IAAuB,EAAvC,EAA2CL,IAAI,IAAI;YAC9CA,IAAI,CAACM,YAAT,EAAuB;;;gBAGhBC,SAAS,GAAGC,kBAAkB,CAACR,IAAI,CAACM,YAAL,CAAkBG,OAAlB,CAA0B,QAA1B,EAAoC,IAApC,CAAD,CAAlB,CAA8DC,KAA9D,CAAoE,sCAApE,CAAlB;;cAEIH,SAAJ,EAAe;kBACRlB,aAAa,GAAG,OAAOkB,SAAS,CAAC,CAAD,CAAT,GAAe,MAAf,GAAwB,EAA/B,IAAqC,MAArC;YAErBI,kBAAkB,CAACJ,SAAS,CAAC,CAAD,CAAV,CAAlB,CAAiCE,OAAjC,CAAyC,MAAzC,EAAiD,GAAjD,EAAsDA,OAAtD,CAA8D,MAA9D,EAAsE,GAAtE,EAA2EA,OAA3E,CAAmF,MAAnF,EAA2F,GAA3F,EAAgGA,OAAhG,CAAwG,MAAxG,EAAgH,GAAhH,CAFqB,GAGtB,GAHA;YAKA7D,aAAa,CAACuC,IAAd,CAAmB;cAClBa,IADkB;cAElB3B,aAAa,EAAEkC,SAAS,CAAC,CAAD,CAFN;cAGlBrB,KAAK,EAAEqB,SAAS,CAAC,CAAD,CAHE;cAIlB5B,iBAAiB,EAAE4B,SAAS,CAAC,CAAD,CAAT,CAAaK,KAAb,CAAmB,SAAnB,CAJD;cAKlBvB,aALkB;cAMlBlB,KAAK,EAAE;aANR;;SAXF,MAoBO;UACNjB,cAAc,CAAC8C,IAAD,CAAd;;OAtBF;KAFD,CA2BE,OAAOa,KAAP,EAAc;;;;;;;;"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "css-has-pseudo",
3
- "version": "0.6.0",
3
+ "version": "0.10.0",
4
4
  "description": "Style elements relative to other elements in CSS",
5
5
  "author": "Jonathan Neal <jonathantneal@hotmail.com>",
6
6
  "license": "CC0-1.0",