全屏API调用虽同步,但状态变更异步,需用Promise封装并监听fullscreenchange事件来可靠处理成功与失败;必须在用户手势中调用,且需清理事件监听器防泄漏。

全屏 API(requestFullscreen 和 exitFullscreen)本身是同步调用,但其实际状态变化是异步的,会触发 fullscreenchange 事件。直接使用回调或轮询判断状态不够可靠,用 Promise 封装能统一处理成功与失败,提升可读性和可组合性。
封装 requestFullscreen 为 Promise
监听 fullscreenchange 事件,在进入全屏后 resolve;同时监听 fullscreenerror 或检查 document.fullscreenElement 是否为 null 来 reject 失败情况。注意:需在用户手势(如 click)中调用,否则会被浏览器静默拒绝。
- 先保存当前文档引用,避免异步执行时
this或document变化 - 注册一次性的
fullscreenchange监听器,进入全屏(document.fullscreenElement !== null)即 resolve - 同时监听
fullscreenerror,或在超时/检测到仍无全屏元素时 reject - 记得清理事件监听器,防止内存泄漏
示例:
function requestFullscreen(el) {
return new Promise((resolve, reject) => {
if (!el.requestFullscreen) {
reject(new Error('Fullscreen API not supported'));
return;
}
<pre class="brush:php;toolbar:false;">const onFullscreenChange = () => {
if (document.fullscreenElement === el) {
document.removeEventListener('fullscreenchange', onFullscreenChange);
document.removeEventListener('fullscreenerror', onFullscreenError);
resolve();
}
};
const onFullscreenError = () => {
document.removeEventListener('fullscreenchange', onFullscreenChange);
document.removeEventListener('fullscreenerror', onFullscreenError);
reject(new Error('Fullscreen request denied or failed'));
};
document.addEventListener('fullscreenchange', onFullscreenChange);
document.addEventListener('fullscreenerror', onFullscreenError);
el.requestFullscreen().catch(reject); // 兼容部分浏览器的 Promise 返回}); }
封装 exitFullscreen 为 Promise
退出全屏同样依赖 fullscreenchange 事件:当 document.fullscreenElement 变为 null 时表示退出完成。
- 无需额外权限检查,但需确保当前处于全屏状态再调用(可选前置校验)
- 同样使用一次性事件监听,避免重复触发
-
document.exitFullscreen()在非全屏时调用会返回已解决的 Promise(现代浏览器),但仍建议统一走事件流以保持行为一致
示例:
function exitFullscreen() {
return new Promise((resolve, reject) => {
if (!document.exitFullscreen) {
reject(new Error('Fullscreen API not supported'));
return;
}
<pre class="brush:php;toolbar:false;">const onFullscreenChange = () => {
if (document.fullscreenElement === null) {
document.removeEventListener('fullscreenchange', onFullscreenChange);
document.removeEventListener('fullscreenerror', onFullscreenError);
resolve();
}
};
const onFullscreenError = () => {
document.removeEventListener('fullscreenchange', onFullscreenChange);
document.removeEventListener('fullscreenerror', onFullscreenError);
reject(new Error('Fullscreen exit failed'));
};
document.addEventListener('fullscreenchange', onFullscreenChange);
document.addEventListener('fullscreenerror', onFullscreenError);
document.exitFullscreen().catch(reject);}); }
组合使用与错误处理
可将两个 Promise 封装函数组合成 toggle 全屏逻辑,并统一处理常见异常(如跨 iframe 调用、权限限制、移动设备不支持等)。
- 用
async/await链式调用更清晰:先尝试退出,再请求新元素全屏 - 捕获
DOMException类型错误(如"NotAllowedError"),提示用户需交互触发 - 对移动端可加 UA 判断,提前拒绝不支持场景,避免无效调用
示例 toggle:
async function toggleFullscreen(el) {
try {
if (document.fullscreenElement) {
await exitFullscreen();
}
await requestFullscreen(el);
console.log('Entered fullscreen successfully');
} catch (err) {
console.warn('Fullscreen toggle failed:', err.message);
// 可触发 UI 提示,例如“请在点击按钮后重试”或“当前环境不支持全屏”
}
}
注意事项与兼容性补充
旧版浏览器需适配带前缀的方法(如 webkitRequestFullscreen),但现代项目通常通过 screenfull.js 等库处理。若自行兼容,应在封装函数内做特性检测并调用对应方法,Promise 结构保持不变。
- 不要依赖
requestFullscreen()的返回值是否为 Promise:部分浏览器(如旧版 Safari)不返回 Promise,必须靠事件驱动 -
fullscreenchange是唯一可靠的完成信号,不能仅靠调用后立即查document.fullscreenElement - 在 iframe 中启用全屏需设置
allow="fullscreen"属性,否则会被忽略
大量免费API接口:立即使用
涵盖生活服务API、金融科技API、企业工商API、等相关的API接口服务。免费API接口可安全、合规地连接上下游,为数据API应用能力赋能!











