HTML5 无折叠屏原生适配机制,需用 CSS screen-spanning 媒体查询(Chromium 119+)配合 window.matchMedia 监听铰链状态,禁用 display-mode、resize 和 @container 等误用方案。

HTML5 本身不处理折叠屏的布局适配,也没有 XML 布局机制——这是 Android 原生开发(如 res/layout 下的 .xml 文件)的概念。你在 Web 端用 HTML/CSS/JS 开发时,适配折叠屏靠的是 CSS 媒体查询、window.matchMedia 和 screen.orientation 等 Web API,不是 XML。
折叠屏检测:用 @media (display-mode: standalone) 不管用
很多开发者误以为 display-mode 能区分折叠状态,其实它只反映 PWA 启动模式(standalone / browser)。真正可用的是 screen-spanning 这个实验性媒体特性,但目前仅 Chromium 119+(Android 上的 Chrome/Edge)支持:
@media (screen-spanning: single-fold-horizontal) {
.app-header { display: none; }
.dual-panel { display: grid; grid-template-columns: 1fr 1fr; }
}
注意:single-fold-horizontal 表示横屏折叠(铰链在上下边),single-fold-vertical 表示竖屏折叠(铰链在左右边)。未匹配时回退到默认单面板布局。
- 别依赖
min-width或aspect-ratio猜测折叠态——同一设备横竖屏下宽高互换,但折叠态和非折叠态可能有相同尺寸 -
screen-spanning在桌面浏览器或旧版 Chrome 中返回not all,需加 JS 回退逻辑 - 真机调试必须用支持该特性的 Android 设备(如 Galaxy Z Fold 系列 + Chrome Beta)
window.matchMedia 监听折叠变化比 resize 更可靠
resize 事件在折叠动画过程中频繁触发且不精准;而 matchMedia 可监听媒体查询状态切换,配合 addEventListener('change') 捕获铰链展开/闭合的关键节点:
立即学习“前端免费学习笔记(深入)”;
const foldQuery = window.matchMedia('(screen-spanning: single-fold-horizontal)');
foldQuery.addEventListener('change', e => {
if (e.matches) {
document.body.classList.add('folded-horizontal');
} else {
document.body.classList.remove('folded-horizontal');
}
});
- 必须在页面加载后立即执行,不能等
DOMContentLoaded太晚——折叠状态可能已确定 - 同一设备可能同时满足多个媒体查询(如横屏 +
single-fold-horizontal),优先级由 CSS 层叠规则决定 - 不要在回调里直接操作大量 DOM;用
requestAnimationFrame批量更新样式
CSS container 查询暂不适用于折叠屏布局
有人想用 CSS @container 根据面板容器宽度自动切换布局,但折叠屏的两个物理屏幕是独立渲染区域,浏览器不会把它们合成一个“容器”。@container 依赖 container-type 的显式声明,对跨屏布局无效。
- 当前唯一可靠的跨屏感知方式仍是
screen-spanning媒体查询 + JS 辅助判断 - 若需兼容 iOS(无
screen-spanning支持),只能降级为基于screen.width和screen.height的启发式判断(例如:宽 > 800px 且高 - 避免用
viewportwidth/height 判断——折叠动画中 viewport 尺寸会剧烈抖动,不可信
折叠屏 Web 适配的核心矛盾在于:浏览器尚未统一暴露铰链位置、面板尺寸、是否正在动画等底层信息。现在能做的,就是用 screen-spanning 抓住 Chromium 生态的有限能力,再用 JS 补足边界情况。别试图用一套 CSS 通吃所有折叠形态——不同厂商的铰链偏移、黑边宽度、多窗口策略都不同,硬套只会让布局在某个机型上突然错位。










