From e3ffce919fa86e5e0fd624d62723f6ad26ba153a Mon Sep 17 00:00:00 2001 From: Joe Lencioni Date: Mon, 20 Mar 2017 16:57:22 -0700 Subject: [PATCH] Use defaultProps instead of adding props to the svg Currently, when transforming an SVG file that has attributes on the top-level `` element, the transformed component ends up looking something like this: ```js _extends({ xmlns: 'http://www.w3.org/2000/svg', viewBox: '0 0 1000 1000' }, props), ``` this adds the overhead of _extends. I think it might be a better to instead move these values into `defaultProps` on the generated component. Closes #7 --- src/index.js | 39 ++++++++++++++++++++++++++++++++++++--- 1 file changed, 36 insertions(+), 3 deletions(-) diff --git a/src/index.js b/src/index.js index 3fef0a1..a34c30c 100644 --- a/src/index.js +++ b/src/index.js @@ -12,6 +12,11 @@ const buildSvg = template(` var SVG_NAME = function SVG_NAME(props) { return SVG_CODE; }; `); +const buildSvgWithDefaults = template(` + var SVG_NAME = function SVG_NAME(props) { return SVG_CODE; }; + SVG_NAME.defaultProps = SVG_DEFAULT_PROPS_CODE; +`); + let ignoreRegex; export default ({ types: t }) => ({ @@ -45,12 +50,40 @@ export default ({ types: t }) => ({ const svgCode = traverse.removeProperties(parsedSvgAst.program.body[0].expression); - const svgReplacement = buildSvg({ + const opts = { SVG_NAME: importIdentifier, SVG_CODE: svgCode, - }); + }; + + // Move props off of element and into defaultProps + if (svgCode.openingElement.attributes.length > 1) { + const keepProps = []; + const defaultProps = []; - path.replaceWith(svgReplacement); + svgCode.openingElement.attributes.forEach((prop) => { + if (prop.type === 'JSXSpreadAttribute') { + keepProps.push(prop); + } else { + defaultProps.push( + t.objectProperty( + t.identifier(prop.name.name), + prop.value, + ) + ); + } + }); + + svgCode.openingElement.attributes = keepProps; + opts.SVG_DEFAULT_PROPS_CODE = t.objectExpression(defaultProps); + } + + if (opts.SVG_DEFAULT_PROPS_CODE) { + const svgReplacement = buildSvgWithDefaults(opts); + path.replaceWithMultiple(svgReplacement); + } else { + const svgReplacement = buildSvg(opts); + path.replaceWith(svgReplacement); + } } }, },