React中视频字幕无法被NVDA屏幕阅读器读取,应如何调整代码?
适配方案
1. 先确认终端NVDA与浏览器的无障碍配置
- 打开NVDA菜单,依次进入「首选项」→「设置」→「无障碍」,勾选读出HTML视频字幕选项后保存
- 打开Chrome/Edge浏览器设置,进入「无障碍」页面,开启允许屏幕阅读器读取网页字幕内容开关,若使用Firefox则在
about:config中开启media.webspeech.texttrack.enabled配置项
2. 代码层面优化调整
你修改后将kind属性设置为captions(字幕,包含音效等非对话音频提示)是正确的,在此基础上补充以下属性:
<video width='100%' height='auto' controls role="region" aria-label="帮助视频,配有英文字幕" > <source src={process.env.PUBLIC_URL + '/videos/guestHelpVideo.mp4'} type='video/mp4' /> <track src={process.env.PUBLIC_URL + '/videos/help-video-subtitles.vtt'} type='text/vtt' label='English' kind='captions' srcLang='en' default aria-hidden="false" /> </video>
- 同时确认你的
.vtt字幕文件编码为UTF-8无BOM格式,文件第一行必须是WEBVTT开头,不要有多余的前置空行或特殊字符
3. 兜底适配方案
如果原生track标签仍无法被NVDA识别,可通过监听字幕的cuechange事件,将当前激活的字幕内容同步到aria-live实时区域,NVDA会自动播报该区域的更新内容:
import { useRef, useEffect, useState } from 'react'; function HelpVideo() { const videoRef = useRef(null); const [currentCaption, setCurrentCaption] = useState(''); useEffect(() => { const video = videoRef.current; if (!video) return; const track = video.textTracks[0]; track.mode = 'showing'; const handleCueChange = () => { const activeCues = track.activeCues; if (activeCues.length > 0) { setCurrentCaption(activeCues[0].text); } else { setCurrentCaption(''); } }; track.addEventListener('cuechange', handleCueChange); return () => track.removeEventListener('cuechange', handleCueChange); }, []); return ( <div> <video ref={videoRef} width='100%' height='auto' controls role="region" aria-label="帮助视频,配有英文字幕" > <source src={process.env.PUBLIC_URL + '/videos/guestHelpVideo.mp4'} type='video/mp4' /> <track src={process.env.PUBLIC_URL + '/videos/help-video-subtitles.vtt'} type='text/vtt' label='English' kind='captions' srcLang='en' default /> </video> {/* 实时字幕播报区域,视觉上隐藏但保留无障碍访问 */} <div aria-live="polite" className="sr-only" > {currentCaption} </div> </div> ) }
其中sr-only的样式如下,确保元素视觉不可见但可被屏幕阅读器识别:
.sr-only { position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0, 0, 0, 0); white-space: nowrap; border-width: 0; }
内容的提问来源于stack exchange,提问作者KshitijV97
相关产品推荐
相关产品推荐

