原文:WhenAndHowToUseCSSMulti-ColumnLayout作者:RachelAndrew译者:博轩当我们专注于CSSGrid布局和CSSFlexbox布局时,还有另一种经常被忽视的布局方法。在本文中,我将介绍多列布局——通常称为multicol或“CSS列”。通过本文,您了解了使用色谱柱的最佳实践,以及使用色谱柱的一些注意事项。什么是多元醇?multicol的基本思想是你可以把一大块内容分成多个栏目,就像报纸一样。您可以使用两个属性之一来完成此操作。您可以使用cloumn-count属性来指定内容的列数。您还可以使用column-width属性指定理想的列宽,让浏览器确定合适的列数。无论您的内容包含什么元素,当您将其转换为多列布局时,一切都将保持正常的内容流,但会以列显示。这使得multicol布局不同于当今浏览器中常见的其他布局。比如Flexbox和Grid,获取容器元素的子元素,让这些子元素参与flex和grid的布局。使用multicol,在每一列内,您还可以获得正常的内容流。在下面的示例中,我们使用column-width最小列宽为14em。Multicol会分配尽可能多的14em宽的列,然后让每个列共享剩余的空间。每列的宽度至少为14em,除非容器的宽度小于14em,否则只会显示一列。Multicol也是CSS中首次出现的行为。它可以创建列,它也默认符合响应式规则。你不需要添加CSS查询条件(MediaQueries)和修改每个断点的列数,而是制定一个最优的宽度,让浏览器自己处理。示例链接//核心代码摘录.container{max-width:800px;保证金:0自动;column-width:14em;}columnstyle当你使用columns创建布局时,cloumns框中的内容会无法定位。您不能使用JavaScript进行定位,也不能为个别列指定唯一的样式,例如背景颜色、边距、填充等。所有列框将保持相同的大小。您唯一可以做的就是使用column-rule属性在列之间添加规则,它的作用类似于边框。您还可以使用column-gap属性控制列之间的间距,该属性默认为1em,但您可以将其更改为任何有效的长度单位。示例链接//核心代码.container{max-width:800px;保证金:0自动;列宽:14em;列间距:2em;column-rule:1pxsolid#ccc;}这是multicol的基本功能。您可以将一大块内容拆分成列。内容将依次填充每一列,以内联方向创建列。您可以控制列与列之间的间隙和规则,只需使用与边框相同的值即可。到目前为止,以上所有内容都在浏览器中得到了很好的支持,并且已经存在了很长时间,这使得该规范在向后兼容性方面非常安全。关于使用列,您可能还需要考虑一些其他事项,以及在Web上使用列时需要注意的一些潜在问题。跨越列有时,您可能希望将某些内容分解为列,同时用一个元素跨越这些列。使用multicol的columns-span属性可以实现这一点。在下面的示例中,我使用
元素来跨列。注意,这样做的时候,内容被分成了两个区域,一个在上面,另一个用column-span元素集。内容不会跳过设置了column-span的元素。column-span属性目前在Firefox中实现并且向后兼容。示例链接//核心代码blockquote{font:2em'BerkshireSwash',cursive;保证金:0;列跨度:全部;text-align:center;}.container{最大宽度:800px;保证金:0自动;列宽:14em;列间距:2em;column-rule:1pxsolid#ccc;}你应该知道,在目前的规范中,column-span的值只有all或none。如果要实现报纸的样式,可以使用多栏布局结合其他布局。在下面的示例中,我们实现了一个带有两个列轨道的网格容器(Grid)。左侧轨道的宽度为2fr,右侧轨道的宽度为1fr。我们把左边的轨道变成了一个有两列的multicol容器。它还包含一个障碍元素。在右侧,我们将内容放入第二个Grid列轨道中。通过尝试各种布局方法,我们可以找出适合手头工作的确切方法——不要害怕混合搭配!示例链接//核心代码.container{max-width:800px;保证金:0自动;显示:网格;网格间隙:1em;网格模板列:2fr1fr;align-items:start;}.containerarticle{column-count:2;列间距:2em;column-rule:1pxsolid#ccc;}.containeraside{border-left:1pxsolid#ccc;padding:01em;}控制内容截断如果您的内容包含标题,您可能希望避免标题出现在列末尾而内容出现在下一列中。再比如,如果你的内容中有一些图片带有文字说明,那么理想情况下,图片和文字说明会作为一个整体展示,而不是分栏显示。当您将内容拆分成列时,这种行为称为CSS碎片。将内容分成两页显示,就好像打印机选择了两栏打印模式一样。因此,相对于Web上的其他布局方式,multicol是最接近PagedMedia的布局方式。因此,我们可以使用属于CSS2.1的属性page-break来实现这一点。page-break-beforepage-break-afterpage-break-inside最近,CSS片段模块规范定义了如何为各种片段模块上下文设计片段属性,包括PagedMedia、multicol和停滞区域样式(RegionStyling);area还将支持显示破碎(碎片化)的连续内容。通过使用这些通用属性,它们可以应用于任何未来的CSS片段模块上下文,就像Flexbox的对齐属性被移动到BoxAlignment规范中一样,以便它们可以用于Grid和Block布局。break-beforebreak-afterbreak-inside在下面的示例中,我在元素上使用了break-insideavoid属性,以防止图像的标题与图像分离。在支持这个属性的浏览器中,我们应该看到连接的效果,即使它让列中的内容看起来不平衡。示例链接//核心代码图{margin:0;break-inside:avoid;}.container{max-width:800px;保证金:0自动;column-width:14em;}不幸的是,在multicol中的支持非常不完整。即使在支持的地方,它们也应该被认为是一个建议,因为在实践中,有很多要求控制内容是否应该分开,但实际上浏览器并没有真正让这些东西分开。在上面的例子中,我们定义了显示优先级,但是在使用的时候要小心,只在最需要的地方使用。Columns布局的一些问题当我们浏览网页时,我们没有看到multicol被广泛使用。原因是读者通常从上到下滚动。对于使用英文或其他竖排文字的人来说,横排并不是很好的阅读体验。如果您固定容器的高度,例如使用viewportunitvh,当内容过多时会溢出inline,同时会得到一个水平滚动条。示例链接这些情况都不是理想的。因此,在使用多栏布局时,我们需要仔细考虑每一栏的内容。Columnsblockoverflow在Level2规范中,我们考虑如何使用一种方法,列的内容不会溢出,生成水平滚动条,而是在block的方向生成新的列。这意味着您可以拥有一个具有高度的multicol容器,一旦内容超过该容器的宽度,就会在下方创建一组新的列。这看起来有点像我们上面的跨越示例,但不是让设置了column-span的元素导致新的列框开始,容器宽度受块大小限制,从而解决了溢出问题。此功能将使multicol对网络更有用。虽然我们现在还有很长的路要走,但您可以关注CSS工作组repo中的问题。如果您有此功能的其他用例,请发布它们,这在设计新功能时非常有帮助。我们今天如何使用Multicol?根据当前规范,不建议在不考虑滚动问题的情况下将所有内容拆分为列。然而,在某些情况下,multicol是web的理想选择。有足够的示例供您在查看设计模式时参考。折叠小型UI或文本元素multicol可用于需要占用较少空间的项目列表的任何地方。例如,一个简单的复选框列表或名称列表。通常在这些情况下,访问者不会阅读一栏然后返回到下一栏的顶部,而是扫描内容以选中要单击的复选框或要选择的项目。即使您确实创建了滚动体验,此问题仍然存在。您可以在DonarMuseum网站上看到SanderdeJong以这种方式使用multicol的示例。识别少量内容有时,当我们设计网站时,我们知道某些区域的内容相对较小,无需滚动即可适合大多数屏幕。我在Notist演示页面中使用multicol进行介绍性演讲。AndyClarke为Equfund网站设计了一个可爱的例子。为避免非常小的屏幕导致页面滚动,就像宽度一样,您可以使用媒体查询来检查高度。对于超过最小高度的内容,可以在断点处设置min-height,避免小设备用户体验不佳。瀑布式(砌体式)内容显示另一个多列布局工作得很好的地方是如果你想创建一个瀑布式内容显示。Multicol是目前创建可变高度布局的唯一方法。网格布局要么留下间隙,要么拉伸项目以形成严格的二维网格。VeerlePieters在她的灵感页面上有一个以这种方式使用multicol的很好的例子。Grid和Flexbox的替代方案这些列属性也可以用作Grid和Flex布局的替代方案。如果在容器上指定了这些属性之一,使用display:flex或display:grid将删除任何列行为,将该容器转换为Flex或Grid布局。例如,如果您有一个使用Grid布局的卡片布局,并且该布局在列而不是页面中运行时是可读的,您可以使用multicol作为简单的后备。不支持Grid的浏览器将获得multicol显示,支持Grid的浏览器将获得GridLayout。不要忘记多色!我经常回答Grid和Flexbox的问题,答案是不要使用Grid或Flexbox,而是尝试使用Multicol。您可能不会在每个站点上都使用它,但是当您遇到本文提到的场景时它会非常有用。MDN上有关于multicol和CSS片段模块的有用资源。如果你的项目中还有multicol的其他使用场景,欢迎留言分享!本文已联系原作者及授权翻译,转载请保留原文链接