5

目标 - 使用客户端:

将动态 SVG 绘图(使用 d3js 创建)转换为可下载的 PNG 图像,并使用 Internet Explorer 工作。

完成:

在 Chrome 中实现,没问题。一旦我有了 PNG DataURI,它就可以很容易地转换为可下载的 PNG blob。

不幸的是,在 IE 中运行相同的代码会产生 SecurityException,当我尝试将画布转换为 PNG DataURI ( canvas.toDataURL ) 时它会失败。

显然这是一个活跃的IE BUG,我在 StackExchange 上发现其他人也有同样的问题。我相信这与应用于来自其他域(并在画布中绘制)的图像的 CORS 限制有关,但我的 SVG 来自本地页面。

想法

想知道原因是否与我为IMG 元素呈现的 SVG 绘图生成初始 DataURI ( data:image/svg+xml ) 的方式有关。

我已经尝试了两种替代方法来生成image/svg+xml、 base64 和 charset=utf8,但它们并没有解决遇到的问题。所以想知道它是否是 SVG 的内容,目前 SVG 绘图中没有图像。

参考代码:

var rawSvg = new XMLSerializer().serializeToString(svgElement);

var img3 = new Image();
document.body.appendChild(img3);
var canv = document.createElement("canvas");
var canv_ctx = canv.getContext("2d");

img3.onload = function () {
   //-- Image has loaded using the native data:image/svg+xml 
   canv_ctx.drawImage(this, 0, 0);

   //-- IE Will throw a Security Exception here...
   console.log(canv.toDataURL("image/png")); 
};

img3.src = "data:image/svg+xml;base64," + btoa(rawSvg);
//-- Or utf8
//img3.src = "data:image/svg+xml;charset=utf8," + encodeURIComponent(rawSvg);

更新:

测试了 Canvg 对绘制到画布上的2d 上下文“ drawSvg(...) ”的扩展。这克服了在画布元素上调用 toDataURL 时的 SecurityException,但是绘制函数对于文本渲染和放置不够准确。所以我仍然需要一个解决方案。

查看示例屏幕截图,左侧使用原生 drawImage 进行正确渲染,右侧使用 Canvg 的 drawSvg 进行错误渲染

使用 Canvg 的代码 - 注意:您需要参考 JS

var canvas = document.createElement("canvas"),
    cctx = canvas.getContext("2d");
var rawSvg = new XMLSerializer().serializeToString(svgClone.node());
canvas.width = svgWidth;
canvas.height = svgHeight;
//cctx.drawImage(this, 0, 0);
//-- Use Canvg's extension to canvasContext
cctx.drawSvg(rawSvg);
//-- This Works on IE - not accurate though
var dataURL = canvas.toDataURL();
4

0 回答 0