我正在尝试获取使用 JavaScript 覆盖到页面上的视频的尺寸,但是它返回海报图像的尺寸而不是实际视频,因为它似乎是在视频加载之前计算的.
应该注意的是,Sime Vidas 目前接受的上述解决方案实际上在现代浏览器中不起作用,因为 videoWidth 和 videoHeight 属性直到“loadedmetadata”事件触发后才设置。
如果您碰巧在 VIDEO 元素渲染后足够远的地方查询这些属性,有时可能会起作用,但在大多数情况下,这两个属性都会返回 0 值。
为了保证您获得正确的属性值,您需要执行以下操作:
var v = document.getElementById("myVideo");
v.addEventListener( "loadedmetadata", function (e) {
var width = this.videoWidth,
height = this.videoHeight;
}, false );
注意:我没有费心考虑 Internet Explorer 9 之前的版本,它使用 AttachEvent 而不是 addEventListener,因为该浏览器 9 之前的版本无论如何都不支持 HTML5 视频。
<video id="foo" src="foo.mp4"></video>
var vid = document.getElementById("foo");
vid.videoHeight; // returns the intrinsic height of the video
vid.videoWidth; // returns the intrinsic width of the video
规格:https://html.spec.whatwg.org/multipage/embedded-content.html#the-video-element
这是一个随时可用的函数,它异步返回视频的尺寸,无需更改文档中的任何内容。
// ---- Definitions ----- //
/**
Returns the dimensions of a video asynchrounsly.
@param {String} url Url of the video to get dimensions from.
@return {Promise<{width: number, height: number}>} Promise which returns the dimensions of the video in 'width' and 'height' properties.
*/
function getVideoDimensionsOf(url){
return new Promise(resolve => {
// create the video element
const video = document.createElement('video');
// place a listener on it
video.addEventListener( "loadedmetadata", function () {
// retrieve dimensions
const height = this.videoHeight;
const width = this.videoWidth;
// send back result
resolve({height, width});
}, false);
// start download meta-datas
video.src = url;
});
}
// ---- Use ---- //
getVideoDimensionsOf("https://www.w3schools.com/html/mov_bbb.mp4")
.then(console.log);
如果您想观看,这里是用于该片段的视频:Big Buck Bunny
监听当用户代理刚刚确定媒体资源的持续时间和尺寸时调度的
loadedmetadata
事件
https://www.w3.org/TR/html5/semantics-embedded-content.html#eventdef-media-loadedmetadata
videoTagRef.addEventListener('loadedmetadata', function(e){
console.log(videoTagRef.videoWidth, videoTagRef.videoHeight);
});
这是在 Vue 中完成的方法:
<template>
<div>
<video src="video.mp4" @loadedmetadata="getVideoDimensions"></video>
</div>
</template>
<script>
export default {
methods: {
getVideoDimensions (e) {
console.log(e.target.videoHeight)
console.log(e.target.videoWidth)
}
}
}
</script>
这也应该注意
在某些情况下例如HLS流
“onmetadataloaded”也不起作用。
在这些情况下,这个解决方案非常完美。
var video = document.getElementById("video")
video.onplaying = function () {
var width = video.videoWidth
var height = video.videoHeight
console.log("video dimens loaded w="+width+" h="+height)
}
这是我的 TypeScript 解决方案:
videoResolution: { width: number; height: number } = { width: 0, height: 0 };
/**
* Obtains the width and height of a video element once its metadata has loaded.
* @param video - The HTMLVideoElement for which to obtain the resolution.
*/
getVideoResolution(video: HTMLVideoElement): void {
const loadedMetadataListener = () => {
// Access the videoWidth and videoHeight properties of the HTML video element
this.videoResolution.width = video.videoWidth;
this.videoResolution.height = video.videoHeight;
// Remove the event listener
video.removeEventListener('loadedmetadata', loadedMetadataListener);
};
video.addEventListener('loadedmetadata', loadedMetadataListener, false);
}
只需使用 HTML 视频元素调用 getVideoResolution 函数即可。
在 Vuejs 中,我在 Mounted 标签中使用以下代码。
var app = new Vue({
el: '#id_homepage',
mounted: function () {
var v = document.getElementById("id_video");
var width = v.offsetWidth;
v.height = Math.floor(width*(9/16)); // dynamically setting video height to maintain aspect ratio
},
});