MediaCapabilities: decodingInfo() 方法
Baseline 广泛可用 *
注意:此功能在 Web Workers 中可用。
MediaCapabilities 接口的 decodingInfo() 方法返回一个 Promise,该 Promise 以关于用户代理如何解码/显示具有给定配置的媒体的信息来 fulfilled。
解析后的对象包含三个布尔属性 supported、smooth 和 powerefficient,它们指示是否支持解码描述的媒体,如果支持,则指示解码是否会流畅且省电。
该方法还可以用于测试用户代理解码使用密钥系统编码的媒体的能力,但前提是在主线程和安全上下文中调用。如果 configuration.keySystemConfiguration 属性中传递的配置支持解码数据,则解析后的 Promise 还包括一个 MediaKeySystemAccess 对象,该对象可用于创建 MediaKeys 对象以设置加密播放。
注意:使用此属性调用 decodingInfo() 可能会导致用户可见的效果,例如请求访问一个或多个系统资源的权限。因此,应仅在应用程序准备好使用提供的配置创建和使用 MediaKeys 对象时调用此函数。
语法
decodingInfo(configuration)
参数
configuration-
一个对象,其中包含一个
type属性,并且一个video或audio属性,其中包含相应类型的配置,以及一个可选的keySystemConfiguration,用于解码使用密钥系统加密的媒体。type-
正在测试的媒体类型。这接受以下三种值之一:
文件-
表示用于普通文件播放的配置。
media-source-
表示用于
MediaSource播放的配置。 webrtc-
表示使用
RTCPeerConnection接收的配置(当设置了keySystemConfiguration时不允许)。
video-
视频媒体源的配置对象。它具有以下属性:
audio-
音频媒体源的配置对象。它具有以下属性:
contentType-
包含有效音频 MIME 类型以及(可选)
codecs参数的字符串。 channels-
音频轨道使用的通道数。
bitrate-
用于编码音频文件一秒钟的比特数。
samplerate-
构成音频文件一秒钟的音频样本数。
keySystemConfiguration可选-
指定加密媒体密钥系统配置的对象。
注意:
Navigator.requestMediaKeySystemAccess()在其supportedConfigurations参数中接受相同数据类型的数组。如果指定,则
type必须是media-source或file(而不是webrtc)。它具有以下属性:keySystem-
标识媒体密钥系统的字符串。例如
org.w3.clearkey或com.widevine.alpha。 initDataType可选-
一个字符串,指示初始化数据格式的数据类型名称,例如
"cenc"、"keyids"和"webm"。允许的名称定义在 Encrypted Media Extensions Initialization Data Format Registry 中。 distinctiveIdentifier可选-
一个字符串,指示实现是否可能为从该配置创建的任何对象的任何操作使用“独特标识符”(或独特永久标识符)。允许的值为:
required-
返回的对象必须支持此功能。
可选-
返回的对象可能支持此功能。这是默认值。
not-allowed-
返回的对象不得支持或使用此功能。
persistentState可选-
一个字符串,指示返回的对象是否能够持久化会话数据或任何其他类型的状态。允许的值为:
required-
返回的对象必须支持此功能。
可选-
返回的对象可能支持此功能。这是默认值。
not-allowed-
返回的对象不得支持或使用此功能。仅当不允许持久化状态时,才能创建“临时”会话。
sessionTypes可选-
一个字符串数组,指示必须支持的会话类型。允许的值包括:
temporary-
一个会话,其中许可证、密钥和会话记录或相关数据不会持久化。应用程序不需要管理此类存储。实现必须支持此选项,这是默认选项。
persistent-license-
一个会话,其中许可证(以及可能与会话相关的其他数据)将得到持久化。即使销毁了许可证,许可证及其关联密钥的记录也会保留,这证明了该许可证及其包含的密钥客户端不再可用。
audio可选-
与上面的
audio配置关联的音频密钥系统轨道配置。如果设置,则必须也设置audio配置。encryptionScheme-
与内容类型相关的加密方案,例如
cenc、cbcs、cbcs-1-9。此值应由应用程序设置(默认为null,表示可以使用任何加密方案)。 robustness-
与内容类型相关的健壮性级别。空字符串表示可以接受任何解密和解码内容类型的能力。
video可选-
与上面的
video配置关联的视频密钥系统轨道配置。如果设置,则必须也设置video配置。encryptionScheme-
与内容类型相关的加密方案,例如
cenc、cbcs、cbcs-1-9。此值应由应用程序设置(默认为null,表示可以使用任何加密方案)。 robustness-
与内容类型相关的健壮性级别。空字符串表示可以接受任何解密和解码内容类型的能力。
返回值
一个 Promise,以一个包含以下属性的对象 fulfilled:
supported-
如果媒体内容根本无法解码,则为
true。否则为false。 平滑-
如果在不丢帧的情况下可以以配置中指定的帧率播放媒体,则为
true。否则为false。 powerEfficient-
如果媒体播放将是省电的,则为
true。否则为false。 keySystemAccess-
一个
MediaKeySystemAccess,可用于创建MediaKeys对象以设置加密播放,或者如果使用提供的配置不支持解码,则为null。
浏览器将报告支持的媒体配置为 smooth 和 powerEfficient,直到在该设备上记录了统计信息。所有支持的音频编解码器都将 powerEfficient 报告为 true。
异常
TypeError-
如果传递给
decodingInfo()方法的configuration无效,则抛出此异常,原因可能是类型不是 video 或 audio,contentType不是有效的编解码器 MIME 类型,媒体解码配置不是type(file、media-source 或 webrtc)的有效值,或者传递给方法的媒体配置中的任何其他错误,包括省略任何值。 InvalidStateErrorDOMException-
当定义了
configuration.keySystemConfiguration时,该方法在 worker 中调用。 SecurityErrorDOMException-
该方法在安全上下文之外调用,并且定义了
configuration.keySystemConfiguration。
用法说明
与 Navigator.requestMediaKeySystemAccess() 的比较
decodingInfo() 方法和 Encrypted Media Extensions API 的 Navigator.requestMediaKeySystemAccess() 方法反映了选择加密媒体解码配置的基本不同的方法。
Navigator.requestMediaKeySystemAccess() 的配置参数接受一个可能的配置数组,并允许系统选择它认为合适的配置。
相比之下,decodingInfo() 一次只接受一个配置。预期调用者将多次执行 decodingInfo(),从最首选的配置开始,并在找到满足应用程序对流畅、省电或两者兼有的配置要求后立即停止。换句话说,选择决策被委托给了调用者。
示例
获取未加密媒体文件的解码信息
此示例演示了如何为音频文件创建媒体配置,然后在 MediaCapabilities.decodingInfo() 中使用它。
// Create media configuration to be tested
const audioConfig = {
type: "file", // or 'media-source' or 'webrtc'
audio: {
contentType: "audio/ogg; codecs=vorbis", // valid content type
channels: 2, // audio channels used by the track
bitrate: 132700, // number of bits used to encode 1s of audio
samplerate: 5200, // number of audio samples making up that 1s.
},
};
// check support and performance
navigator.mediaCapabilities.decodingInfo(audioConfig).then((result) => {
if (result.supported) {
log(
`The audio configuration is supported${result.smooth ? ", smooth" : ", not smooth"}${result.powerEfficient ? ", power efficient" : ", not power efficient"}.`,
);
} else {
log("The audio configuration is not supported");
}
});
同样,下面的代码显示了视频文件的配置。
const videoConfig = {
type: "file",
video: {
contentType: "video/webm;codecs=vp8", // valid content type
width: 800, // width of the video
height: 600, // height of the video
bitrate: 10000, // number of bits used to encode 1s of video
framerate: 30, // number of frames making up that 1s.
},
};
// check support and performance
navigator.mediaCapabilities.decodingInfo(videoConfig).then((result) => {
if (result.supported) {
log(
`The video configuration is supported${result.smooth ? ", smooth" : ", not smooth"}${result.powerEfficient ? ", power efficient" : ", not power efficient"}.`,
);
} else {
log("The video configuration is not supported");
}
});
获取加密媒体的解码信息
此示例演示了如何使用 decodingInfo() 为加密内容选择媒体配置。
与前面的示例一样,我们定义了一个媒体配置,但这次我们使用了 media-source(而不是 file)的 type,并指定了音频和视频内容。我们还指定了一个简单的 keySystemConfiguration。
const encryptedMediaConfig = {
type: "media-source", // or 'file'
audio: {
contentType: "audio/webm; codecs=opus",
channels: 2, // audio channels used by the track
bitrate: 132700, // number of bits used to encode 1s of audio
samplerate: 48000, // number of audio samples making up that 1s.
},
video: {
contentType: 'video/webm; codecs="vp09.00.10.08"',
width: 800, // width of the video
height: 600, // height of the video
bitrate: 10000, // number of bits used to encode 1s of video
framerate: 30, // number of frames making up that 1s.
},
keySystemConfiguration: {
keySystem: "org.w3.clearkey",
initDataType: "webm",
distinctiveIdentifier: "required",
},
};
在前面的示例中,我们使用了 Promise 链来等待结果。在这里,我们选择使用 async 和 await 来等待结果,然后将其记录下来。
getDecodingInfo(encryptedMediaConfig);
async function getDecodingInfo(mediaConfig) {
const result = await navigator.mediaCapabilities.decodingInfo(mediaConfig);
console.log(result);
if (!result.supported) {
log("This encrypted media configuration is not supported.");
return;
}
// keySystemAccess is returned if decoding encrypted media is supported
// This can be used to decrypt and playback the media
if (!result.keySystemAccess) {
log("Encrypted media support is not available.");
return;
}
log(
`The encrypted media configuration is supported${result.smooth ? ", smooth" : ", not smooth"}${result.powerEfficient ? ", power efficient" : ", not power efficient"}.`,
);
}
日志输出如下所示。
迭代加密媒体的解码信息
上一个示例演示了如何使用 decodingInfo() 获取单个配置的信息。实际上,该方法通常会迭代调用多个配置,选择第一个满足应用程序对流畅播放或省电标准的配置。其工作方式如下所述。
假设我们已经有一个名为 orderedMediaConfigs 的媒体配置数组,我们已将其从最需要排序到最不需要。我们可以使用 Array.prototype.map() 为每个配置调用 decodingInfo(),并获得一个包含所有返回的 Promise 对象的数组。
const capabilitiesPromises = orderedMediaConfigs.map((mediaConfig) =>
navigator.mediaCapabilities.decodingInfo(mediaConfig),
);
然后,我们使用 for await...of 循环来迭代解析的 Promise。在循环中,我们将最后一个支持的配置存储到 nonSmoothConfig,并在找到流畅的配置后立即退出循环,将其设置为 bestConfig。
// Assume this app wants a supported && smooth config.
let bestConfig = null;
let nonSmoothConfig = null;
for await (const mediaCapabilityInfo of capabilitiesPromises) {
if (!mediaCapabilityInfo.supported) continue;
if (!mediaCapabilityInfo.smooth) {
nonSmoothConfig = mediaCapabilityInfo;
continue;
}
bestConfig = mediaCapabilityInfo;
break;
}
如果在循环中找到了流畅且支持的配置(bestConfig),则使用它来 创建媒体密钥并解码媒体。如果未找到流畅的配置,我们可能会改用 nonSmoothConfig 来解码媒体。这将是最后找到的支持配置,由于我们排序了原始 orderedMediaConfigs 的方式,它应该是帧率最低的配置。
let keys = null;
if (bestConfig) {
keys = await bestConfig.keySystemAccess.createMediaKeys();
// … use keys to decode media using best config
} else if (nonSmoothConfig) {
console.log(
"No smooth configs found. Using lowest resolution configuration!",
);
keys = await nonSmoothConfig.keySystemAccess.createMediaKeys();
// … use keys to decode media using lowest framerate config
} else {
console.log("No supported configs!");
// Fail!
}
如果没有支持的配置,我们将别无选择,只能失败并通知用户。
规范
| 规范 |
|---|
| Media Capabilities # dom-mediacapabilities-decodinginfo |
浏览器兼容性
加载中…