diff --git a/plugins/reusePaths.js b/plugins/reusePaths.js index 022b1c036..1704b16b2 100644 --- a/plugins/reusePaths.js +++ b/plugins/reusePaths.js @@ -1,5 +1,6 @@ 'use strict'; +const { collectStylesheet } = require('../lib/style'); const { detachNodeFromParent, querySelectorAll } = require('../lib/xast'); /** @@ -22,7 +23,9 @@ exports.description = * * @type {import('./plugins-types').Plugin<'reusePaths'>} */ -exports.fn = () => { +exports.fn = (root) => { + const stylesheet = collectStylesheet(root); + /** * @type {Map>} */ @@ -101,25 +104,31 @@ exports.fn = () => { let index = 0; for (const list of paths.values()) { if (list.length > 1) { - // add reusable path to defs - /** - * @type {XastElement} - */ + /** @type {XastElement} */ const reusablePath = { type: 'element', name: 'path', - attributes: { ...list[0].attributes }, + attributes: {}, children: [], }; - delete reusablePath.attributes.transform; - let id; - const reusablePathId = reusablePath.attributes.id; - if (reusablePathId == null || hrefs.has(reusablePathId)) { - id = 'reuse-' + index; - index += 1; - reusablePath.attributes.id = id; + + for (const attr of ['fill', 'stroke', 'd']) { + if (list[0].attributes[attr] != null) { + reusablePath.attributes[attr] = list[0].attributes[attr]; + } + } + + const originalId = list[0].attributes.id; + if ( + originalId == null || + hrefs.has(originalId) || + stylesheet.rules.some( + (rule) => rule.selector === `#${originalId}` + ) + ) { + reusablePath.attributes.id = 'reuse-' + index++; } else { - id = reusablePath.attributes.id; + reusablePath.attributes.id = originalId; delete list[0].attributes.id; } // TODO remove legacy parentNode in v4 @@ -155,7 +164,8 @@ exports.fn = () => { } for (const name of ['href', 'xlink:href']) { if (child.attributes[name] != null) { - child.attributes[name] = '#' + id; + child.attributes[name] = + '#' + reusablePath.attributes.id; } } } @@ -164,7 +174,8 @@ exports.fn = () => { } pathNode.name = 'use'; - pathNode.attributes['xlink:href'] = '#' + id; + pathNode.attributes['xlink:href'] = + '#' + reusablePath.attributes.id; } } } diff --git a/test/plugins/reusePaths.01.svg b/test/plugins/reusePaths.01.svg index e177f845a..ad2dd2ad0 100644 --- a/test/plugins/reusePaths.01.svg +++ b/test/plugins/reusePaths.01.svg @@ -18,7 +18,7 @@ - + diff --git a/test/plugins/reusePaths.02.svg b/test/plugins/reusePaths.02.svg index 4e7181e5f..cd75b449a 100644 --- a/test/plugins/reusePaths.02.svg +++ b/test/plugins/reusePaths.02.svg @@ -11,8 +11,8 @@ - - + + diff --git a/test/plugins/reusePaths.05.svg b/test/plugins/reusePaths.05.svg index 7cfd410c5..5b3363446 100644 --- a/test/plugins/reusePaths.05.svg +++ b/test/plugins/reusePaths.05.svg @@ -24,7 +24,7 @@ an ID attribute. - + diff --git a/test/plugins/reusePaths.06.svg b/test/plugins/reusePaths.06.svg index a96d550c4..7efa7f9dd 100644 --- a/test/plugins/reusePaths.06.svg +++ b/test/plugins/reusePaths.06.svg @@ -23,7 +23,7 @@ in an href by another node. - +