UNPKG

svg-parse-path-normalized

Version:

Parse svg path data from string and normalize it to calculable value arrays

207 lines (168 loc) 5.71 kB
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Parse pathdata – convert plugin</title> <style> body { font-family: 'Fira Sans', 'Segoe UI', sans-serif; } svg { width: 100%; overflow: visible; border: 1px solid #ccc; } .grd { display: grid; grid-template-columns: 1fr 1fr; gap: 2em; height: 95vh; } .col { height: 100%; display: flex; flex-direction: column; gap: 0; justify-content: flex-start; } .col>* { margin-top: 0; margin-bottom: 1rem; } textarea { width: 100%; display: block; min-height: 10em; flex: 1 1 auto; resize: vertical; } input {} input[type="range"] { width: 100%; display: block; } input[type="checkbox"] { margin-right: 0.5em; } label { display: inline-block; line-height: 1.4em; margin: 0; margin-right: 0.5em; } code { background: #eee; display: inline-block; padding: 0.5em; margin-right:0.3em; } #pErrors { font-weight: 700; color: red; } input[type="number"] { width: 4em; } </style> </head> <body> <div class="grd"> <div class="col"> <svg id="svg" viewBox="0 0 100 100"> <path id="path" fill="none" stroke="black" d="M3,7 L13,7 m-20,10 l10,0 V27 H23 v10 h10 C 33,43 38,47 43,47 c 0,5 5,10 10,10 S 63,67 63,67 s -10,10 10,10 Q 50,50 73,57 q 20,-5 0,-10 T 70,40 t 0,-15 A 5, 10 45 10 40,20 a5,5 20 01 -10,-10 Z " /> <path id="path2" fill="none" stroke="green" stroke-width="0.5" /> </svg> </div> <div class="col"> <h1>Convert pathData</h1> <h2>Parse pathdata via <a href="https://github.com/jarek-foksa/path-data-polyfill">Jarek Foksa's polyfill</a> and convert it</h2> <p>If it ever gets implemented by natively supported <code>getpathData()</code><code>setpathData()</code> methods</p> <textarea id="svgOut"></textarea> </div> </div> <script src="https://cdn.jsdelivr.net/npm/path-data-polyfill@1.0.4/path-data-polyfill.min.js"></script> <script src="../js/pathDataConvert.js"></script> <script> let options = { //normalize: true, //optimize: true, //toAbsolute: true, toRelative: true, //quadraticToCubic: true, cubicToQuadratic: true, cubicToQuadraticPrecision: 0.1, lineToCubic: true, //toLonghands: true, toShorthands: true, arcToCubic: true, //arcParam: false, arcAccuracy: 1, decimals: 1, } const pathData = path.getPathData().convert(options) path2.setPathData(pathData); svgOut.value = pathDataToD(pathData) /** * serialize pathData array to * d attribute string */ function pathDataToD(pathData, decimals = -1, minify = false) { // implicit l command if (pathData[1].type === "l" && minify) { pathData[0].type = "m"; } let d = `${pathData[0].type}${pathData[0].values.join(" ")}`; for (let i = 1; i < pathData.length; i++) { let com0 = pathData[i - 1]; let com = pathData[i]; let { type, values } = com; // minify arctos if (minify && type === 'A' || type === 'a') { values = [values[0], values[1], values[2], [values[3], values[4], values[5]].join(''), values[6]] } // round if (values.length && decimals > -1) { values = values.map(val => { return typeof val === 'number' ? +val.toFixed(decimals) : val }) } // omit type for repeated commands type = (com0.type === com.type && com.type.toLowerCase() != 'm' && minify) ? " " : ( (com0.type === "m" && com.type === "l") || (com0.type === "M" && com.type === "l") || (com0.type === "M" && com.type === "L") ) && minify ? " " : com.type; d += `${type}${values.join(" ")}`; } if (minify) { d = d .replaceAll(" 0.", " .") .replaceAll(" -", "-") .replaceAll("-0.", "-.") .replaceAll("Z", "z"); } return d; } </script> </body> </html>