原生JS可用的webcam访问代码移植到Angular后无摄像头画面求助
问题根因
@ViewChild 查询返回的是 Angular 封装的 ElementRef 实例,而非直接的 DOM 元素,你直接给 myVideo.srcObject 赋值是写到了 ElementRef 对象上,没有作用到真实的 video 节点上,所以不会有画面也不会触发报错。
修正后的代码
TypeScript 部分
import { ViewChild, ElementRef } from '@angular/core'; // 明确指定查询类型为 ElementRef,泛型约束为 video 元素 @ViewChild('myVideo') myVideo!: ElementRef<HTMLVideoElement>; public takePicture(event?: any): void { navigator.mediaDevices.getUserMedia({ video: { facingMode: 'user' } }) .then(stream => { // 取 nativeElement 拿到真实 DOM 节点再赋值 if (this.myVideo?.nativeElement) { this.myVideo.nativeElement.srcObject = stream; } }) .catch(err => { // 加入错误捕获,方便排查权限、设备占用等问题 console.error('摄像头访问失败:', err); }); }
如果是 Angular 8 及更早版本,@ViewChild 需要额外传入第二个参数:@ViewChild('myVideo', { static: false }) myVideo!: ElementRef<HTMLVideoElement>;
HTML 部分
无需调整,保持原有写法即可:
<button (click)="takePicture($event)">打开摄像头</button> <video #myVideo autoplay playsinline style="width: 100px; height: 100px;"></video>
额外排查点
- 确保应用运行在
localhost或者 HTTPS 环境下,这是浏览器getUserMediaAPI 的强制要求 - 如果需要在组件初始化时自动打开摄像头,要把调用逻辑写在
ngAfterViewInit生命周期钩子中,确保@ViewChild已经完成查询赋值
内容的提问来源于stack exchange,提问作者Search Bug and Destroy
相关产品推荐
相关产品推荐

