借助CSS has实现打开弹窗时自动锁定滚动

欢迎关注我的公众号:前端侦探

分享一个 CSS 小技巧

在平时开发中,经常会遇到这样一种问题:当打开一个弹窗时,后面的页面是可以滚动的,演示如下

那么,该如何锁定页面的滚动呢?

一、传统的实现方式

传统的方式其实也不复杂,就是在打开弹窗时阻止滚动就行了,通常是改变overflow属性

js 复制代码
const openModal = () => {
  document.body.style.overflow = 'hidden'
}

const closeModal = () => {
  document.body.style.overflow = 'auto'
}

如果是在现代框架里,比如vue,可以用监听弹窗状态来实现

js 复制代码
watch(
  () => show.value,
  (val) => {
    if (val) {
      document.body.style.overflow = 'hidden'
    } else {
      document.body.style.overflow = 'auto'
    }
  },
)

这样就能锁定滚动了

二、传统方式的局限

虽然上面的实现看似完美,其实还有潜在问题的。比如有多个弹窗,弹窗覆盖的情况下,这个时候锁定就会出问题了。

因为在关闭第二个弹窗的时候,页面已经解除锁定了,所以在第一个弹窗还在的时候,页面已经可以滚动了

如果想要优化这个问题,还需要做进一步的判断

三、借助 CSS has 实现

现在有了CSS :has伪类,一切就好办了,无需过多的判断,直接一个选择器搞定

css 复制代码
body:has(dialog[open]){
  overflow: hidden
}

这行选择器表示,只要有属性为open的弹窗,body就自动锁定,无论有多少层弹窗

天然就实现了打开弹窗时自动锁定,是不是非常简单?

完整代码可以查看:CSS has lock scroll (juejin.cn)

四、has已经全兼容了

提一下兼容性,目前现代浏览器都支持了(虽然还比较新,但各大浏览器都跟进了),如下

其实关于has能做的事情有很多很多,远不止父级选择器 那么简单,可以说has可以选择网页中任意元素。

关于has选择器的用途,之前在这篇文章中还有其他介绍,可以参考一下:CSS 有了:has伪类可以做些什么? - 掘金 (juejin.cn)

最后,如果觉得还不错,对你有帮助的话,欢迎点赞、收藏、转发 ❤❤❤

相关推荐
子兮曰4 天前
jev-ultrafast 深度解析:7 秒订机票的浏览器 Agent 是如何炼成的
前端·后端·agent
子兮曰4 天前
Jev 爆发一周:7 秒 Agent 背后的 System One 生态与三场争议
前端·后端·ai编程
前端小万4 天前
写公众号赚了 3000 块后,我做了一款叫 "一键成稿" 的软件
前端·微信小程序
爱勇宝4 天前
ZCode 开源 24 小时:一份没有历史的账本,回答不了"有没有偷代码"
前端·后端·chatglm (智谱)
三十而立洋4 天前
Cookie 详解:从产生到安全,一次讲透
前端·javascript
卡布鲁4 天前
把一个 Vite + Vue3 应用塞进 qiankun (React + Umi3) 主站:十个坑的复盘
前端·javascript·react.js
汉堡大王95274 天前
Jev:不是聊天机器人, 而是一个智能 if 语句
前端·人工智能·后端
梦想很大很大4 天前
从运行事实到回归证据:Workrun 的 Telemetry 与 Evaluation 实践
前端·人工智能·后端
计算机魔术师4 天前
Meta Muse agent 接入 Shopify 的 Shop Pay 实现代理式购物
前端
沙蒿同学4 天前
我用 Go 搭了一条 AI Agent 流水线:从 1 张商品图到一整套淘宝详情页
前端·javascript·后端