今天小编给大家分享一下JavaScript怎么实现截屏功能的相关知识点,内容详细,逻辑清晰,相信大部分人都还太了解这方面的知识,所以分享这篇文章给大家参考一下,希望大家阅读完这篇文章后有所收获,下面我们一起来了解一下吧。
1.Blob的媒体类型必须是"image/svg+xml
"
2.需要一个 svg 元素
3.在 svg 元素里面插入一个 foreignObject
元素
4.在 foreignObject 元素里面放入符合规范的 html
把dom转成canvas就这么简单,就上面几个步骤。下面是文档给出的一上简单的demo:
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
</head>
<body>
<canvas id="canvas" width="200" height="200">
</canvas>
<script>
var canvas = document.getElementById('canvas');
var ctx = canvas.getContext('2d');
var data = '<svg xmlns="http://www.w3.org/2000/svg" width="200" height="200">' +
'<foreignObject width="100%" height="100%">' +
'<div xmlns="http://www.w3.org/1999/xhtml" >' +
'<em>I</em> like ' +
'<span >' +
'cheese</span>' +
'</div>' +
'</foreignObject>' +
'</svg>';
var DOMURL = window.URL || window.webkitURL || window;
var img = new Image();
var svg = new Blob([data], {type: 'image/svg+xml'});
var url = DOMURL.createObjectURL(svg);
img.onload = function() {
ctx.drawImage(img, 0, 0);
DOMURL.revokeObjectURL(url);
}
img.src = url;
</script>
</body>
</html>
复制代码,运行一下,哇,帅呆了,浏览器上出现了超酷的两行艺术字呢!
嗯,原来dom转成canvas这么简单啊?那我通过 document.body.innerHTML
把body里面的所有dom取出来,然后放到 foreignObject 元素里面,不就OK了、把整个页面都截取下来了吗?
demo仅仅是个Hello World,但是实际项目中的Dom结构比这个复杂多了,比如,引入了外部样式表、图片、而且还可能某些标签不符合xml规范(如缺少闭合标签等)。下面的举个简单的例子,.container不是使用行内样式的,而是在style标签里面定义,字体红色,转成图片后,样式不生效。
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
.container {
color: red;
}
</style>
</head>
<body>
<div class="container" >
Hello World!
</div>
<canvas id="canvas" width=200" height="200">
</canvas>
<script>
var canvas = document.getElementById('canvas');
var ctx = canvas.getContext('2d');
var data = '<svg xmlns="http://www.w3.org/2000/svg" width="200" height="200">' +
'<foreignObject width="100%" height="100%">' +
'<div xmlns="http://www.w3.org/1999/xhtml" >' +
document.querySelector('.container').innerHTML +
'</div>' +
'</foreignObject>' +
'</svg>';
var DOMURL = window.URL || window.webkitURL || window;
var img = new Image();
var svg = new Blob([data], {type: 'image/svg+xml'});
var url = DOMURL.createObjectURL(svg);
img.onload = function() {
ctx.drawImage(img, 0, 0);
DOMURL.revokeObjectURL(url);
}
img.src = url;
</script>
</body>
</html>
既然外部样式不生效,那我们可以通过JS遍历所有的dom元素,把全部的样式通过element.style对象添加到行内样式啊。这个思路听起来不错,但是,实现这个把外部样式转成行内样式的函数我还真写不出来啊。需求比较紧,也没有那 多时间去瞎折腾了,所以,就想找找有没有现成的库。于是又去google一下。很幸运, 一下子就搜到了一个叫做html2canvas的库,非常棒的一个库,很强大、但用法非常简单.就这么简单的方法,就可以把我的整个页面截图下来了:
function convertHtml2Canvas() {
html2canvas(document.body, {
allowTaint: false,
taintTest: true
}).then(function(canvas) {
document.body.appendChild(canvas);
}).catch(function(e) {
console.error('error', e);
});
}
目前还有一个问题,就是这种方法默认是把整个页面截取下来的(就是说,会以你的innerHeight和innerWidth为边界,会存在大量的空白),可是,我的卡组只是占了页面的一小部分,我只想要卡组的部分啊。其实已经有了canvas就好办了,我们可以对它进行处理啊。大概思路是:1.把上面得到的canvas对象转成Blob并放到一个img元素。然后再把img.src绘制到canvas里面。这时候调用canvas.drawImage
方法就可以截取我们想要的内容了。下面的两个函数分别是把canvas转成image以及反过来把image转成canvas。
// Converts canvas to an image
function convertCanvasToImage(canvas) {
var image = new Image();
image.src = canvas.toDataURL("image/png", 0.1);
return image;
}
// Converts image to canvas; returns new canvas element
function convertImageToCanvas(image, startX, startY, width, height) {
var canvas = document.createElement("canvas");
canvas.width = width;
canvas.height = height;
canvas.getContext("2d").drawImage(image, startX, startY, width, height, 0, 0, width, height);
return canvas;
}
然后,再把我们上面的写的 convertHtml2Canvas 改成下面的:
function convertHtml2Canvas() {
html2canvas(document.body, {
allowTaint: false,
taintTest: true
}).then(function(canvas) {
var img = convertCanvasToImage(canvas);
document.body.appendChild(img);
img.onload = function() {
img.onload = null;
canvas = convertImageToCanvas(img, 0, 0, 384, 696);
img.src = convertCanvasToImage(canvas).src;
$(img).css({
display: 'block',
position: 'absolute',
top: 0,
left: 400 + 'px'
});
}
}).catch(function(e) {
console.error('error', e);
});
}
这时候就可以把它的页面的某部分内容进行截取下来了。效果如卡组分享测试页面。页面左边部分是DOM结构的,右边部分是则是使用html2canvas转换出来的图片。
以上就是“JavaScript怎么实现截屏功能”这篇文章的所有内容,感谢各位的阅读!相信大家阅读完这篇文章都有很大的收获,小编每天都会为大家更新不同的知识,如果还想学习更多的知识,请关注亿速云行业资讯频道。
亿速云「云服务器」,即开即用、新一代英特尔至强铂金CPU、三副本存储NVMe SSD云盘,价格低至29元/月。点击查看>>
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。
原文链接:https://my.oschina.net/u/1268508/blog/4373578