对象 HTMLImageElement 不能是 Internet Explorer 中的 "saved as" 图片
object HTMLImageElement cannot be "saved as" image in Internet Explorer
我尝试:使用 D3 创建一个 SVG 元素,单击一个按钮将其转换为使用 CANVAS 的图像,因此可以右键单击并 "saved as" 图像。
问题:[object HTMLImageElement] 对象在 Internet Explorer 中不可见 "image" 所以当我右键单击它时,它不会提示 "Save image as..."选项。在 Chrome 和 Firefox 中它工作正常。
我有以下 HTML 代码:
<input type="button" id="toPngBtn" value="Save" /><br />
<div id="myDiv"></div>
<div id="exportDiv"></div>
以及以下 javascript 代码:
//Make an SVG Container
var svgContainer = d3.select("#myDiv").append("svg")
.attr("id", "myCircle")
.attr("width", 60)
.attr("height", 60);
//Draw the Circle
var circle = svgContainer.append("circle")
.attr("cx", 30)
.attr("cy", 30)
.attr("r", 20);
// Save button to
d3.select("#toPngBtn").on("click", function () {
var svg = document.getElementById('myCircle');
var xml = new XMLSerializer().serializeToString(svg);
var data = "data:image/svg+xml;base64," + btoa(xml);
var image = new Image;
image.src = data;
var imgWidth = image.width;
var imgHeigth = image.height;
var exportDiv = document.getElementById('exportDiv');
exportDiv.innerHTML = '<canvas id="exportCanvas" width="' + imgWidth + '" height="' + imgHeigth + '"></canvas>';
var canvas = document.querySelector("canvas"),
context = canvas.getContext("2d");
canvas.innerHTML = image;
image.onload = function () {
context.drawImage(image, 0, 0);
};
});
所以我所做的是:当页面加载时,我使用 D3.js 绘制一个圆圈。如果单击 "toPngBtn" 按钮,那么我将获取 svg 元素,将其序列化,创建一个新的 Image() 对象并将 blob 附加到源。我获取 SVG 的尺寸并创建一个相同大小的新 CANVAS 并将其附加到 div。我将 canvas 的 innerHTML 设置为新创建的图像,当图像加载时,我告诉上下文绘制图像。
好的部分是图像显示在页面上。糟糕的是,在 Internet Explorer 中我无法右键单击图像并保存它。在 Chrome 和 Firefox 中工作正常。
问题:是否有解决方法?我尝试使用
...
image.onload = function () {
context.drawImage(image, 0, 0);
var a = document.createElement("a");
a.download = "svg-graph.png";
a.href = canvas.toDataURL("image/png");
a.click();
};
...
提示下载文件,但 Internet Explorer 再次不允许 CORS,因此它不起作用...关于如何在 IE 中下载 SVG 图像的任何想法?
谢谢。
Internet Explorer 不支持锚标记上的 download
属性。
所以对于Internet Explorer,你可以试试下面的代码
window.navigator.msSaveBlob(canvas.msToBlob(), "svg-graph.png");
完成代码:
function isIE() {
var userAgent = window.navigator.userAgent;
return userAgent.indexOf("MSIE ") > -1 || userAgent.indexOf("Trident/") > -1;
}
image.onload = function () {
context.drawImage(image, 0, 0);
if(isIE()){
window.navigator.msSaveBlob(canvas.msToBlob(), "svg-graph.png");
} else{
var a = document.createElement("a");
a.download = "svg-graph.png";
a.href = canvas.toDataURL("image/png");
a.click();
}
};
为了安全起见,将 svg 图像绘制到 canvas 确实污染了 IE < Edge 中的 canvas(如果 <foreignObject>
在正在绘制的 svg 中,则在最新的 Safari 中原因。
因此,当您右键单击绘制的 canvas 时,您将无法再访问 save image as...
功能。
但是,在这些浏览器中,您只需右键单击原始 svg 元素并选择 save image as...
=> yourFile.png
。
所以解决方案是首先尝试在 canvas 上渲染 svg,然后 check if it was tainted 通过在 try-catch 块中调用它的 toDataURL()
方法,或者做一些 UA-string 欺骗并直接向用户发送一些通知,让用户右键单击图像并自行完成...
请注意,即使 canvas 被污染,它与您的情况下的 cross-origin-resources 无关。
我尝试:使用 D3 创建一个 SVG 元素,单击一个按钮将其转换为使用 CANVAS 的图像,因此可以右键单击并 "saved as" 图像。
问题:[object HTMLImageElement] 对象在 Internet Explorer 中不可见 "image" 所以当我右键单击它时,它不会提示 "Save image as..."选项。在 Chrome 和 Firefox 中它工作正常。
我有以下 HTML 代码:
<input type="button" id="toPngBtn" value="Save" /><br />
<div id="myDiv"></div>
<div id="exportDiv"></div>
以及以下 javascript 代码:
//Make an SVG Container
var svgContainer = d3.select("#myDiv").append("svg")
.attr("id", "myCircle")
.attr("width", 60)
.attr("height", 60);
//Draw the Circle
var circle = svgContainer.append("circle")
.attr("cx", 30)
.attr("cy", 30)
.attr("r", 20);
// Save button to
d3.select("#toPngBtn").on("click", function () {
var svg = document.getElementById('myCircle');
var xml = new XMLSerializer().serializeToString(svg);
var data = "data:image/svg+xml;base64," + btoa(xml);
var image = new Image;
image.src = data;
var imgWidth = image.width;
var imgHeigth = image.height;
var exportDiv = document.getElementById('exportDiv');
exportDiv.innerHTML = '<canvas id="exportCanvas" width="' + imgWidth + '" height="' + imgHeigth + '"></canvas>';
var canvas = document.querySelector("canvas"),
context = canvas.getContext("2d");
canvas.innerHTML = image;
image.onload = function () {
context.drawImage(image, 0, 0);
};
});
所以我所做的是:当页面加载时,我使用 D3.js 绘制一个圆圈。如果单击 "toPngBtn" 按钮,那么我将获取 svg 元素,将其序列化,创建一个新的 Image() 对象并将 blob 附加到源。我获取 SVG 的尺寸并创建一个相同大小的新 CANVAS 并将其附加到 div。我将 canvas 的 innerHTML 设置为新创建的图像,当图像加载时,我告诉上下文绘制图像。
好的部分是图像显示在页面上。糟糕的是,在 Internet Explorer 中我无法右键单击图像并保存它。在 Chrome 和 Firefox 中工作正常。
问题:是否有解决方法?我尝试使用
...
image.onload = function () {
context.drawImage(image, 0, 0);
var a = document.createElement("a");
a.download = "svg-graph.png";
a.href = canvas.toDataURL("image/png");
a.click();
};
...
提示下载文件,但 Internet Explorer 再次不允许 CORS,因此它不起作用...关于如何在 IE 中下载 SVG 图像的任何想法? 谢谢。
Internet Explorer 不支持锚标记上的 download
属性。
所以对于Internet Explorer,你可以试试下面的代码
window.navigator.msSaveBlob(canvas.msToBlob(), "svg-graph.png");
完成代码:
function isIE() {
var userAgent = window.navigator.userAgent;
return userAgent.indexOf("MSIE ") > -1 || userAgent.indexOf("Trident/") > -1;
}
image.onload = function () {
context.drawImage(image, 0, 0);
if(isIE()){
window.navigator.msSaveBlob(canvas.msToBlob(), "svg-graph.png");
} else{
var a = document.createElement("a");
a.download = "svg-graph.png";
a.href = canvas.toDataURL("image/png");
a.click();
}
};
为了安全起见,将 svg 图像绘制到 canvas 确实污染了 IE < Edge 中的 canvas(如果 <foreignObject>
在正在绘制的 svg 中,则在最新的 Safari 中原因。
因此,当您右键单击绘制的 canvas 时,您将无法再访问 save image as...
功能。
但是,在这些浏览器中,您只需右键单击原始 svg 元素并选择 save image as...
=> yourFile.png
。
所以解决方案是首先尝试在 canvas 上渲染 svg,然后 check if it was tainted 通过在 try-catch 块中调用它的 toDataURL()
方法,或者做一些 UA-string 欺骗并直接向用户发送一些通知,让用户右键单击图像并自行完成...
请注意,即使 canvas 被污染,它与您的情况下的 cross-origin-resources 无关。