Element Capture API
Element Capture API DOM(元素)节点捕获
捕获并记录一个特定的 HTML 元素 (能剪裁并去除那些遮盖和被遮盖的内容)
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0" />
<title>Element Capture</title>
<style>
.box {
overflow-y: scroll;
width: 200px;
height: 200px;
border: 1px solid pink;
box-sizing: border-box;
resize: both;
}
.dialog {
isolation: isolate;
position: fixed;
top: 20%;
left: 20%;
width: 200px;
height: 100px;
margin: 0;
/* display: flex;
justify-content: center;
align-items: center; */
font-size: 20px;
background-color: pink;
}
</style>
</head>
<body>
<h1>Element Capture</h1>
<hr />
<div class="box">
<ul>
<li class="item">1. Lorem ipsum dolor sit amet.</li>
<li class="item">2. Eum voluptates eos maiores sed.</li>
<li class="item">3. Inventore itaque placeat aliquam! Laborum.</li>
<li class="item">4. Odit facilis totam ullam dignissimos?</li>
<li class="item">5. A dolorem repellendus nesciunt iusto?</li>
<li class="item">6. Magni cupiditate facere voluptatum aspernatur?</li>
<li class="item">7. Voluptates minima ullam laudantium laboriosam.</li>
<li class="item">8. Explicabo officia odit doloremque blanditiis.</li>
<li class="item">9. Voluptatem ea sed itaque officiis.</li>
<li class="item">10. Impedit culpa incidunt alias maiores!</li>
</ul>
</div>
<hr />
<button type="button" id="btn-dialog">show</button>
<dialog id="dialog" class="dialog">
<header>
<b>dialog test title</b>
</header>
</dialog>
<hr />
<script>
const box = document.querySelector('.box');
const dialog = document.querySelector('#dialog');
const dialogBtn = document.querySelector('#btn-dialog');
let num = 0, timerId = null;
// 监听按钮点击事件,显示或隐藏 dialog 元素。
dialogBtn.addEventListener('click', () => {
// dialog.showModal() / dialog.close()
dialog.toggleAttribute('open');
dialogBtn.textContent = dialog.open ? 'hide' : 'show';
if (dialog.open) {
clearInterval(timerId);
timerId = null;
captureElement().catch((err) => console.log(err));
timerId = setInterval(() => {
dialog.children[0].children[0].textContent = num++;
}, 500);
}
});
async function captureElement() {
// 请求用户授权,开始捕获当前的标签页。
const stream = await navigator.mediaDevices.getDisplayMedia({
preferCurrentTab: true,
});
const [track] = stream.getVideoTracks();
console.log('track => ', track);
// 将 captureTarget 与一个新的 RestrictionTarget 关联起来
const restrictionTarget = await RestrictionTarget.fromElement(dialog);
// 开始使用 RestrictionTarget 限制自我捕捉的视频轨道。
await track.restrictTo(restrictionTarget);
const video = document.createElement('video');
video.autoplay = true;
video.width = dialog.clientWidth;
video.height = dialog.clientHeight;
video.srcObject = stream;
document.body.appendChild(video);
// 捕获视频轨道的画面,并将其显示在 canvas 中。
// const canvas = document.createElement('canvas');
// const ctx = canvas.getContext('2d');
// const draw = () => {
// ctx.drawImage(video, 0, 0, canvas.width, canvas.height);
// requestAnimationFrame(draw);
// };
// requestAnimationFrame(draw);
// // 显示 canvas 元素,并将其置于 dialog 元素的顶层。
// canvas.width = video.width * devicePixelRatio;
// canvas.height = video.height * devicePixelRatio;
// canvas.style.width = `${video.width}px`;
// canvas.style.height = `${video.height}px`;
// document.body.appendChild(canvas);
// 监听 dialog 元素的关闭事件,停止捕获视频轨道。
dialog.addEventListener('close', () => {
track.stop();
document.body.removeChild(video);
});
// 监听视频轨道的结束事件,移除 video 元素。
track.addEventListener("ended", () => {
document.body.removeChild(video);
})
}
</script>
</body>
</html>