Canvas drawImage 捕获 video 黑屏主因是 video 未就绪或跨域污染:需监听 loadeddata 事件、设置 crossOrigin="anonymous"、确保 readyState ≥ 2,且 canvas 宽高为正整数。
直接调用 drawImage 却得到全黑或空白图像,大概率是 video 还没加载完成、没播放、或未满足 canvas 捕获前提。video 必须处于「可绘制状态」:已加载元数据(loadedmetadata)、至少帧已解码(canplay 或 playing),且不能是跨域资源(否则会触发 canvas 污染)。
实操建议:
立即学习“前端免费学习笔记(深入)”;
video 的 loadeddata 事件后再首次调用 drawImage,比 loadedmetadata 更可靠video 元素设置了 crossOrigin="anonymous"(若源为外部 URL),否则即使加载成功也会因污染被拒绝读取autoplay 未生效或用户未交互(如点击)时尝试捕获——部分浏览器会阻止静音 autoplay 下的 canvas 读取video.readyState ≥ 2(HAVE_CURRENT_DATA)再绘制,可用 setInterval 轮询或监听 timeupdate
canvas 绘制本身不自动缩放像素,drawImage 的目标宽高若与 canvas 的 width/height 属性值不一致,就会触发浏览器插值缩放,造成失真。常见错误是只设了 CSS 样式宽高,却没同步设置 canvas 的 DOM 属性。
实操建议:
立即学习“前端免费学习笔记(深入)”;
width 和 height 属性(不是 CSS),例如:canvas.width = 160; canvas.height = 90;
const scale = Math.min(160 / video.videoWidth, 90 / video.videoHeight);,再传入 drawImage(video, 0, 0, video.videoWidth * scale, video.videoHeight * scale)
ctx.scale() 替代尺寸计算——它会影响后续所有绘制,且易叠加误差canvas.toDataURL() 返回空字符串或损坏 base64,通常源于 canvas 被污染(tainted canvas),即曾绘制过跨域但未声明 crossOrigin 的视频/图片;也可能是调用时机过早(video 未就绪)或 canvas 尺寸为 0。
实操建议:
立即学习“前端免费学习笔记(深入)”;
crossOrigin="anonymous",且服务端响应头包含 Access-Control-Allow-Origin: *(或指定域名)video.src 赋值后立刻调用 toDataURL,必须等 loadeddata 或 playing 事件之后width 和 height 是否为正整数——若为 0 或 NaN,toDataURL 必然返回空串canvas.toDataURL('image/png', 1.0);JPEG 可加质量参数(0.1–1.0)控制体积每秒多次 drawImage + toDataURL 会快速堆积 bitmap 数据,尤其在移动端易触发 GC 停顿或 OOM。不是所有场景都需要逐帧截图——缩略图通常只需关键帧或间隔采样。
实操建议:
立即学习“前端免费学习笔记(深入)”;
requestAnimationFrame 替代 setInterval 控制捕获节奏,自然对齐屏幕刷新率if (Date.now() - lastCapture > 500) { capture(); lastCapture = Date.now(); }
toDataURL 后无需清空 canvas,但若后续绘制内容不同,应调用 ctx.clearRect(0, 0, w, h)
canvas.toBlob(callback, type, quality) 避免 base64 字符串内存开销canvas 污染问题最隐蔽也最难调试,一旦发生,整个 canvas 就不可读取——连 getImageData 都会抛错。务必在 video 加载阶段就验证 crossOrigin 设置是否生效,而不是等到截图失败才排查。
Tplink路由器管理界面无法进入(如何解决Tplink路由器管理界面无法进入的问题)
如何通过Tplink路由器App添加设备(Tplink路由器App添加设备指南)
Tplink路由器App禁用设备功能详解(Tplink路由器App禁用设备查看指南)
如何正确安装Tplink路由器(Tplink路由器安装指南)
TPLink F80E路由器是哪个年代的产品(TPLink F80E路由器的生产年份是什么)
TPLink AC1900路由器的设置方法是什么(如何设置TPLink AC1900路由器)