【CSS 小知识】网页弹出浮层时,禁止背景滚动的几种方法

4,510 阅读7分钟

本文由 ChatGPT 归纳总结,一切权利归 ChatGPT 所有,且本人不保证内容的正确性。

当弹出浮层时,如何用 CSS 防止页面滚动?

如果需要,可以通过下面的模板代码进行测试:

提问开始了,show time。

overflow:hidden

您可以使用 CSS 的 overflow:hidden 属性来防止页面在弹出浮层时滚动。具体来说,可以通过以下步骤实现:

  1. 在HTML的 <body> 标签上添加一个类名,例如 no-scroll。

  2. 使用 CSS 将该类名与 overflow:hidden 属性关联,这将防止页面滚动,同时也会隐藏滚动条,例如:

.no-scroll {
  overflow: hidden;
}
  1. 当弹出浮层时,使用 JavaScript 将该类名添加到 <body> 标签中,例如:
document.querySelector('body').classList.add('no-scroll');
  1. 当浮层关闭时,使用 JavaScript 将该类名从 <body> 标签中删除,例如:
document.querySelector('body').classList.remove('no-scroll');

这样,当浮层弹出时,页面将不再滚动,而是保持固定。

position: fixed

除了 overflow:hidden 还有别的方法吗?

除了 overflow:hidden,还有一种方法可以防止页面滚动,那就是使用 position: fixed。该方法的实现步骤如下:

  1. 在 HTML 的 <body> 标签上添加一个类名,例如 no-scroll。

  2. 使用 CSS 将该类名与以下属性关联:

.no-scroll {
  position: fixed;
  width: 100%;
}

这将使页面固定在原地,同时保持原来的宽度。请注意,如果您使用这种方法,请确保您的弹出浮层具有合适的高度,以避免出现内容截断的情况。

  1. 当弹出浮层时,使用 JavaScript 将该类名添加到 ` 标签中,例如:
document.querySelector('body').classList.add('no-scroll');
  1. 当浮层关闭时,使用 JavaScript 将该类名从 <body> 标签中删除,例如:
document.querySelector('body').classList.remove('no-scroll');

使用 position: fixed 可以有效地防止页面滚动,并且可以确保内容不会被截断。然而,如果您的浮层高度不够不合适,使用这种方法可能会导致页面底部的内容被遮盖。因此,建议在实现之前对页面进行测试,以确保该方法适用于您的特定情况。

scroll 事件

继续追问:

还有吗?

除了上述两种方法,还有一种更为简单的方法,那就是使用 JavaScript 来实现。具体来说,可以在弹出浮层时,禁用 document 对象上的 scroll 事件来防止页面滚动。实现步骤如下:

  1. 在弹出浮层时,使用 JavaScript 将 document 对象上的 scroll 事件禁用:
document.addEventListener('scroll', disableScroll);
function disableScroll() {
  window.scrollTo(0, 0);
}

这会将页面滚动到顶部,并阻止进一步滚动。

  1. 当浮层关闭时,使用 JavaScript 将 document 对象上的 scroll 事件重新启用:
document.removeEventListener('scroll', disableScroll);

这将允许用户再次滚动页面。

这种方法的好处是它不需要更改 CSS 样式或将元素的位置设置为固定,因此不会对页面布局产生任何影响。另外,这种方法还可以使用在移动设备上,因为移动设备上的滚动行为可能不同于桌面设备。但是,这种方法需要编写一些 JavaScript 代码来实现,因此可能需要一些编程知识。

补充:ChatGPT 没有给出这种方法的一大缺点说明:会把浮层里面的滚动事件也给禁用了。

position: sticky

继续追问,ChatGPT 又给出了一种方法:

还有一种方法可以防止页面滚动,那就是使用 CSS3 中的 position: sticky 属性。position: sticky 可以让元素在滚动到指定位置时“停留”在屏幕上,不随页面滚动而滚动,同时也不需要设置元素的高度或使用 overflow:hiddenposition: fixed。但需要注意的是,position: sticky 目前还不支持 IE 浏览器和旧版的 Edge 浏览器。实现步骤如下:

  1. 在弹出浮层时,使用 JavaScript 将 <body> 元素添加一个类名,例如 no-scroll:
document.querySelector('body').classList.add('no-scroll');
  1. 在 CSS 中,定义 no-scroll 类的样式:
.no-scroll {
  height: 100vh;
}

.no-scroll > * {
  position: sticky;
  top: 0;
}

这将设置 <body> 元素的高度为 100% 屏幕高度,并将子元素(即页面内容)的位置设置为 sticky,这样子元素就会“停留”在屏幕上。

  1. 当浮层关闭时,使用 JavaScript 将 <body> 元素的 no-scroll 类名删除:
document.querySelector('body').classList.remove('no-scroll');

这将恢复页面的滚动。

使用 position: sticky 方法,不需要更改页面布局和元素的位置,也不需要添加 overflow:hidden 属性或将元素的位置设置为 fixed,而且也不需要编写复杂的 JavaScript 代码。不过,需要注意的是,position: sticky 目前还不支持 IE 浏览器和旧版的 Edge 浏览器。

overscroll-behavior: contain

当我继续追问,ChatGPT 开始一本正经的给出之前给的答案了,此时我也就中断了 ChatGPT 的回答。

image.png

然后我换了另一个问题提问:我听说「给弹出层添加 overscroll-behavior: contain; 也可以防止 body 滚动」 这个说法正确吗?

是的,您所听说的方法也可以用来防止页面滚动。overscroll-behavior 属性可以用来控制页面在滚动到边缘时的行为。其中,overscroll-behavior: contain; 可以防止页面滚动,但允许内部元素滚动。

实现步骤如下:

  1. 在弹出浮层时,为浮层添加 overscroll-behavior: contain; 属性:
.popup {
  position: fixed;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  overscroll-behavior: contain;
}

这将禁用页面滚动,但允许浮层内的元素滚动。

  1. 当浮层关闭时,将浮层的 overscroll-behavior 属性移除即可:
document.querySelector('.popup').style.overscrollBehavior = 'auto';

这样可以还原页面滚动。

使用 overscroll-behavior: contain; 方法,不需要更改页面布局和元素的位置,也不需要添加 overflow:hidden 属性或将元素的位置设置为 fixed。此外,这种方法允许浮层内的元素滚动,因此用户仍然可以与浮层进行交互。

事实上,overscroll-behavior: contain; 的作用是防止页面的默认滚动行为(overscroll)影响指定元素,使得在该元素内部滚动时,不会影响到页面的其他部分。所以这个方法 仅适用浮层内有滚动条的情况。

总结

最后我让 ChatGPT 总结了下上面四种方案的优缺点,以下是回答。

好的,下面是四种方法的优缺点总结:

  1. overflow: hidden; 方法:

优点:简单易用,不需要更改页面布局和元素的位置,适用于大多数情况。

缺点:不能允许浮层内的元素滚动,如果需要浮层内元素滚动,则不适用;同时可能会破坏页面的用户体验,使用户感到页面突然“卡住”或无法滚动。

  1. position: fixed; 方法:

优点:可以实现不同的页面滚动方式,允许浮层内元素滚动,且适用于大多数情况。

缺点:需要将浮层的位置设置为固定位置,可能需要更改页面布局和元素的位置,同时需要将页面滚动条隐藏,可能会破坏页面的用户体验。

  1. position: sticky; 方法:

优点:不需要更改页面布局和元素的位置,不需要添加 overflow:hidden 属性或将元素的位置设置为 fixed,且允许浮层内元素滚动。

缺点:目前还不支持 IE 浏览器和旧版的 Edge 浏览器。

  1. overscroll-behavior: contain; 方法:

优点:不需要更改页面布局和元素的位置,不需要添加 overflow:hidden 属性或将元素的位置设置为 fixed,允许浮层内元素滚动。

缺点:目前还不支持 IE 浏览器和旧版的 Edge 浏览器。

根据具体情况选择不同的方法可以更好地解决问题。

可以看到 ChatGPT 的正确率很高,但并不是百分之百正确,需要我们做些 review,绝对是一个不错的 AI 智能助手。

主题:掘金自带——channing-cyan。