Javascript 如何响应地将SVG标记排列到视频标记的上方';什么是真正的比赛场地?
Javascript 如何响应地将SVG标记排列到视频标记的上方';什么是真正的比赛场地?,javascript,css,svg,responsive-design,html5-video,Javascript,Css,Svg,Responsive Design,Html5 Video,//一些测试代码 设v=document.getElementById(“视频”); 常量testHandler=()=>{ 设v_w=v.videoWidth; 设v_h=v.高度; 设c_w=v.clientWidth; 设c_h=v.clientHeight; 日志(v_w,v_h,c_w,c_h); } v、 addEventListener('loadeddata',testHandler); 我的目的是在视频标签的真实播放区域上方准确地排列一个SVG标签。 为了便于理解当前情况,我
//一些测试代码
设v=document.getElementById(“视频”);
常量testHandler=()=>{
设v_w=v.videoWidth;
设v_h=v.高度;
设c_w=v.clientWidth;
设c_h=v.clientHeight;
日志(v_w,v_h,c_w,c_h);
}
v、 addEventListener('loadeddata',testHandler);
我的目的是在视频标签的真实播放区域上方准确地排列一个SVG标签。
为了便于理解当前情况,我用灰色背景和0.5的不透明度设置了SVG区域的样式。
绿色矩形是视频和SVG标记区域,红色矩形是实际播放区域。换句话说,这是我的目标区域
首先,我想知道一种获得实际比赛区域(红色矩形)坐标的有效方法。
其次,我想知道一种反应灵敏的设计技巧,可以将SVG标记精确地排列到真实播放区域的上方。我解决了这个问题。
它只需要计算视频比率和一些标签的偏移值
<video id="video" width="100%" height="100%" controls src="test.mp4"></video>
<svg id="svg" width="100%" height="100%" style="position: absolute; left:0px; background:gray; opacity:0.5; pointer-events: none;"></svg>
<script>
const svgHandler = (e) => {
let v = document.getElementById("video");
let v_w = v.videoWidth;
let v_h = v.videoHeight;
let c_w = v.clientWidth;
let c_h = v.clientHeight;
let v_rate = v_h / v_w;
let c_rate = c_h / c_w;
// 1. get real playing area
let r_w;
let r_h;
if (v_rate < c_rate) {
r_w = c_w;
r_h = c_w * v_rate;
} else {
r_h = c_h;
r_w = parseInt(r_h / v_rate);
}
// 2. arrange an SVG tag to the above of the real playing area
let v_off = getOffset(v);
let left_padding = (c_w - r_w) / 2 + v_off.left;
if (e.type == "loadeddata") {
let v_panel_off = getOffset(document.body);
left_padding += v_panel_off.left;
}
let top_padding = (c_h - r_h) / 2 + v_off.top;
let s = document.getElementById("svg");
s.style.position = 'absolute';
s.style.top = parseInt(top_padding);
s.style.left = parseInt(left_padding);
s.style.width = parseInt(r_w);
s.style.height = parseInt(r_h);
s.style.pointerEvents = "none";
}
const getOffset = (el) => {
const rect = el.getBoundingClientRect();
return {
left: rect.left + window.scrollX,
top: rect.top + window.scrollY
};
}
document.getElementById("video").addEventListener('loadeddata', svgHandler);
window.onresize = svgHandler;
</script>
常量svgHandler=(e)=>{
设v=document.getElementById(“视频”);
设v_w=v.videoWidth;
设v_h=v.高度;
设c_w=v.clientWidth;
设c_h=v.clientHeight;
设v_率=v_h/v_w;
设c_率=c_h/c_w;
//1.获得真正的比赛场地
让r_w;
让r_h;
if(v_比率{
const rect=el.getBoundingClientRect();
返回{
左:rect.left+window.scrollX,
顶部:rect.top+window.scrollY
};
}
document.getElementById(“视频”).addEventListener(“loadeddata”,svgHandler);
window.onresize=svgHandler;
不确定如何才能到达红色区域。请求视频元素的宽度和高度将为您提供绿色边框区域的尺寸-毕竟,您指定希望video
元素本身如此大。我猜您必须深入研究播放视频文件的实际属性,并希望您可以从那里的某个地方读取其原始w&h…如果您知道实际视频流的宽度和高度,那么您可以使用“padding bottom hack”以正确的纵横比跨越容器元素,然后简单地将视频和svg放在那里。(所有四个角坐标均设置为0,宽度和高度设置为自动。)
<video id="video" width="100%" height="100%" controls src="test.mp4"></video>
<svg id="svg" width="100%" height="100%" style="position: absolute; left:0px; background:gray; opacity:0.5; pointer-events: none;"></svg>
<script>
const svgHandler = (e) => {
let v = document.getElementById("video");
let v_w = v.videoWidth;
let v_h = v.videoHeight;
let c_w = v.clientWidth;
let c_h = v.clientHeight;
let v_rate = v_h / v_w;
let c_rate = c_h / c_w;
// 1. get real playing area
let r_w;
let r_h;
if (v_rate < c_rate) {
r_w = c_w;
r_h = c_w * v_rate;
} else {
r_h = c_h;
r_w = parseInt(r_h / v_rate);
}
// 2. arrange an SVG tag to the above of the real playing area
let v_off = getOffset(v);
let left_padding = (c_w - r_w) / 2 + v_off.left;
if (e.type == "loadeddata") {
let v_panel_off = getOffset(document.body);
left_padding += v_panel_off.left;
}
let top_padding = (c_h - r_h) / 2 + v_off.top;
let s = document.getElementById("svg");
s.style.position = 'absolute';
s.style.top = parseInt(top_padding);
s.style.left = parseInt(left_padding);
s.style.width = parseInt(r_w);
s.style.height = parseInt(r_h);
s.style.pointerEvents = "none";
}
const getOffset = (el) => {
const rect = el.getBoundingClientRect();
return {
left: rect.left + window.scrollX,
top: rect.top + window.scrollY
};
}
document.getElementById("video").addEventListener('loadeddata', svgHandler);
window.onresize = svgHandler;
</script>