CSS 真棒

Avatar of Brandon Smith
Brandon Smith 发布

DigitalOcean 为您旅程的每个阶段提供云产品。立即开始使用 200 美元的免费额度!

我最近买了一个马克杯,准备在工作时使用。作为一个专业的 Web 开发人员,我决定用它来彰显我办公室“反讽之王”的地位。当然,这个笑话并不独特,我在 T 恤、会议演示文稿等各种地方都见过它。

在座的各位中,大多数人可能都至少遇到过一次这个图片。这是一个我们都能感同身受的笑话,对吧?你尝试用 CSS 做一些简单的事情,但即使是基本属性之间相互作用的那些神秘方式,也会不可避免地搞砸它。

如果这个笑话体现了开发者对 CSS 的集体挫败感,那么冒着破坏乐趣的风险,我认为剖析其核心问题会很有趣,把它作为一个案例研究,来解释为什么人们会对 CSS 感到沮丧。

问题

查看 CodePen 上 Brandon (@brundolf) 编写的笔 CSS 真棒

要出现此问题,必须满足三个条件

  • 内容无法缩小以适应容器
  • 容器无法扩展以适应内容
  • 容器无法优雅地处理溢出

在现实场景中,第二个条件很可能是需要修复的问题,但我们将探讨所有三个条件。

修复内容大小

这对框的内容来说有点不公平,因为单词“AWESOME”在给定的字体大小和容器宽度下无法在一行内显示。默认情况下,文本在空格处换行,不会拆分单词。但让我们假设一下,我们绝对无法更改容器的大小。例如,文本可能是某个网站上放大的标题,而该网站正在非常小的手机上查看。

拆分单词

要使连续的单词换行,我们必须使用 CSS 属性 word-break。将其设置为 break-all 将指示浏览器在必要时拆分单词,以便将文本内容换行到其容器内。

查看 CodePen 上 Brandon (@brundolf) 编写的笔 CSS 真棒:word-break

其他内容

在这种情况下,使内容更具响应性的唯一方法是启用断字。但是,还有其他类型的可能溢出的内容。如果 word-wrap 设置为 nowrap,则文本甚至不会在单词之间换行。或者,内容可能是块级元素,其 widthmin-width 设置为大于容器的宽度。

修复容器大小

容器元素可能被强制不增长的方式有很多种。例如:widthmax-widthflex。但它们都有一个共同点,那就是宽度是由内容以外的其他因素决定的。这本身并不坏,尤其是在没有固定高度的情况下,在这种情况下,内容通常会向下扩展。但是,如果您遇到此情况的变体,值得考虑您是否真的需要控制宽度,或者是否可以将其留给页面来确定。

设置 width 的替代方案

通常情况下,如果您设置了元素的 width,并且以像素为单位设置,那么您实际上是想设置 min-widthmax-width。问问自己您真正关心的是什么。当该元素缺少内容时,它是否完全消失了,因为它缩小到宽度为 0?设置 min-width,以便它具有尺寸,但仍然有空间增长。它是否变得太宽,以至于整段文字都放在一行上,难以阅读?设置 max-width,以便它不会超过某个限制,也不会在小型设备上超出屏幕边缘。CSS 就像一个助手:您想要引导它,而不是指示它的每一个动作。

由 Flexbox 引起的溢出

如果您的某个 Flex 项目具有溢出的内容,事情就会变得稍微复杂一些。您可以做的第一件事是检查您是否指定了它的宽度,如上一节所述。如果您没有,那么可能发生的情况是该元素正在“Flex 缩小”。Flex 项目首先按照正常规则进行大小调整;width、内容等。结果大小称为它们的 flex-basis(也可以使用相同名称的属性显式设置)。在为每个项目建立 Flex 基线后,将应用 flex-growflex-shrink(或 flex,它一次指定两者)。项目以加权方式增长和缩小,基于这两个值和容器的大小。

设置 flex-shrink: 0 将指示浏览器此项目永远不应该小于其 Flex 基线。如果 Flex 基线由内容确定(默认值),则这应该可以解决您的问题。但是要小心,您可能会在元素的父级中再次遇到同样的问题。如果此 Flex 项目拒绝缩小,即使 Flex 容器小于它,它也会溢出,您又回到了原点。

处理溢出

有时根本无法避免。也许容器宽度受屏幕大小本身的限制。也许内容是数据表,其中行无法换行,列也无法进一步折叠。我们仍然可以比仅仅让它随意溢出更优雅地处理溢出。

overflow: hidden;

最简单的解决方案是隐藏溢出的内容。设置 overflow: hidden; 将简单地截断内容到达容器元素边框的位置。如果内容更具美学性质并且不包含关键信息,这可能是可以接受的。

查看 CodePen 上 Brandon (@brundolf) 编写的笔 CSS 真棒:overflow:hidden

如果内容是文本,我们可以通过添加 text-overflow: ellipsis; 使其在视觉上更具吸引力,这会自动在被截断的文本中添加一个漂亮的“...” 。值得注意的是,您将看到更少的实际内容以腾出空间用于省略号。还要注意,这需要设置 overflow: hidden;

查看 CodePen 上 Brandon (@brundolf) 编写的笔 CSS 真棒:省略号

overflow: auto;

通常,首选的解决方法是设置overflow-x: auto;。这会让浏览器在内容溢出时添加滚动条,允许用户向该方向滚动容器。

查看CodePen上的Brandon (@brundolf) 编写的示例 CSS真棒:overflow:auto

这是一个非常优雅的备选方案,因为它意味着无论如何,用户都能够访问所有内容。此外,滚动条只有在需要时才会出现,这意味着即使您不希望它发挥作用,在关键位置添加此属性也不是一个坏主意。

为什么这个难题会如此普遍地引起使用过 CSS 的人的共鸣?

CSS 很难,因为它的一些属性会相互影响,常常以意想不到的方式。因为当你设置其中一个属性时,你实际上并非只设置了那一件事。那一件事会与其他十几个因素结合、相互作用并发生冲突,包括你从未真正设置过的默认因素。

缓解此问题的一个经验法则是不要比必要时更明确。网页默认情况下是响应式的。编写良好的 CSS 意味着利用这一事实,而不是覆盖它。如果可能,使用百分比或视口单位代替媒体查询。在可以的情况下,使用min-width代替width。从规则的角度,从你真正想表达的意思的角度去思考,而不是只是添加属性直到事情看起来正确。尝试了解浏览器如何解决布局和大小调整,并在其基础上谨慎地进行更改和添加。与 CSS 合作,而不是对抗它。

另一个经验法则是让宽度或高度由内容决定。在本例中,这还不够,但在大多数情况下,它就足够了。给事物提供扩展的途径。当你设置元素大小规则时,特别是如果这些元素将包含文本内容,请仔细考虑极端情况。“如果此内容缩减为单个字符会怎样?如果此内容扩展为三个段落会怎样?它可能看起来不太好,但我的布局会完全破坏吗?”

CSS 很奇怪。它与任何其他代码都不一样,这使得很多程序员感到不舒服。但如果使用得当,它实际上可以非常棒。