track元素的default属性未设置时默认不激活;js启用需先确保dom插入、loadedmetadata触发且readystate为2,再设mode='showing';应避免硬索引texttracks[0],优先用kind/label或id定位。

track元素的default属性不设时,track默认不会被激活
浏览器只会在 <track default></track> 显式存在时自动启用对应字幕轨道;没写 default,哪怕它是页面里唯一的 <track></track>,也不会自动显示。这不是 bug,是规范行为——default 是唯一触发“初始启用”的开关,JS 无法绕过它“模拟”这个初始状态。
用JS手动启用track需先确保track已加载且ready
常见错误是直接操作 track.mode 却没等 track 就绪,结果无效。关键点:
-
track必须已插入 DOM,且<video></video>已加载元数据(触发loadedmetadata) - 检查
track.readyState:0=uninitialized,1=loading,2=loaded —— 只有到 2 才能安全设mode - 设
track.mode = 'showing'才会显示字幕;'hidden'隐藏,'disabled'完全禁用(包括JS控制)
示例:
video.addEventListener('loadedmetadata', () => {
const track = video.textTracks[0];
if (track && track.readyState === 2) {
track.mode = 'showing';
}
});
textTracks索引不稳定,别硬写[0]
即使只有一个 <track kind="subtitles"></track>,textTracks 列表顺序也不保证稳定(尤其动态添加或跨浏览器)。更可靠的做法:
- 用
video.textTracks.forEach(t => { if (t.kind === 'subtitles' && t.label === 'English') t.mode = 'showing'; }) - 或提前给
<track></track>加id,再用document.getElementById('eng-sub')拿到后操作 - 注意:修改
mode后,video.textTracks的onchange不会触发,得自己监听逻辑
Chrome/Firefox对动态启用track的支持差异
不是所有浏览器都允许 JS 在任意时机启用字幕:
- Chrome 要求视频至少播放过一次(哪怕
play().catch()也行),否则mode = 'showing'会被静默忽略 - Firefox 相对宽松,但若
track的src是跨域且没配 CORS,readyState可能卡在 1,永远到不了 2 - 移动端 Safari 对非
default轨道的 JS 控制更敏感,建议加setTimeout延迟 100ms 再设mode,避开渲染竞态
最稳妥的路径:等 loadedmetadata → 等 track.readyState === 2 → 触发一次 video.play().catch(e => {})(仅作权限解锁)→ 再设 mode = 'showing'。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











