HTML5 视频 MEDIA_ERR_DECODE 随机出现

HTML5 video MEDIA_ERR_DECODE occurs randomly

我正在开发项目 包含 6 个音频和视频元素,一个接一个地播放。 发布前的代码顺序是这样的:

  1. 预加载所有媒体资源直到 "canplaythrough"
  2. 正在播放视频 1
  3. 停止视频 1 并播放音频 1
  4. 停止 audio-1 并再次播放 video-1。

然后视频 1 播放了 2-3 秒并停止发送错误代码 3(3 = MEDIA_ERR_DECODE - 解码时发生错误)。我试图通过 link 播放相同的视频并且播放正常。

此问题在某些 OS 浏览器中随机出现。 例如:

UPDATE 仅在首次查看或禁用缓存时,才会在 Win10 最新的 Opera 上发生。

更新 2 视频编解码器为 H.264,音频编解码器为 AAC,帧率为 24。

MEDIA_ERR_DECODE

的定义

HTML5 spec for for media error codes

An error of some description occurred while decoding the media resource, after the resource was established to be usable.

Mozilla MediaError documentation

Despite having previously been determined to be usable, an error occurred while trying to decode the media resource, resulting in an error.

Firefox 错误消息(如此support ticket

The video playback was aborted due to a corruption problem or because the video used features your browser did not support.

解雇的常见原因

  • 视频已加密,但您未能解密。这可能是由于多种原因造成的:

    1) 使用多个 DRM 方案(而不是一个)加密视频可能会导致某些浏览器无法解密;

    2)您在视频开始播放之前忽略了解密(可能是在您完成许可请求之前不小心设置为自动播放);

    3) 没有足够的资源来解码视频,因为几个视频缓冲区(即使它们不是加密视频)已经用完了。

  • 您的浏览器不支持特定的媒体格式(例如 DASH)。这可能可以通过插件来解决,具体取决于媒体类型。

  • 您在 <source> 元素上设置了错误的 MIME 类型;请注意,某些浏览器更喜欢声明不同的 MIME 类型,以便解码某些视频格式。

  • 太多的视频缓冲区没有被清除就被用完了。

你的情况诊断

由于错误的触发相当不确定,这似乎是资源问题,而不是任何其他可能性。您有六个音频和视频元素一个接一个地播放,因此您应该在每次传送媒体时清除每个元素。您也不应该并排加载所有六个。

var video = document.getElementById('myVideo');
var nextVideo = document.getElementById('nextVideo');

video.addEventListener('ended', (event)=>{
    video.src = ""; // or the src attribute of the active <source> element.
    video.load();
    // If you aren't going to re-use this video element, you should also
    // remove all eventListeners from it and then remove it from the DOM.
    nextVideo.preload = "auto"; // I'm assuming the src has already been set.
    nextVideo.autoplay = true;
    // Second video should start playing now due to autoplay. If not, call load() again.
});

video.preload = "auto";
nextVideo.preload = "metadata";
video.src = "video.mp4";
nextVideo.src = "nextVideo.mp4";
video.autoplay = true;
nextVideo.load(); // I believe load() might not be necessary for preload = "metadata".
video.load(); // I believe load() is necessary for preload = "auto".
// First video should start playing now due to autoplay.

这与 iOS 相关的 类似。

当视频文件过大时,您可能会遇到此问题。推荐设置为:

video.preload = "auto"

更改为:

video.preload = "metadata"

就我而言,这是因为我正在流式传输高比特率 HLS 内容,并且没有限制缓冲量。

SourceBuffer 已满且 appendBuffer 失败,但在 Chrome(Chrome 91)中,错误消息具有误导性 MEDIA_ERR_DECODE

这可能会很快发生,在某个时间戳开始播放视频,播放 30 秒,然后 MEDIA_ERR_DECODE 错误会可靠地发生,并且它似乎在某个视频时间戳可靠地发生,这导致我相信这确实是由于视频编码中的一些问题。

但事实并非如此。我的VOD托管平台的专业人士建议我限制缓冲区长度,通过将(我正在使用hls.js)maxMaxBufferLength从默认的600s更改为30s,问题就解决了! MEDIA_ERR_DECODE我做了这个更改后再也没有发生过。