JavaScript 下载svg图片为png格式


Posted in Javascript onJune 21, 2018

1.遇到需要将svg下载的需求,网上找了一些代码,地址是这个https://github.com/exupero/saveSvgAsPng,但是不太好用,莫名的把网页所有的svg都下载了,于是在源码的基础上做了一些小的修改;代码如下所示

var doctype = '<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" [<!ENTITY nbsp " ">]>'; 
function convertToPng(src, w, h) { 
      var canvas = document.createElement('canvas'); 
      var context = canvas.getContext('2d'); 
      canvas.width = w; 
      canvas.height = h; 
      context.drawImage(src, 0, 0); 
      var png; 
      try { 
        png = canvas.toDataURL("image/png"); 
      } catch (e) { 
        if ((typeof SecurityError !== 'undefined' && e instanceof SecurityError) || e.name == "SecurityError") { 
          console.error("Rendered SVG images cannot be downloaded in this browser."); 
          return; 
        } else { 
          throw e; 
        } 
      } 
      return png; 
    } 
    function isElement(obj) { 
      return obj instanceof HTMLElement || obj instanceof SVGElement; 
    } 
    function reEncode(data) { 
      data = encodeURIComponent(data); 
      data = data.replace(/%([0-9A-F]{2})/g, function (match, p1) { 
        var c = String.fromCharCode('0x' + p1); 
        return c === '%' ? '%25' : c; 
      }); 
      return decodeURIComponent(data); 
    } 
    function uriToBlob(uri) { 
      var byteString = window.atob(uri.split(',')[1]); 
      var mimeString = uri.split(',')[0].split(':')[1].split(';')[0] 
      var buffer = new ArrayBuffer(byteString.length); 
      var intArray = new Uint8Array(buffer); 
      for (var i = 0; i < byteString.length; i++) { 
        intArray[i] = byteString.charCodeAt(i); 
      } 
      return new Blob([buffer], {type: mimeString}); 
    } 
    function downLoad(el, name) { 
      if (!isElement(el)) { 
        throw new Error('an HTMLElement or SVGElement is required; got ' + el); 
      } 
      if (!name) { 
        console.error("文件名为空!"); 
        return; 
      } 
      var xmlns = "http://www.w3.org/2000/xmlns/"; 
      var clone = el.cloneNode(true); 
      clone.setAttribute("version", "1.1"); 
      if (!clone.getAttribute('xmlns')) { 
        clone.setAttributeNS(xmlns, "xmlns", "http://www.w3.org/2000/svg"); 
      } 
      if (!clone.getAttribute('xmlns:xlink')) { 
        clone.setAttributeNS(xmlns, "xmlns:xlink", "http://www.w3.org/1999/xlink"); 
      } 
      var svg = clone.outerHTML; 
      var uri = 'data:image/svg+xml;base64,' + window.btoa(reEncode(doctype + svg)); 
      var image = new Image(); 
      image.onload = function () { 
        var png = convertToPng(image, image.width, image.height); 
        var saveLink = document.createElement('a'); 
        var downloadSupported = 'download' in saveLink; 
        if (downloadSupported) { 
          saveLink.download = name + ".png"; 
          saveLink.style.display = 'none'; 
          document.body.appendChild(saveLink); 
          try { 
            var blob = uriToBlob(png); 
            var url = URL.createObjectURL(blob); 
            saveLink.href = url; 
            saveLink.onclick = function () { 
              requestAnimationFrame(function () { 
                URL.revokeObjectURL(url); 
              }) 
            }; 
          } catch (e) { 
            saveLink.href = uri; 
          } 
          saveLink.click(); 
          document.body.removeChild(saveLink); 
        } 
      }; 
      image.src = uri; 
    }

这里使用的时候只需要调用download方法就可以了,建议封装成一个单独的下载服务;download方法的第一个参数el指的是dom元素,就是svg元素,具体的获取方法通过js或者d3的选择器都可以;例如

<div id="svg-parent-div"><svg>...</svg></div>

一般通过获取svg的父元素来找到它,比如

var el = d3.select("#svg-parent-div").node().children[0]; 
download(el,"下载图片");

这样就可以了;

代码对于svg的没设置命名空间的情况做了处理,通过如下代码,如果svg 元素没有 设置命名空间,则添加; 

el.setAttributeNS(xmlns, "xmlns", "http://www.w3.org/2000/svg"); 
el.setAttributeNS(xmlns, "xmlns:xlink", "http://www.w3.org/1999/xlink");

同时,添加的命名空间作用在clone的元素上,不会影响原来的svg元素;

总结

以上所述是小编给大家介绍的JavaScript 下载svg图片为png格式,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
Javascript 模式实例 观察者模式
Oct 24 Javascript
JS获得URL超链接的参数值实例代码
Jun 21 Javascript
JS组件Bootstrap Table布局详解
May 27 Javascript
jQuery动态产生select option下拉列表
Mar 15 Javascript
react native实现往服务器上传网络图片的实例
Aug 07 Javascript
通过vue-router懒加载解决首次加载时资源过多导致的速度缓慢问题
Apr 08 Javascript
你应该了解的JavaScript Array.map()五种用途小结
Nov 14 Javascript
Vue唯一可以更改vuex实例中state数据状态的属性对象Mutation的讲解
Jan 18 Javascript
Vue指令v-for遍历输出JavaScript数组及json对象的常见方式小结
Feb 11 Javascript
JS异步执行结果获取的3种解决方式
Feb 19 Javascript
弱类型语言javascript中 a,b 的运算实例小结
Aug 07 Javascript
解决vant的Toast组件时提示not defined的问题
Nov 11 Javascript
MVVM 双向绑定的实现代码
Jun 21 #Javascript
在vue2.0中引用element-ui组件库的方法
Jun 21 #Javascript
vue树形结构获取键值的方法示例
Jun 21 #Javascript
vue使用jsonp抓取qq音乐数据的方法
Jun 21 #Javascript
Vue 获取数组键名的方法
Jun 21 #Javascript
Taro集成Redux快速上手的方法示例
Jun 21 #Javascript
vue2.0项目实现路由跳转的方法详解
Jun 21 #Javascript
You might like
用PHP创建PDF中文文档
2006/10/09 PHP
php中的数组操作函数整理
2008/08/18 PHP
phalcon框架使用指南
2016/02/23 PHP
TP5框架实现的数据库备份功能示例
2020/04/05 PHP
删除重复数据的算法
2006/11/23 Javascript
JavaScript 入门·JavaScript 具有全范围的运算符
2007/10/01 Javascript
javascript 多浏览器 事件大全
2010/03/23 Javascript
location.search在客户端获取Url参数的方法
2010/06/08 Javascript
jquery offset函数应用实例
2012/11/14 Javascript
简单实用的反馈表单无刷新提交带验证
2013/11/15 Javascript
angularJS 中input示例分享
2015/02/09 Javascript
jQuery简单实现禁用右键菜单
2015/03/10 Javascript
Backbone.js的Hello World程序实例
2015/06/19 Javascript
jQuery实现图片走马灯效果的原理分析
2016/01/16 Javascript
AngularJS中的表单简单入门
2016/07/28 Javascript
Angular指令之restict匹配模式的详解
2017/07/27 Javascript
JS字符串去除连续或全部重复字符的实例
2018/03/08 Javascript
解决Nodejs全局安装模块后找不到命令的问题
2018/05/15 NodeJs
vue 优化CDN加速的方法示例
2018/09/19 Javascript
详解如何使用node.js的开发框架express创建一个web应用
2018/12/20 Javascript
JS实现骰子3D旋转效果
2019/10/24 Javascript
js 计数排序的实现示例(升级版)
2020/01/12 Javascript
详解Vue3 Composition API中的提取和重用逻辑
2020/04/29 Javascript
javascript实现文字跑马灯效果
2020/06/18 Javascript
利用Python如何生成hash值示例详解
2017/12/20 Python
使用python对文件中的单词进行提取的方法示例
2018/12/21 Python
Python虚拟环境的原理及使用详解
2019/07/02 Python
python查找重复图片并删除(图片去重)
2019/07/16 Python
给ubuntu18安装python3.7的详细教程
2020/06/08 Python
英国舒适型鞋履品牌:FitFlop
2017/05/17 全球购物
创建索引时需要注意的事项
2013/05/13 面试题
博士学位自我鉴定范文
2013/12/26 职场文书
三项教育活动实施方案
2014/03/30 职场文书
公司委托书怎么写
2014/08/02 职场文书
2014年商场国庆节活动策划方案
2014/09/16 职场文书
详解CSS开发过程中的20个快速提升技巧
2021/05/21 HTML / CSS