溢出式菜单

CSS 播客 - 034:溢出

当内容超出其父元素的范围时,您可以通过多种方式来处理这种情况。您可以滚动添加更多空间、剪裁溢出的边缘、使用省略号指示截断位置,等等。在开发手机应用和支持多种屏幕尺寸的应用时,尤其需要考虑溢出问题。

CSS 中有两种不同的剪裁选项;text-overflow 有助于剪裁单行文字,而 overflow 属性有助于控制框模型中的溢出。

单行溢出(使用 text-overflow

在包含文本节点(例如段落 <p>)的任何元素上使用 text-overflow 属性。它用于指定文本在不适合元素可用空间时如何显示。网页上所有可查看的 HTML 文本都位于文本节点中。如需使用 text-overflow,您需要一行未换行的文本,因此您还必须将 overflow 设置为 hidden,并提供可防止换行的 white-space 值。

p {
    text-overflow: ellipsis;
    overflow: hidden;
    white-space: nowrap;
}

使用 overflow 属性

溢出属性设置在元素上,用于控制当其子元素需要的空间超出其可用空间时会发生什么情况。这可能是有意为之,例如在 Google 地图等互动式地图中,用户可以平移剪裁为特定尺寸的大图片。也可能是无意的,例如在聊天应用中,用户输入了一条很长的消息,但该消息无法完全显示在文本气泡中。

您可以将溢出视为两个部分。父元素的空间受到严格限制,不会发生变化。您可以将此视为一个窗口。子元素是希望与父元素之间有更多空间的元素。您可以将此视为您透过窗口看到的景象。管理溢出有助于指导窗口如何框定此内容。

在垂直和水平轴上滚动

overflow-y 属性用于控制设备视口垂直轴上的物理溢出,因此会向上和向下滚动。

overflow-x 属性可控制设备视口水平轴上的溢出,从而实现左右滚动。

滚动方向的逻辑属性

Browser Support

  • Chrome: 135.
  • Edge: 135.
  • Firefox: 69.
  • Safari: not supported.

Source

overflow-inlineoverflow-block 属性会根据文档方向和书写模式设置溢出。

overflow 简写形式

overflow 简写形式可在一行中同时设置 overflow-xoverflow-y 样式:

overflow: hidden scroll;

如果指定了两个关键字,则第一个关键字适用于 overflow-x,第二个关键字适用于 overflow-y。否则,overflow-xoverflow-y 使用相同的值。

详细了解适用于 overflow 属性的值和关键字

overflow: visible(默认)
如果不设置该属性,overflow: visible 是网页的默认值。这样可确保内容永远不会被意外隐藏,并遵循“永不隐藏内容”或“精确布局的安全布局”的核心原则。
overflow: hidden
使用 overflow: hidden 时,内容会在指定方向上被剪裁,并且不会提供滚动条来显示它。
overflow: scroll
overflow: scroll 可启用滚动条,以便用户滚动浏览内容。即使内容未溢出,也会显示滚动条。如果容器将来可能会滚动(例如,根据调整大小),这是一种减少未来布局偏移的好方法,并且可以直观地让用户为可滚动区域做好准备。
overflow: clip
overflow: hidden 类似,具有 overflow: clip 的内容会被剪裁到元素的内边距框。cliphidden 的区别在于,clip 关键字还会禁止所有滚动,包括程序化滚动。
overflow: auto
最后,是使用最频繁的值,即 overflow: auto。这样可以尊重用户的偏好设置,并在需要时显示滚动条,但默认情况下会隐藏滚动条,并将滚动责任交给用户和浏览器。

滚动和溢出

许多 overflow 行为都会引入滚动条,但有一些特定的滚动行为和属性可以帮助您控制溢出容器的滚动。

滚动和无障碍功能

请务必确保可滚动区域可以接受焦点,以便键盘用户可以使用 Tab 键切换到该框,然后使用箭头键滚动。

如需允许滚动框接受焦点,请添加 tabindex="0"、具有 aria-labelledby 属性的名称和适当的 role 属性。例如:

<div tabindex="0" role="region" aria-labelledby="id-of-descriptive-text">
    content
</div>

然后,可以使用 CSS 指示该框已获得焦点,并使用 outline 属性提供视觉提示,表明该框现在可以滚动。

使用 CSS 来强制执行无障碍功能一文中,Adrian Roselli 演示了 CSS 如何帮助防止无障碍功能退化。例如,仅当使用正确的属性时,才开启滚动并添加焦点指示器。以下规则仅在盒子具有 tabindexaria-labelledbyrole 属性时才会使其可滚动。

[role][aria-labelledby][tabindex] {
  overflow: auto;
}

[role][aria-labelledby][tabindex]:focus {
  outline: .1em solid blue;
}

盒子模型中的滚动条位置

滚动条会占用内边距框内的空间,如果 inline 而不是 overlaid,则可能会争夺空间。盒子模型模块会更详细地介绍这种潜在的布局偏移来源。

根滚动器与隐式滚动器

您可能会注意到,某些滚动条具有下拉刷新行为和其他特殊行为,尤其是在开发移动应用和混合应用时。此滚动行为发生在根滚动器上。一个网页上始终只有一个根滚动器。默认情况下,documentElement 是网页的根滚动器,不过,通过更改根滚动器,可以将特殊行为应用于 documentElement 以外的滚动器,我们将此新滚动器称为隐式根滚动器。

如需创建根滚动器,您可以采用一种称为滚动器提升的方法,即将容器定位为固定,确保其覆盖整个视口,并使用滚动器将 z-index 设置为最高。点击此处体验根滚动器与嵌套的隐式滚动器。

与滚动没有增强滚动行为的隐式滚动器相比,该视频展示了具有反弹行为和新样式功能的根滚动器。

设置滚动条样式

您可以设置滚动条的样式,使其融入网站的设计。scrollbar-color 设置滚动条的滑块和边衬的颜色。

如需更改滚动条的宽度,请使用 scrollbar-width。您无法将此属性设置为任意长度,但可以指定需要 thin 滚动条还是 none

scroll-behavior

Browser Support

  • Chrome: 61.
  • Edge: 79.
  • Firefox: 36.
  • Safari: 15.4.

Source

scroll-behavior 可让您选择启用由浏览器控制的元素滚动。这样,您就可以指定如何处理网页内导航(例如 .scrollTo() 或链接)。

prefers-reduced-motion 搭配使用时,此属性尤其有用,可用于根据用户偏好设置指定滚动行为。

@media (prefers-reduced-motion: no-preference) {
  .scroll-view {
    scroll-behavior: auto;
  }
}

overscroll-behavior

Browser Support

  • Chrome: 63.
  • Edge: 18.
  • Firefox: 59.
  • Safari: 16.

Source

如果您曾遇到过这种情况:到达模态叠加层的末尾后,继续滚动,结果叠加层后面的页面也随之移动,这就是滚动链或冒泡到父级滚动容器。借助 overscroll-behavior 属性,您可以防止溢出滚动泄漏到父容器中(称为滚动链)。

滚动贴靠

滚动通常很顺畅,可让您将内容放置在滚动视口内的任意位置。对于某些设计(例如图片库或模拟页面或幻灯片的内容),您可能希望内容贴靠到滚动视口。

设置滚动容器

如需启用滚动吸附,请将 scroll-snap-type 添加到滚动容器。您首先需要定义滚动吸附将发生在哪个轴上。可以是逻辑属性(blockinline)、物理属性(xy),也可以是 both

您还可以定义滚动吸附的严格程度。默认严格程度为 proximity,这意味着滚动容器会尽可能尝试贴靠。您还可以将严格程度设置为 mandatory,以确保滚动容器始终会贴靠。

.scroll-container {
    scroll-snap-type: block mandatory;
}

滚动吸附功能可将元素与滚动容器的完整边界对齐,但如果滚动容器的一部分不可见,会发生什么情况?例如,您可能有一个固定标题覆盖了部分滚动容器。为了帮助将贴靠元素与滚动容器的可见部分对齐,您可以设置 scroll-padding

控制可贴靠的元素

如需使元素可贴靠,请将 scroll-snap-align 属性设置为 startendcenter。如果滚动贴靠方向为 both,您可以设置两个值。此属性用于设置元素的边缘是否与滚动容器的边缘对齐,或者是否居中。

您可以使用 scroll-margin 调整贴靠元素边缘周围的间距:

scroll-margin 还用于在滚动到某个元素时设置内边距:

如需使滚动更具粘性,您可以向滚动容器中的某个项添加 scroll-snap-stop: always。但不会阻止您在一次滚动中滚动浏览多个商品。如果您以惯性滚动的方式结束滚动动作,滚动将会在下一个贴靠位置结束,而不是继续滚动。

检验您的掌握情况

文字溢出和元素溢出是否相同?

true
与元素溢出相比,文本溢出比较特殊。
false
文本溢出通常是指内联溢出,而元素溢出是指块溢出。

overflow 属性接受 2 个关键字,第一个关键字用于哪个轴?

横向
🎉
类别
在传递两个简写值时,第一个值几乎总是水平方向的值。

滚动条在显示和内联时会占用盒子模型中的哪个空间?

内容框
再试一次!
填充框
overlay 模式下的滚动条会与内边距重叠,而 inline 模式下的滚动条会添加到内边距中。
border-box
再试一次!
边距框
再试一次!

如需捕获嵌套隐式滚动器中滚动产生的额外动量,您会使用哪个属性?

scroll-behavior
再试一次!
scroll-hint
再试一次!
overscroll-behavior
将此属性设置为 contain 将会捕获滚动。
scroll-padding
再试一次!
overscroll-effect
再试一次!

哪个值声明滚动容器必须尽可能在贴靠元素处停止?

required
错误。
mandatory
正确!
0px
错误。
proximity
错误。

scrollbar-width 的有效值有哪些?

5px
错误。
thin
正确!
medium
错误。
none
正确!

资源

Smashing Magazine 上的“CSS 中的溢出和数据丢失”