如何解决 iOS 11 Safari getUserMedia“无效约束”问题

Posted

技术标签:

【中文标题】如何解决 iOS 11 Safari getUserMedia“无效约束”问题【英文标题】:How to resolve iOS 11 Safari getUserMedia "Invalid constraint" issue 【发布时间】:2017-10-27 19:08:27 【问题描述】:

我正在尝试在 ios 11 的 Safari 中运行以下代码。它应该提示用户授予他们设备摄像头的访问权限,然后将其显示在我的 <video autoplay id="video"></video> 元素中。但是,在 iOS 11 中运行时,会抛出 OverconstrainedError

message: "Invalid constraint", constraint: ""
代码在android中运行良好,成功打开摄像头。 我尝试了多个有效配置,但都没有成功。

我知道 iOS 11 刚刚发布,所以它可能是一个错误,但有什么想法吗?有没有其他人遇到过这种情况?

代码:

var video = document.getElementById('video');
if(navigator.mediaDevices && navigator.mediaDevices.getUserMedia) 
     navigator.mediaDevices.getUserMedia(video: true)
         .then(function(stream) 
             video.src = window.URL.createObjectURL(stream);
             video.play();
         )
         .catch(function(err) 
             console.log(err);
         );


编辑 1

我已经运行 navigator.mediaDevices.getSupportedConstraints() 并返回以下内容:


    aspectRatio: true,
    deviceid: true,
    echoCancellation: false,
    facingMode: true,
    frameRate: true,
    groupId: true,
    height: true,
    sampleRate: false,
    sampleSize: false,
    volume: true,
    width: true

我尝试过省略video 属性的配置,但没有成功。

【问题讨论】:

这里也一样,也在 iOS 11 上。虽然我找到了相机工作的线程,但我运气不好:***.com/questions/45692526/… 试试video: true,audio:false。我发现getSupportedConstraints() 会返回很多误报,请改用track.getSettings() (source)。 【参考方案1】:

safari 中的无效约束错误是因为浏览器希望您传递正确的宽度,其中之一:

320 640 1280

320 或 640 以 4:3 的纵横比自动计算高度,1280 以 16:9 的纵横比自动计算,然后如果您传递 320 的宽度,则您的视频流设置在:

320x240

如果设置宽度为 640,则视频流设置在:

640x480

如果你设置宽度为 1280,那么你的视频流设置在:

1280x720

在任何其他情况下,宽度值都会出现错误“InvalidConstrain”。

您还可以使用最小、最大、精确或理想的宽度约束,请查看MDN documentation

这是codepen中的一个示例

var config =  video:  width: 320/*320-640-1280*/  ;
var start = () => navigator.mediaDevices.getUserMedia(config)
  .then(stream => v.srcObject = stream)
  .then(() => new Promise(resolve => v.onloadedmetadata = resolve))
  .then(() => log("Success: " + v.videoWidth + "x" + v.videoHeight))
  .catch(log);

var log = msg => div.innerhtml += "<p>" + msg + "</p>";

PD:在 chrome 中,您可以设置宽度和高度,并且视频流设置为这些尺寸,Firefox 执行 fitness distance,而 Safari 期望完全匹配。

【讨论】:

320px 在 iOS12(仅 640 和 1280)上不适合我,我需要添加 frameRate:15。多么糟糕的行为! 这是一个很棒的信息。我想知道某处是否有关于此的文档。我知道developer.mozilla.org/en-US/docs/Web/API/MediaDevices,但也许有一个用于 Safari。我还想知道其他约束(frameRate 等)。 @kintaro。你好。我在 safari 13 中打开了您的示例,但出现错误:无效约束 嗨@Pantera,320 有错误?请查看 Millar248 的评论,他说 320 不起作用,仅适用于 iOS12 中的 640 和 1280【参考方案2】:

请记住,Xcode 附带的 iOS 模拟器不支持网络摄像头或麦克风,这就是为什么您可能会收到 OverconstrainedError(根据 https://developer.mozilla.org/en-US/docs/Web/API/MediaDevices/getUserMedia 文档,这意味着没有设备适合传递的选项,即使您不支持把细节)

【讨论】:

【参考方案3】:

似乎是一个错误已得到纠正,因为我刚刚再次尝试,错误消息不再出现。

请注意,虽然错误消息消失了,但我确实必须再进行一项更改才能使其正常工作,即在 then 回调中添加 video.srcObject = stream;

【讨论】:

在 iOS 12 上仍然发生在我身上

以上是关于如何解决 iOS 11 Safari getUserMedia“无效约束”问题的主要内容,如果未能解决你的问题,请参考以下文章

如何让“Pointermove”委托在父母/孩子的Safari iOS中工作?

Safari很卡?教你开启iOS11的隐藏功能,加快上网速度

WebRTC 远程视频在 ios Safari 上一直冻结

iOS 12 Safari iframe + 位置:固定 + translate3d 错误

在 iOS 移动 Safari 13(iPhone X 和 11)中隐藏全屏 Web 应用程序的状态/位置栏

当触发 iOS Safari 中的虚拟键盘时,它会使我的 CSS 过渡闪烁。如何解决这个问题?