CSS gap
属性并非新鲜事物,但去年它获得了一项重要的新功能:现在它不仅适用于 CSS Grid,也适用于 Flexbox。鉴于此,并且我认为该属性比看起来更复杂,因此我想回顾并准确解释其工作原理。
让我们仔细研究 gap
及其相关属性,并了解它们如何以及在哪里工作。
首先,让我们回顾所有与 gap
相关的 CSS 属性。共有六个:
grid-row-gap
grid-column-gap
grid-gap
row-gap
column-gap
gap
从这个列表中,我们可以忽略前三个属性。grid-*
属性是在起草 CSS Grid 规范的早期添加的,后来在 gap
变得更通用时被弃用。浏览器仍然支持这些被弃用的 grid-*
属性(截至撰写本文时),并且仅仅将它们视为不存在 grid-
前缀。因此,grid-gap
与 gap
相同,grid-column-gap
与 column-gap
相同,grid-row-gap
与 row-gap
相同。
至于其他三个属性,考虑到 gap
是一个简写,允许您指定其他两个属性,我们实际上只需要知道 row-gap
和 column-gap
的作用。
我们对这些属性的理解取决于我们使用的 CSS 布局类型。让我们首先看看这些选项。
如果您像我一样,您已经在网格布局中使用了 gap
,但现在它也可以用于 Flexbox 以及多列布局。让我们回顾每种情况。
所有浏览器都支持网格布局中的 gap
,并且在此上下文中它们非常容易理解。
row-gap
在行轨道之间引入空间column-gap
在列轨道之间引入空间让我们创建一个具有三列和两行的网格:
<code>.container { display: grid; grid-template-columns: 200px 100px 300px; grid-template-rows: 100px 100px; }</code>
这将给我们以下网格:
上图中的线称为网格线,它们分隔网格的轨道(行和列)。这些线在网格中并不真正存在——它们是不可见的,没有厚度,并且通常是当我们启用网格检查器(在 Safari、Firefox、Edge 或 Chrome 中)时 DevTools 显示的内容。
但是,如果我们开始向网格添加间隙,它将像这些线开始获得厚度一样工作。
让我们添加一个 20px 的间隙:
<code>.container { display: grid; grid-template-columns: 200px 100px 300px; grid-template-rows: 100px 100px; gap: 20px; }</code>
现在,我们轨道之间的线有 20px 厚,因此将网格项目推得更远。
值得注意的是,轨道仍然具有相同的大小(由 grid-template-*
属性定义);因此,网格比没有间隙时更宽更大。
在网格中,row-gap
始终应用于行轨道之间。因此,如果我们在上面的示例中用 row-gap
替换 gap
,我们将得到:
而 column-gap
始终应用于列轨道之间,因此用 column-gap
替换 gap
会产生以下结果:
网格很简单,因为默认情况下,列是垂直的,行是水平的,就像在表格中一样。因此,很容易记住 column-gap
和 row-gap
应用的位置。
现在,当使用 writing-mode
时,事情会变得稍微复杂一些。网络上的默认书写模式是从左到右的水平模式,但也有垂直书写模式,当发生这种情况时,列变为水平,行变为垂直。始终注意 writing-mode
,因为它可能使其不如通常那样直观。
这是一个很好的过渡到下一节,因为列和行在 Flexbox 中获得了新的含义。
让我们谈谈 Flexbox 布局中的间隙,这里的事情变得稍微复杂一些。我们将使用以下示例:
<code>.container { display: flex; }</code>
默认情况下,这将给我们一个行 Flex 容器,这意味着容器内的项目从左到右堆叠在同一水平线上。
在这种情况下,column-gap
应用于项目之间,而 row-gap
没有任何作用。这是因为只有一行(或行)。但现在让我们在项目之间添加一些间隙:
<code>.container { display: flex; column-gap: 10px; }</code>
现在让我们将容器的 flex-direction
切换为列,它将项目从上到下垂直堆叠,使用以下代码:
<code>.container { display: flex; flex-direction: column; column-gap: 10px; }</code>
接下来会发生什么:
间隙消失了。即使 column-gap
在容器处于行方向时确实在项目之间添加了空间,但在列方向中它不再起作用。
我们需要使用 row-gap
来找回它。或者,我们可以使用具有一个值的 gap
简写,它将在两个方向上应用相同的间隙,因此在两种情况下都有效。
<code>.container { display: flex; flex-direction: column; gap: 10px; }</code>
因此,总而言之,column-gap
始终垂直工作(假设默认的 writing-mode
),row-gap
始终水平工作。这并不取决于 Flex 容器的方向。
但是现在看看涉及换行的示例:
<code>.container { display: flex; flex-wrap: wrap; column-gap: 40px; row-gap: 10px; justify-content: center; }</code>
在这里,如果空间不足以在一行中容纳所有内容,我们允许项目使用 flex-wrap: wrap
在多行上换行。
在这种情况下,column-gap
仍然垂直应用于项目之间,row-gap
水平应用于两条 Flex 行之间。
这与网格之间有一个有趣的区别。列间隙不一定跨 Flex 行对齐。这是因为 justify-content: center
将项目在其 Flex 行内居中。这样,我们可以看到每条 Flex 行都是一个单独的布局,间隙独立于其他行应用。
多列 是一种布局类型,它使内容在多列之间自动流动变得非常容易,就像您在传统的报纸文章中所期望的那样。我们设置列数并为每列设置大小。
多列布局中的间隙与网格或 Flexbox 的工作方式不太相同。有三个值得注意的区别:
row-gap
没有效果,column-gap
具有非 0 的默认值,让我们逐一分解。首先,row-gap
没有效果。在多列布局中,没有行需要分隔。这意味着只有 column-gap
是相关的(以及 gap
简写)。
其次,与网格和 Flexbox 不同,多列布局中 column-gap
的默认值为 1em(而不是 0)。因此,即使根本没有指定间隙,内容列仍然是视觉上分开的。当然可以覆盖默认间隙,但这是一个很好的默认值。
以下是示例所基于的代码:
<code>.container { column-count: 3; padding: 1em; }</code>
最后,我们可以设置多列布局中列之间空隙的样式。我们使用 column-rule
属性,它的作用类似于 border
:
<code>.container { column-count: 3; column-gap: 12px; column-rule: 4px solid red; padding: 12px; }</code>
gap
在各方面都得到了很好的支持。caniuse 上有更多信息,但总而言之:
gap
在任何地方都受支持。caniuse 的全球支持率为 87.31%。因此,总的来说,gap
属性得到了很好的支持,并且在大多数情况下,不需要变通方法。
设置 Flexbox 和 CSS Grid 中间隙的样式将非常有用。令人遗憾的是,它今天在任何地方都不受支持。但好消息是它可能在不久的将来实现。这已经在 CSS 工作组中讨论过,并且正在 Firefox 中开发中。一旦我们在 Firefox 中有了有效的实现以及规范提案,它可能会推动其他浏览器中的实现。
与此同时,有一些解决方法。
一种方法是为网格容器赋予背景颜色,然后为项目赋予不同的颜色,最后留出间隙以使容器颜色显示出来。
虽然这有效,但这意味着我们无法使用间隙来在项目之间引入空间。这里的间隙充当边框宽度。因此,为了更清晰地视觉上分隔项目,我们需要在项目上使用填充或边距,这并不理想……正如我们将在下一节中看到的那样。
是的,在大多数情况下,我们也可以使用 margin
(和/或 padding
)来在布局元素之间添加视觉空间。但是 gap
具有多个优点。
首先,间隙是在容器级别定义的。这意味着我们为整个布局定义它们一次,并且它们在布局中始终一致地应用。使用边距需要在每个项目上进行声明。当项目性质不同或来自不同的可重用组件时,这可能会变得很复杂。
最重要的是,gap
只需一行代码即可默认执行正确操作。例如,如果我们试图在 Flex 项目之间引入一些空间,而不是围绕它们,则边距需要特殊情况才能删除第一个项目之前的额外边距和最后一个项目之后的额外边距。使用间隙,我们不需要这样做。
使用 margin: 0 20px
在每个 Flex 项目上,我们将得到:
但是,在容器上使用 gap: 40px
,我们将得到:
同样在网格布局中,在容器级别定义间隙比必须在每个项目上定义边距并考虑应用于网格边缘的边距要简单得多,并且效果更好。
在每个网格项目上使用 margin: 20px
:
而改为在网格容器上使用 gap: 40px
:
根据到目前为止所说的所有内容,margin
和 gap
不必是互斥的。事实上,有很多方法可以将布局的项目进一步分开,并且它们都可以很好地协同工作。
gap
属性只是在布局容器中框之间创建的空白空间的一部分。margin
、padding
和对齐方式都可能会增加 gap
已定义的空白空间。
让我们考虑一个示例,我们使用给定的宽度、一些间隙、一些内容分布(使用 justify-content
)以及一些边距和填充来构建一个简单的 Flex 布局:
<code>.container { display: flex; gap: 40px; width: 900px; justify-content: space-around; } .item { padding: 20px; margin: 0 20px; }</code>
让我们假设这段代码产生以下结果:
现在,让我们准确地看看项目之间的空白空间是如何创建的:
如我们所见,两个连续的 Flex 项目之间有四种不同类型的空白空间:
space-around
值在 Flex 行内均匀分布项目。让我们以一个非常贴近我内心的话题结束:DevTools 对调试间隙的支持。总会有出错的情况,知道 DevTools 可以为我们提供支持非常令人欣慰,但我们确实需要知道哪些工具可以帮助我们。
对于 gap
,我可以想到两个可能非常有用的特定功能。
除非我们拼写错误 gap
或提供了无效的值,否则该属性将始终应用于页面。例如,这是正确的:
<code>.some-class { display: block; gap: 3em; }</code>
它不会做任何事情,但它是有效的 CSS,浏览器并不介意 gap
不适用于块布局。但是,Firefox 有一个名为“Inactive CSS”的功能就是这样做的:它关心应用于有意义的事物的有效 CSS。在这种情况下,Firefox DevTools 在检查器中显示警告。
Chrome 和 Microsoft Edge 还具有一个非常有用的调试间隙的功能。它是通过微软和谷歌之间的合作添加的,其目标是在 Chromium(支持这两个浏览器以及其他浏览器的开源项目)中构建布局调试工具。在这些浏览器中,您可以将鼠标悬停在“样式”面板中的各个属性上,并查看它们对页面的影响。
就是这样。我希望本文有助于理解 CSS 中间隙工作方式的一些细节。
以上是注意'差距”的详细内容。更多信息请关注PHP中文网其他相关文章!