2021年更新
CSS Grid Layout Level 3包括一个砌体特征。
代码看起来像这样:
grid-template-rows: masonry
grid-template-columns: masonry
截至2021年3月,它仅在Firefox中可用(激活该标志后)。
https://drafts.csswg.org/css-grid-3/#masonry-layout
https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Grid_Layout/Masonry_Layout
最后更新;以下是原始答案
Flexbox
一个动态的砖石布局是不可能与flexbox,至少不是在一个干净和有效的方式。
Flexbox是一个一维布局系统。这意味着它可以沿着水平或垂直的线对齐项目。伸缩项仅限于其行或列。
真正的网格系统是二维的,这意味着它可以沿着水平线和垂直线对齐项目。内容项可以同时跨行和跨列,而flex项不能做到这一点。
这就是为什么flexbox构建网格的能力有限。这也是W3C开发另一种CSS3技术——网格布局(Grid Layout)的原因。
行包装
在具有flex-flow:行换行的伸缩容器中,伸缩项必须换行到新行。
这意味着一个伸缩项不能在同一行中的另一个项下面换行。
注意上面div #3是如何在div #1下面换行的,创建了一个新行。它不能包装在div #2下面。
因此,当物品不是一行中最高的时,就会留下空白,造成难看的空隙。
列包装
如果切换到flex-flow:列换行,则更容易实现类似网格的布局。然而,列方向容器马上就有四个潜在的问题:
Flex项目垂直流动,而不是水平流动(就像您在本例中需要的那样)。
容器水平展开,而不是垂直展开(就像Pinterest的布局)。
它要求容器有一个固定的高度,这样物品就知道在哪里包装。
在撰写本文时,它在所有主流浏览器中都有一个缺陷,即容器不能扩展以容纳额外的列。
因此,列方向容器在这种情况下和许多其他情况下都不是一个选项。
未定义项目尺寸的CSS网格
如果可以预先确定内容项的各种高度,网格布局将是您问题的完美解决方案。所有其他需求都在Grid的能力范围内。
必须知道网格项目的宽度和高度,以便缩小与周围项目的差距。
因此,网格,这是最好的CSS必须提供建立一个水平流动的砌体布局,在这种情况下,不足。
事实上,在CSS技术能够自动消除这些差距之前,CSS通常都没有解决方案。类似这样的事情可能需要重新循环文档,所以我不确定它是否有用或有效。
你需要一个脚本。
JavaScript解决方案倾向于使用绝对定位,它从文档流中删除内容项,以便重新排列它们,没有间隙。这里有两个例子:
Desandro Masonry
圬工是一个JavaScript网格布局库。它
通过将元素放置在基于可用的最佳位置来工作
垂直空间,有点像泥瓦匠把石头装在墙上。
来源:http://masonry.desandro.com/
如何建立一个像Pinterest一样的网站
(Pinterest)确实是一个很酷的网站,但我觉得有趣的是这些针板的布局方式……所以本教程的目的是重新创建这个响应块效果自己…
来源:https://benholland.me/javascript/2012/02/20/how-to-build-a-site-that-works-like-pinterest.html
定义了项目维度的CSS网格
对于内容项的宽度和高度已知的布局,这里有一个纯CSS水平流动的砌体布局:
grid-container {
display: grid; /* 1 */
grid-auto-rows: 50px; /* 2 */
grid-gap: 10px; /* 3 */
grid-template-columns: repeat(auto-fill, minmax(30%, 1fr)); /* 4 */
}
[short] {
grid-row: span 1; /* 5 */
background-color: green;
}
[tall] {
grid-row: span 2;
background-color: crimson;
}
[taller] {
grid-row: span 3;
background-color: blue;
}
[tallest] {
grid-row: span 4;
background-color: gray;
}
grid-item {
display: flex;
align-items: center;
justify-content: center;
font-size: 1.3em;
font-weight: bold;
color: white;
}
<grid-container>
<grid-item short>01</grid-item>
<grid-item short>02</grid-item>
<grid-item tall>03</grid-item>
<grid-item tall>04</grid-item>
<grid-item short>05</grid-item>
<grid-item taller>06</grid-item>
<grid-item short>07</grid-item>
<grid-item tallest>08</grid-item>
<grid-item tall>09</grid-item>
<grid-item short>10</grid-item>
<grid-item tallest>etc.</grid-item>
<grid-item tall></grid-item>
<grid-item taller></grid-item>
<grid-item short></grid-item>
<grid-item short></grid-item>
<grid-item short></grid-item>
<grid-item short></grid-item>
<grid-item tall></grid-item>
<grid-item short></grid-item>
<grid-item taller></grid-item>
<grid-item short></grid-item>
<grid-item tall></grid-item>
<grid-item short></grid-item>
<grid-item tall></grid-item>
<grid-item short></grid-item>
<grid-item short></grid-item>
<grid-item tallest></grid-item>
<grid-item taller></grid-item>
<grid-item short></grid-item>
<grid-item tallest></grid-item>
<grid-item tall></grid-item>
<grid-item short></grid-item>
</grid-container>
jsFiddle演示
它是如何工作的
建立一个块级网格容器。(内联网格将是另一个选择)
grid-auto-rows属性设置自动生成行的高度。在这个网格中,每一行都是50px高。
网格间隙属性是网格列间隙和网格行间隙的简称。该规则在网格项之间设置10px的间距。(它不适用于物品和容器之间的区域。)
grid-template-columns属性设置显式定义的列的宽度。
repeat符号定义了重复列(或行)的模式。
自动填充函数告诉网格在不溢出容器的情况下排列尽可能多的列(或行)。(这可以创建类似flex布局的flex-wrap: wrap的行为。)
minmax()函数的作用是:为每列(或行)设置最小和最大大小范围。在上面的代码中,每个列的宽度最小为容器的30%,最大为可用的空闲空间。
fr单位表示网格容器中空闲空间的一部分。它可以与flexbox的flex-grow属性相媲美。
通过grid-row和span,我们告诉网格项它们应该跨多少行。
浏览器对CSS网格的支持
Chrome - 2017年3月8日全面支持(版本57)
Firefox - 2017年3月6日全面支持(版本52)
Safari——2017年3月26日全面支持(10.1版)
Edge - 2017年10月16日全面支持(版本16)
IE11 -不支持当前规范;支持过时版本
这里是完整的图片:http://caniuse.com/#search=grid
酷的网格覆盖功能在Firefox
在Firefox开发工具中,当您检查网格容器时,在CSS声明中有一个很小的网格图标。点击它会在页面上显示网格的轮廓。
更多详情请访问:https://developer.mozilla.org/en-US/docs/Tools/Page_Inspector/How_to/Examine_grid_layouts