必须由用户手势触发,否则requestFullscreen()静默失败或抛NotAllowedError;需在click、keydown等用户事件回调中调用,禁用setTimeout等异步调用,移动端优先用click,确保元素已挂载且非跨域iframe。

全屏切换不是“调个 API 就完事”,核心限制只有一条:必须由用户手势触发,否则 requestFullscreen() 会静默失败或抛出 NotAllowedError。 其他所有兼容性、状态监听、样式修复问题,都建立在这个前提之上。
requestFullscreen() 被忽略或报 NotAllowedError 怎么办
这是最常遇到的卡点。现象是点击按钮毫无反应,控制台也不报错;或者明确看到 NotAllowedError: API can only be initiated by a user gesture。
- 检查调用是否在真实的用户事件回调里——只允许
click、keydown(且event.key非空)、touchend(iOS Safari 建议降级为click)中直接调用,不能包在setTimeout、Promise.then、fetch().then或页面load后的钩子里 - 确保目标元素已挂载到 DOM,
document.getElementById('video')返回非null,且不是iframe或跨域内容 - 移动端特别注意:
<video></video>必须没设playsinline属性,否则 iOS Safari 拒绝全屏请求 - 不要提前检查
document.fullscreenElement再决定调用哪个方法——进不进全屏,只看requestFullscreen()是否被允许执行,而不是“当前是不是全屏”
如何安全地 toggle 全屏(进/出自动判断)
所谓 “toggle” 是伪概念,API 本身没有 toggle 方法。你得靠 document.fullscreenElement 判断当前状态,再分别调用 requestFullscreen() 或 document.exitFullscreen()。
-
document.fullscreenElement是唯一可靠的状态标识:为null表示未全屏;否则返回当前全屏的 DOM 元素(注意拼写是fullscreen,不是fullScreen) - 退出全屏必须显式调用
document.exitFullscreen(),不能只依赖用户按 Esc 键——Esc 不会触发你的 JS 逻辑,UI 状态容易脱节 - 调用
document.exitFullscreen()前无需判空,它在非全屏状态下执行不会报错(现代浏览器),但老版 Edge 可能抛NotFoundError,建议统一加.catch(() => {}) - 示例逻辑:
function toggleFullscreen(el) {
if (document.fullscreenElement) {
document.exitFullscreen().catch(() => {});
} else {
el.requestFullscreen().catch(err => console.error('全屏被拒:', err.message));
}
}
监听全屏状态变化为什么总失效
监听必须绑定在 document 上,且事件名必须匹配当前浏览器实际触发的类型。漏掉前缀或绑错对象,就收不到通知。
立即学习“前端免费学习笔记(深入)”;
- 标准事件是
fullscreenchange,但旧版 Chrome/Safari 用webkitfullscreenchange,IE/Edge 用msfullscreenchange;现代浏览器已统一支持无前缀版本,但若你用了带前缀的requestFullscreen(比如webkitRequestFullscreen),某些老环境仍需对应监听带前缀事件 - 事件永远触发在
document上,不是目标元素上——写成el.addEventListener('fullscreenchange', ...)一定无效 - 别用
document.isFullscreen(根本不存在),也别在事件回调里反复查document.fullscreenElement === el来“确认是否是自己”——只要document.fullscreenElement存在,就说明有元素处于全屏,UI 更新应基于这个值做响应 - 推荐写法:
document.addEventListener('fullscreenchange', () => {
const isFullscreen = !!document.fullscreenElement;
button.textContent = isFullscreen ? '退出全屏' : '全屏显示';
});
:fullscreen 伪类为什么没生效
:fullscreen 只对通过 JavaScript 调用 requestFullscreen() 进入全屏的元素生效,对 F11 或地址栏菜单触发的浏览器级全屏无效。
- CSS 规则必须精确匹配目标元素,例如
video:fullscreen不会作用于div#container:fullscreen - 旧版浏览器需要补前缀:
video:-webkit-full-screen、video:-moz-full-screen、video:-ms-fullscreen - 常见用途是重置尺寸和隐藏滚动条:
video:fullscreen { width: 100vw !important; height: 100vh !important; }、:fullscreen ::-webkit-scrollbar { display: none; } - 注意:全屏后
position: fixed元素行为异常很常见,优先用position: absolute+top/left/right/bottom: 0替代
真正难处理的从来不是 API 调用本身,而是全屏后焦点丢失、键盘事件拦截、滚动锁定、以及不同设备对手势的差异化判定——这些没法靠一个 requestFullscreen() 解决,得在交互流程里逐层防御。


















