svg 导出成图片会有很多限制, 外链的图片, 样式均会丢失,推荐使用 saveSvgAsPng.js 进行导出
以下是借鉴库写的导出函数:
function reEncode(data) { return decodeURIComponent( encodeURIComponent(data).replace(/%([0-9A-F]{2})/g, (match, p1) => { const c = String.fromCharCode(`0x${p1}`); return c === '%' ? '%25' : c; }) ) } function export2Base64Img(svgDom, MIMEType, option) { var serializer = new XMLSerializer(); var source = serializer.serializeToString(svgDom); // 方式一: unescape(encodeURIComponent(txt)) // var path = "data:image/svg+xml;base64," + window.btoa(unescape(encodeURIComponent(source))); // 方式二: decodeURIComponent(encodeURIComponent(txt)) var path = "data:image/svg+xml;base64," + window.btoa(reEncode(source)); var canvas = document.createElement("canvas"), context = canvas.getContext("2d"), img = new Image(), pixelRatio = window.devicePixelRatio || 1, _exportPath, handler option = option || {}; canvas.width = parseFloat(svgDom.getAttribute('width')); // * pixelRatio canvas.height = parseFloat(svgDom.getAttribute('height')); // * pixelRatio img.src = path; img.onload = function () { // 增加底色 if (option.background) { context.beginPath(); context.rect(0, 0, canvas.width, canvas.height); context.fillStyle = option.background; context.fill(); context.closePath(); } // context.drawImage(img, 0, 0); var marker = option.watermark || ""; if (marker) { context.font = "18px 微软雅黑"; context.fillStyle = "rgba(12, 0, 70, 0.5)"; var textWidth = context.measureText(marker).width, textHegith = 50, pk = 1.2, rotate = (option.rotation || -45) * Math.PI / 180, sinReg = Math.sin(rotate), cosReg = Math.cos(rotate), width = Math.abs(canvas.width * cosReg) + Math.abs(canvas.height * sinReg), height = Math.abs(canvas.height * cosReg) + Math.abs(canvas.width * sinReg); var xf = Math.ceil(width / textWidth * pk); var yf = Math.ceil(height / textHegith); context.rotate(rotate); for (var i = 0; i < yf; i++) { for (var k = 0; k < xf; k++) { context.fillText(marker, textWidth * k * pk - canvas.height * cosReg, textHegith * i) } } } document.body.appendChild(canvas); _exportPath = canvas.toDataURL(MIMEType || 'image/png', 1) typeof handler === 'function' && handler(_exportPath) document.body.removeChild(canvas) } return new Promise(function (resolve, reject) { handler = resolve }) }