React组件中视频播放时如何更新HTML progress标签的进度值
修正后的实现方案
你现有代码存在3个可优化点:直接操作DOM不符合React规范、setInterval未设置间隔也未做清理、缺少触发progressLoop的时机,以下是符合React开发规范的完整实现:
React 代码
import React, { useRef, useState, useEffect } from 'react' const VideoSection = () => { const videoRef = useRef(null) const timerRef = useRef(null) const [progress, setProgress] = useState(0) // 清理定时器的公共方法 const clearProgressTimer = () => { if (timerRef.current) { clearInterval(timerRef.current) timerRef.current = null } } const progressLoop = () => { // 先清掉之前的定时器,避免重复触发 clearProgressTimer() // 每100ms更新一次进度,兼顾流畅度和性能 timerRef.current = setInterval(() => { const video = videoRef.current if (!video || !video.duration) return setProgress(Math.round((video.currentTime / video.duration) * 100)) // 视频播放结束自动清定时器 if (video.currentTime >= video.duration) { clearProgressTimer() } }, 100) } const handlePlayVideo = () => { videoRef.current?.play() // 视频开始播放时启动进度更新轮询 progressLoop() } const handlePauseVideo = () => { // 视频暂停时停止进度更新 clearProgressTimer() } // 组件卸载时清理定时器,避免内存泄漏 useEffect(() => { return () => clearProgressTimer() }, []) return ( <div> <button onClick={handlePlayVideo}> Play video </button> <button onClick={handlePauseVideo}> Pause video </button> <video src='./video.mp4' ref={videoRef} // 也可以绑定视频的timeUpdate事件替代定时器,性能更好 // onTimeUpdate={() => { // const video = videoRef.current // setProgress(Math.round((video.currentTime / video.duration) * 100)) // }} /> <progress max="100" value={progress} > Progress </progress> </div> ) } export default VideoSection
优化说明
- 你可以选择注释里的
onTimeUpdate事件替代setInterval方案,该事件是浏览器原生的视频时间更新回调,不需要手动轮询,性能更优 - 新增了暂停按钮和对应的逻辑,满足常规播放器操作需求
- 所有DOM操作都替换为React状态管理,移除了不必要的id选择器
CSS 代码(兼容多浏览器)
progress[value] { appearance: none; border: none; width: 100%; height: 6px; } /* 兼容Chrome、Safari */ progress[value]::-webkit-progress-value { background-color: green; } /* 兼容Firefox */ progress[value]::-moz-progress-bar { background-color: green; }
内容的提问来源于stack exchange,提问作者H.sha
相关产品推荐
相关产品推荐

