It appears you have a well-structured Git repository with various files, including SVG icons and HTML documents. Here's a brief overview:
This commit is contained in:
168
backend/node_modules/svgo/plugins/convertOneStopGradients.js
generated
vendored
Normal file
168
backend/node_modules/svgo/plugins/convertOneStopGradients.js
generated
vendored
Normal file
@@ -0,0 +1,168 @@
|
||||
'use strict';
|
||||
|
||||
/**
|
||||
* @typedef {import('../lib/types').XastElement} XastElement
|
||||
* @typedef {import('../lib/types').XastParent} XastParent
|
||||
*/
|
||||
|
||||
const { attrsGroupsDefaults, colorsProps } = require('./_collections');
|
||||
const {
|
||||
detachNodeFromParent,
|
||||
querySelectorAll,
|
||||
querySelector,
|
||||
} = require('../lib/xast');
|
||||
const { computeStyle, collectStylesheet } = require('../lib/style');
|
||||
|
||||
exports.name = 'convertOneStopGradients';
|
||||
exports.description =
|
||||
'converts one-stop (single color) gradients to a plain color';
|
||||
|
||||
/**
|
||||
* Converts one-stop (single color) gradients to a plain color.
|
||||
*
|
||||
* @author Seth Falco <seth@falco.fun>
|
||||
* @type {import('./plugins-types').Plugin<'convertOneStopGradients'>}
|
||||
* @see https://developer.mozilla.org/docs/Web/SVG/Element/linearGradient
|
||||
* @see https://developer.mozilla.org/docs/Web/SVG/Element/radialGradient
|
||||
*/
|
||||
exports.fn = (root) => {
|
||||
const stylesheet = collectStylesheet(root);
|
||||
|
||||
/**
|
||||
* Parent defs that had gradients elements removed from them.
|
||||
*
|
||||
* @type {Set<XastElement>}
|
||||
*/
|
||||
const effectedDefs = new Set();
|
||||
|
||||
/**
|
||||
* @type {Map<XastElement, XastParent>}
|
||||
*/
|
||||
const allDefs = new Map();
|
||||
|
||||
/**
|
||||
* @type {Map<XastElement, XastParent>}
|
||||
*/
|
||||
const gradientsToDetach = new Map();
|
||||
|
||||
/** Number of references to the xlink:href attribute. */
|
||||
let xlinkHrefCount = 0;
|
||||
|
||||
return {
|
||||
element: {
|
||||
enter: (node, parentNode) => {
|
||||
if (node.attributes['xlink:href'] != null) {
|
||||
xlinkHrefCount++;
|
||||
}
|
||||
|
||||
if (node.name === 'defs') {
|
||||
allDefs.set(node, parentNode);
|
||||
return;
|
||||
}
|
||||
|
||||
if (node.name !== 'linearGradient' && node.name !== 'radialGradient') {
|
||||
return;
|
||||
}
|
||||
|
||||
const stops = node.children.filter((child) => {
|
||||
return child.type === 'element' && child.name === 'stop';
|
||||
});
|
||||
|
||||
const href = node.attributes['xlink:href'] || node.attributes['href'];
|
||||
let effectiveNode =
|
||||
stops.length === 0 && href != null && href.startsWith('#')
|
||||
? querySelector(root, href)
|
||||
: node;
|
||||
|
||||
if (effectiveNode == null || effectiveNode.type !== 'element') {
|
||||
gradientsToDetach.set(node, parentNode);
|
||||
return;
|
||||
}
|
||||
|
||||
const effectiveStops = effectiveNode.children.filter((child) => {
|
||||
return child.type === 'element' && child.name === 'stop';
|
||||
});
|
||||
|
||||
if (
|
||||
effectiveStops.length !== 1 ||
|
||||
effectiveStops[0].type !== 'element'
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (parentNode.type === 'element' && parentNode.name === 'defs') {
|
||||
effectedDefs.add(parentNode);
|
||||
}
|
||||
|
||||
gradientsToDetach.set(node, parentNode);
|
||||
|
||||
let color;
|
||||
const style = computeStyle(stylesheet, effectiveStops[0])['stop-color'];
|
||||
if (style != null && style.type === 'static') {
|
||||
color = style.value;
|
||||
}
|
||||
|
||||
const selectorVal = `url(#${node.attributes.id})`;
|
||||
|
||||
const selector = [...colorsProps]
|
||||
.map((attr) => `[${attr}="${selectorVal}"]`)
|
||||
.join(',');
|
||||
const elements = querySelectorAll(root, selector);
|
||||
for (const element of elements) {
|
||||
if (element.type !== 'element') {
|
||||
continue;
|
||||
}
|
||||
|
||||
for (const attr of colorsProps) {
|
||||
if (element.attributes[attr] !== selectorVal) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (color != null) {
|
||||
element.attributes[attr] = color;
|
||||
} else {
|
||||
delete element.attributes[attr];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const styledElements = querySelectorAll(
|
||||
root,
|
||||
`[style*=${selectorVal}]`,
|
||||
);
|
||||
for (const element of styledElements) {
|
||||
if (element.type !== 'element') {
|
||||
continue;
|
||||
}
|
||||
|
||||
element.attributes.style = element.attributes.style.replace(
|
||||
selectorVal,
|
||||
color || attrsGroupsDefaults.presentation['stop-color'],
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
exit: (node) => {
|
||||
if (node.name === 'svg') {
|
||||
for (const [gradient, parent] of gradientsToDetach.entries()) {
|
||||
if (gradient.attributes['xlink:href'] != null) {
|
||||
xlinkHrefCount--;
|
||||
}
|
||||
|
||||
detachNodeFromParent(gradient, parent);
|
||||
}
|
||||
|
||||
if (xlinkHrefCount === 0) {
|
||||
delete node.attributes['xmlns:xlink'];
|
||||
}
|
||||
|
||||
for (const [defs, parent] of allDefs.entries()) {
|
||||
if (effectedDefs.has(defs) && defs.children.length === 0) {
|
||||
detachNodeFromParent(defs, parent);
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
};
|
||||
};
|
Reference in New Issue
Block a user