├── .gitignore ├── README.md ├── lib └── index.js ├── package.json └── test ├── index.js ├── result.svg └── test.svg /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | .*.swp 3 | .idea 4 | node_modules 5 | *.TODO -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # svgPathify 2 | 3 | a node lib to turn svg shape elements into path svg elements 4 | 5 | #install 6 | 7 | ```js 8 | npm install svg_pathify 9 | ``` 10 | 11 | # usage 12 | 13 | ```js 14 | var svgPathify = require('svg_pathify'); 15 | 16 | var result = svgPathify(''); 17 | 18 | /* 19 | 20 | */ 21 | 22 | 23 | result = svgPathify(''); 24 | 25 | /* 26 | 27 | 28 | 29 | 30 | */ 31 | ``` 32 | -------------------------------------------------------------------------------- /lib/index.js: -------------------------------------------------------------------------------- 1 | var DOMParser = require('xmldom').DOMParser; 2 | var XMLSerializer = require('xmldom').XMLSerializer; 3 | var _ = require('lodash'); 4 | 5 | 6 | var shape = { 7 | _translatePath:function(convertObj,attributes){ 8 | var data = {} 9 | _.each(attributes,function(attribute){ 10 | data[attribute.name] = attribute.value; 11 | }) 12 | 13 | var fn = _.isFunction(convertObj.template) ? convertObj.template : 14 | function(data) { 15 | return _.template(convertObj.template)(data); 16 | } 17 | 18 | return fn(data); 19 | }, 20 | generatePathNode:function(document,node){ 21 | var convertObj,attributes,path,tagName; 22 | 23 | tagName = String(node.tagName).toLowerCase(); 24 | //polyline与polygon是同一个东西 25 | if (tagName === 'polyline') tagName = 'polygon'; 26 | 27 | convertObj = shape[tagName]; 28 | if (!convertObj) return; 29 | 30 | path = shape._translatePath(convertObj,node.attributes); 31 | if (!path) return; 32 | 33 | newPathNode = document.createElement('path'); 34 | //赋值d属性 35 | newPathNode.setAttribute('d',path); 36 | //保留其他属性 37 | _.each(node.attributes,function(attribute){ 38 | if (!_.includes(convertObj.attrs,attribute.name)) { 39 | newPathNode.setAttribute(attribute.name,attribute.value); 40 | } 41 | }) 42 | 43 | return newPathNode; 44 | 45 | }, 46 | rect:{ 47 | attrs:['x','y','width','height','rx','ry'], 48 | // template:"M<%=x%>,<%=y%>l<%=width%>,0l0,<%=height%>l<%=-width%>,0l0,<%=-height%>Z" 49 | template: function(data){ 50 | // 需要做一个保护,如果没有写属性值那么默认为0 51 | if(!data.x){ 52 | data.x = '0' 53 | } 54 | 55 | if(!data.y){ 56 | data.y = '0' 57 | } 58 | 59 | if(!data.rx && data.ry){ 60 | data.rx = data.ry 61 | } 62 | 63 | if(!data.ry && data.rx){ 64 | data.ry = data.rx 65 | } 66 | 67 | if(!data.ry && !data.rx){ 68 | data.ry = data.rx = '0' 69 | } 70 | 71 | var tpl = "M<%=x%>,<%=y%>m<%=rx%>,0l<%= width - 2 * rx %>,0q<%=rx%>,0 <%=rx%>,<%=ry%>l0,<%=height - 2 * ry %>q0,<%=ry%> <%=-rx%>,<%=ry%>l<%=-width + 2 * rx %>,0q<%=-rx%>,0 <%=-rx%>,<%=-ry%>l0,<%= - height + 2 * ry %>q0,<%=-ry%>,<%=rx%>,<%=-ry%>Z" 72 | return _.template(tpl)(data) 73 | } 74 | }, 75 | circle:{ 76 | attrs:['cx','cy','r'], 77 | template:[ 78 | "M<%=cx%>,<%=cy%>", 79 | "m<%=-r%>,0", 80 | "a<%=r%>,<%=r%>,0,1,0,<%=r * 2%>,0", 81 | "a<%=r%>,<%=r%>,0,1,0,-<%=r * 2%>,0", 82 | "Z" 83 | ].join('') 84 | }, 85 | line:{ 86 | attrs:['x1','y1','x2','y2'], 87 | template:[ 88 | "M<%=x1%>,<%=y1%>", 89 | "L<%=x2%>,<%=y2%>", 90 | "L<%=x1%>,<%=y1%>", 91 | "Z" 92 | ].join('') 93 | }, 94 | ellipse:{ 95 | attrs:['cx', 'cy', 'rx', 'ry'], 96 | template:[ 97 | "M<%=cx-rx%>,<%=cy%>", 98 | "a<%=rx%>,<%=ry%>,0,1,0,<%=rx * 2%>,0", 99 | "a<%=rx%>,<%=ry%>,0,1,0,-<%=rx * 2%>,0", 100 | "Z" 101 | ].join('') 102 | }, 103 | polygon:{ 104 | attrs:['points'], 105 | template:function(data){ 106 | data.points = data.points.replace(/(^\s*)|(\s*$)/g, ''); 107 | var points = data.points.split(' '); 108 | var p = ''; 109 | _.each(points,function(point,index){ 110 | if (index === 0) { 111 | p += 'M' + point 112 | }else{ 113 | p += 'L' + point 114 | } 115 | }) 116 | p += 'Z'; 117 | 118 | return p; 119 | } 120 | } 121 | } 122 | 123 | var transNode = function(document,node){ 124 | var convertObj,newPathNode; 125 | 126 | //基本的图形都是没有子结点的 127 | if (!node.hasChildNodes() && node.nodeName !== 'path') { 128 | 129 | newPathNode = shape.generatePathNode(document,node); 130 | newPathNode && node.parentNode.replaceChild(newPathNode,node); 131 | return; 132 | } 133 | 134 | _.each(node.childNodes,function(child){ 135 | transNode(document,child); 136 | }) 137 | 138 | } 139 | 140 | module.exports = function(svgString) { 141 | if (!svgString) return; 142 | 143 | var doc = new DOMParser().parseFromString(svgString,'application/xml'); 144 | transNode(doc,doc); 145 | 146 | return new XMLSerializer().serializeToString(doc); 147 | 148 | } 149 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "svg_pathify", 3 | "version": "0.0.8", 4 | "description": "a node lib to turn svg shape elements into path svg elements", 5 | "main": "lib/index.js", 6 | "keywords": [ 7 | "svg", 8 | "svg_pathify", 9 | "path" 10 | ], 11 | "author": "purplebamboo ", 12 | "dependencies": { 13 | "lodash": "^3.7.0", 14 | "xmldom": "^0.1.19" 15 | }, 16 | "devDependencies": {}, 17 | "repository": { 18 | "type": "git", 19 | "url": "git://github.com/purplebamboo/svgPathify.git" 20 | }, 21 | "scripts": { 22 | "test": "node ./test/index.js" 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /test/index.js: -------------------------------------------------------------------------------- 1 | var svgPathify = require('../lib/index.js'); 2 | var fs = require('fs'); 3 | var svgstr = fs.readFileSync('./test/test.svg').toString(); 4 | 5 | 6 | var a = svgPathify(svgstr); 7 | 8 | 9 | fs.writeFileSync('./test/result.svg',a); 10 | -------------------------------------------------------------------------------- /test/result.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /test/test.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | --------------------------------------------------------------------------------