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.
126 lines
3.1 KiB
126 lines
3.1 KiB
"use strict"; |
|
|
|
exports.__esModule = true; |
|
exports.default = svgoPlugin; |
|
|
|
var _svgo = _interopRequireDefault(require("svgo")); |
|
|
|
var _cosmiconfig = _interopRequireDefault(require("cosmiconfig")); |
|
|
|
var _mergeDeep = _interopRequireDefault(require("merge-deep")); |
|
|
|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } |
|
|
|
/* eslint-disable no-underscore-dangle */ |
|
const explorer = (0, _cosmiconfig.default)('svgo', { |
|
searchPlaces: ['package.json', '.svgorc', '.svgorc.json', '.svgorc.yaml', '.svgorc.yml', 'svgo.config.js', '.svgo.yml'], |
|
transform: result => result && result.config, |
|
cache: true |
|
}); |
|
|
|
function encodeSVGDatauri(str, type) { |
|
let prefix = 'data:image/svg+xml'; // base64 |
|
|
|
if (!type || type === 'base64') { |
|
prefix += ';base64,'; |
|
|
|
if (Buffer.from) { |
|
str = prefix + Buffer.from(str).toString('base64'); |
|
} else { |
|
// eslint-disable-next-line |
|
str = prefix + new Buffer(str).toString('base64'); |
|
} // URI encoded |
|
|
|
} else if (type === 'enc') { |
|
str = `${prefix},${encodeURIComponent(str)}`; // unencoded |
|
} else if (type === 'unenc') { |
|
str = `${prefix},${str}`; |
|
} |
|
|
|
return str; |
|
} // See https://github.com/svg/svgo/blob/master/lib/svgo.js#L24 |
|
// _optimizeOnce is synchronous internally |
|
|
|
|
|
function optimizeSync(svgstr, info) { |
|
const { |
|
config |
|
} = this; |
|
|
|
if (config.error) { |
|
throw config.error; |
|
} |
|
|
|
const maxPassCount = config.multipass ? 10 : 1; |
|
let counter = 0; |
|
let prevResultSize = Number.POSITIVE_INFINITY; |
|
let result; |
|
|
|
const optimizeOnceCallback = svgjs => { |
|
if (svgjs.error) { |
|
throw svgjs.error; |
|
} // eslint-disable-next-line no-plusplus |
|
|
|
|
|
if (++counter < maxPassCount && svgjs.data.length < prevResultSize) { |
|
prevResultSize = svgjs.data.length; |
|
|
|
this._optimizeOnce(svgjs.data, info, optimizeOnceCallback); |
|
} else { |
|
if (config.datauri) { |
|
svgjs.data = encodeSVGDatauri(svgjs.data, config.datauri); |
|
} |
|
|
|
if (info.path) { |
|
svgjs.path = info.path; |
|
} |
|
|
|
result = svgjs; |
|
} |
|
}; |
|
|
|
this._optimizeOnce(svgstr, info, optimizeOnceCallback); |
|
|
|
return result; |
|
} |
|
|
|
function getBaseSvgoConfig(config) { |
|
const baseSvgoConfig = { |
|
plugins: [{ |
|
prefixIds: true |
|
}] |
|
}; |
|
if (config.icon || config.dimensions === false) baseSvgoConfig.plugins.push({ |
|
removeViewBox: false |
|
}); |
|
return baseSvgoConfig; |
|
} |
|
|
|
function getFilePath(state) { |
|
return state.filePath || process.cwd(); |
|
} |
|
|
|
function createSvgo(config, rcConfig) { |
|
const mergedConfig = (0, _mergeDeep.default)(getBaseSvgoConfig(config), rcConfig, config.svgoConfig); |
|
return new _svgo.default(mergedConfig); |
|
} |
|
|
|
function getInfo(state) { |
|
return state.filePath ? { |
|
input: 'file', |
|
path: state.filePath |
|
} : { |
|
input: 'string' |
|
}; |
|
} |
|
|
|
function svgoPlugin(code, config, state) { |
|
if (!config.svgo) return code; |
|
const filePath = getFilePath(state); |
|
const svgoRcConfig = config.runtimeConfig ? explorer.searchSync(filePath) : {}; |
|
const svgo = createSvgo(config, svgoRcConfig); |
|
const { |
|
data |
|
} = optimizeSync.call(svgo, code, getInfo(state)); |
|
return data; |
|
} |