controlsList 是 Chromium 专属属性,仅能视觉隐藏原生控件(如 nodownload、nofullscreen),不真正禁用功能,且 Firefox/Safari 完全忽略;必须配合 controls 使用,值须小写空格分隔,不可引号内含空格,非 W3C 标准,无法跨浏览器一致控制下载等行为。

controlsList 属性到底能做什么
它只能在 Chromium 系统(Chrome、Edge)里隐藏原生控件按钮,比如 nodownload 会去掉下载图标,nofullscreen 会让全屏按钮消失,noremoteplayback 禁用 AirPlay / Cast 按钮。但它不是功能开关——按钮没了,不代表对应能力被禁用。用户仍可通过 DevTools 查看网络请求拿到视频地址,或右键另存为(部分浏览器仍保留该菜单项)。
Firefox 和 Safari 完全忽略这个属性,连解析都不做;即使写了 controlsList="nodownload",它们照样显示下载按钮。
- 必须配合
controls属性才生效,单独写controlsList没效果 - 值必须小写、空格分隔、无多余空格(
"nodownload nofullscreen"中双空格可能被 Chrome 忽略) - 不支持引号内带空格的写法,如
controlsList="no download"是无效的
为什么 controlsList 在 Firefox/Safari 里不生效
因为 controlsList 不是 W3C 标准属性,而是 Chromium 的私有扩展。W3C 曾讨论但未纳入正式规范,所以其他引擎没实现。你不能靠它做跨浏览器一致控制——如果业务要求“所有浏览器都看不到下载按钮”,这条路走不通。
实际开发中,看到 Safari 用户依然能点下载,别怀疑代码,就是浏览器不支持。这时候得换思路:要么降级为完全隐藏原生控件(controls 不写),要么用自定义 UI + JS 控制逻辑。
- 检查是否真在 Chrome/Edge 最新版运行(旧版 Chromium 可能不支持
noplaybackrate) - 用 DevTools 的 Elements 面板直接查看
<video>元素,确认渲染出的控件栏是否少了对应按钮 - 不要依赖 JavaScript 动态设置
element.controlsList = "...",该属性只接受 HTML 属性写法,JS 设置无效
想彻底禁用下载?controlsList 不是答案
nodownload 只是视觉隐藏,资源一旦加载,就暴露在 Network 面板里。哪怕按钮没了,用户打开开发者工具 → Network → Filter “media” → 找到 .mp4 请求 → 右键 Copy link address,就能直接下载。
真正防下载得从服务端入手:
- 用签名 URL 或短期 Token(如 5 分钟过期),每次播放前动态生成
- 采用 HLS 或 DASH 分片传输,配合 DRM(Widevine/FairPlay)加密解密流程
- 自定义播放器:移除
controls,用<canvas>或 WebAssembly 渲染帧,避免暴露原始媒体链接
单纯靠前端属性,永远挡不住有心人。controlsList 的定位是“界面精简”和“降低误操作概率”,不是内容保护方案。
替代方案:用 CSS 伪元素隐藏控件(仅限 WebKit)
如果你需要更细粒度控制(比如只隐藏音量滑块,保留进度条),controlsList 不够用。WebKit 内核支持一组伪类选择器,可强制隐藏特定控件:
video::-webkit-media-controls-volume-slider {
display: none !important;
}
但要注意:
- 这些伪类只在 Chrome/Edge/Safari 生效,Firefox 不识别
- 不同浏览器的伪元素名略有差异(Safari 对某些伪类支持不稳定)
- 未来浏览器更新可能调整 Shadow DOM 结构,导致选择器失效
- 不能通过 JS 查询这些伪元素是否存在,也无法监听其点击事件
最终效果取决于浏览器内部实现细节,比 controlsList 更脆弱,只适合内部项目或对兼容性要求极低的场景。

















