You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
95 lines
2.6 KiB
95 lines
2.6 KiB
2 years ago
|
'use strict';
|
||
|
|
||
|
const { parseSvg } = require('./parser.js');
|
||
|
const { stringifySvg } = require('./stringifier.js');
|
||
|
const { builtin } = require('./builtin.js');
|
||
|
const { invokePlugins } = require('./svgo/plugins.js');
|
||
|
const { encodeSVGDatauri } = require('./svgo/tools.js');
|
||
|
|
||
|
const pluginsMap = {};
|
||
|
for (const plugin of builtin) {
|
||
|
pluginsMap[plugin.name] = plugin;
|
||
|
}
|
||
|
|
||
|
const resolvePluginConfig = (plugin) => {
|
||
|
if (typeof plugin === 'string') {
|
||
|
// resolve builtin plugin specified as string
|
||
|
const builtinPlugin = pluginsMap[plugin];
|
||
|
if (builtinPlugin == null) {
|
||
|
throw Error(`Unknown builtin plugin "${plugin}" specified.`);
|
||
|
}
|
||
|
return {
|
||
|
name: plugin,
|
||
|
params: {},
|
||
|
fn: builtinPlugin.fn,
|
||
|
};
|
||
|
}
|
||
|
if (typeof plugin === 'object' && plugin != null) {
|
||
|
if (plugin.name == null) {
|
||
|
throw Error(`Plugin name should be specified`);
|
||
|
}
|
||
|
// use custom plugin implementation
|
||
|
let fn = plugin.fn;
|
||
|
if (fn == null) {
|
||
|
// resolve builtin plugin implementation
|
||
|
const builtinPlugin = pluginsMap[plugin.name];
|
||
|
if (builtinPlugin == null) {
|
||
|
throw Error(`Unknown builtin plugin "${plugin.name}" specified.`);
|
||
|
}
|
||
|
fn = builtinPlugin.fn;
|
||
|
}
|
||
|
return {
|
||
|
name: plugin.name,
|
||
|
params: plugin.params,
|
||
|
fn,
|
||
|
};
|
||
|
}
|
||
|
return null;
|
||
|
};
|
||
|
|
||
|
const optimize = (input, config) => {
|
||
|
if (config == null) {
|
||
|
config = {};
|
||
|
}
|
||
|
if (typeof config !== 'object') {
|
||
|
throw Error('Config should be an object');
|
||
|
}
|
||
|
const maxPassCount = config.multipass ? 10 : 1;
|
||
|
let prevResultSize = Number.POSITIVE_INFINITY;
|
||
|
let output = '';
|
||
|
const info = {};
|
||
|
if (config.path != null) {
|
||
|
info.path = config.path;
|
||
|
}
|
||
|
for (let i = 0; i < maxPassCount; i += 1) {
|
||
|
info.multipassCount = i;
|
||
|
const ast = parseSvg(input, config.path);
|
||
|
const plugins = config.plugins || ['preset-default'];
|
||
|
if (Array.isArray(plugins) === false) {
|
||
|
throw Error(
|
||
|
"Invalid plugins list. Provided 'plugins' in config should be an array."
|
||
|
);
|
||
|
}
|
||
|
const resolvedPlugins = plugins.map(resolvePluginConfig);
|
||
|
const globalOverrides = {};
|
||
|
if (config.floatPrecision != null) {
|
||
|
globalOverrides.floatPrecision = config.floatPrecision;
|
||
|
}
|
||
|
invokePlugins(ast, info, resolvedPlugins, null, globalOverrides);
|
||
|
output = stringifySvg(ast, config.js2svg);
|
||
|
if (output.length < prevResultSize) {
|
||
|
input = output;
|
||
|
prevResultSize = output.length;
|
||
|
} else {
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
if (config.datauri) {
|
||
|
output = encodeSVGDatauri(output, config.datauri);
|
||
|
}
|
||
|
return {
|
||
|
data: output,
|
||
|
};
|
||
|
};
|
||
|
exports.optimize = optimize;
|