响应式 flexbox 和重新排序子子项
Posted
技术标签:
【中文标题】响应式 flexbox 和重新排序子子项【英文标题】:Responsive flexbox and reordering subchildren 【发布时间】:2020-05-16 18:14:21 【问题描述】:我需要一些关于响应式 html 的帮助。
我有一个 flexbox 布局,有两列。每列包含两个不同高度的 div。
在移动设备上,我将 flex-direction 设置为列,因此它分成一列:
但正如您可能已经猜到的那样,我希望订单是 ABCD。我意识到我目前的设置可能无法做到这一点,因为 AFAIK 你不能订购子孩子。但是我有什么选择来获得想要的结果?
我可以用 javascript 重新排列东西,但如果可能的话,我更喜欢纯 CSS 方法。
这可以实现吗?我需要 CSS 网格来执行此操作吗?
我添加了一个 sn-p 来说明这个问题。也在codepen上:https://codepen.io/Mudloop/pen/PowrKPV
(为简单起见,它没有媒体查询,只是相同的 html 两次不同的类)。
* box-sizing: border-box;
body background-color: #444; color: white; font-family: sans-serif; max-width:650px;
.normal
display: flex;
flex-direction: row;
flex-wrap: wrap;
align-items: flex-start;
margin: 20px;
.normal > div
color: white;
width: calc(50%);
.normal > div > div
background-color: #333;
padding: 10px;
margin: 10px;
.mobile
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-items: flex-start;
margin:20px;
.mobile > div
color: white;
width: 100%;
.mobile > div > div
background-color: #333;
padding: 10px;
margin: 10px;
<body>
Desktop
<div class="normal">
<div>
<div>A<br></div>
<div>C<br><br><br><br><br></div>
</div>
<div>
<div>B<br><br></div>
<div>D<br><br><br></div>
</div>
</div>
Mobile
<div class="mobile">
<div>
<div>A<br></div>
<div>C<br><br><br><br><br></div>
</div>
<div>
<div>B<br><br></div>
<div>D<br><br><br></div>
</div>
</div>
</body>
【问题讨论】:
grid 肯定会用 cssorder
property 解决它。
谢谢@RicoKahler。我希望有另一种解决方案,因为 CSS 网格让我害怕 :) 但如果没有,我会尝试找出它们。
看起来 CSS 网格也不能解决问题,因为网格单元格不能具有可变(任意)高度。
【参考方案1】:
您可以在桌面上使用multi-column 布局。
并在移动设备上使用媒体查询切换到flex
(允许重新order
元素)。
在Full page
模式下运行下面的例子并尝试调整窗口大小:
(我在块中添加了一些文本以使它们更真实)
*
box-sizing: border-box;
body
background-color: #444;
color: white;
font-family: sans-serif;
max-width: 1280px;
width: 100%
.normal
padding: 10px;
border: solid 1px #ccc;
margin: 20px;
columns: 2 200px;
column-fill: balance;
.normal>div
margin: 0 0 10px;
padding: 10px;
background-color: #333;
page-break-inside: avoid;
@media (max-width:480px)
.normal
display: flex;
flex-direction: column
.normal>div:nth-child(1)
order: 1
.normal>div:nth-child(2)
order: 3
.normal>div:nth-child(3)
order: 2
.normal>div:nth-child(4)
order: 4
Desktop
<div class="normal">
<div>A<br>Lorem ipsum, or lipsum as it is sometimes known, is dummy text used in laying out print, graphic or web designs.</div>
<div>C<br>The purpose of lorem ipsum is to create a natural looking block of text (sentence, paragraph, page, etc.) that doesn't distract from the layout. A practice not without controversy, laying out pages with meaningless filler text can be very useful
when the focus is meant to be on design, not content.</div>
<div>B<br>It usually begins with:<br>“Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.”</div>
<div>D<br> The passage is attributed to an unknown typesetter in the 15th century who is thought to have scrambled parts of Cicero's De Finibus Bonorum et Malorum for use in a type specimen book.</div>
</div>
【讨论】:
这看起来是一个很好的解决方案。以前从未听说过多列布局,很高兴知道它的存在。而且它似乎得到了很好的支持。 @SvenM,很乐意为您提供帮助。 似乎如果单元格 A 变大,它会将单元格 C 推到下一列。你知道有没有办法解决这个问题? (无论内容如何,我的布局都保持一致)。 设法通过将 column-fill 设置为 auto 并添加 break-after:avoid 和 break-after:column 来解决它(我认为)。【参考方案2】:是的,您可以通过在具有display: flex
的容器内的子项上使用order
属性来实现此目的,并结合媒体查询,而无需使用网格。我不确定您的布局对 HTML 结构的约束是什么,所以我对其进行了一些更改。
我为“桌面”布局使用了最大高度来强制弹性项目用列流包装。然后,当媒体查询被触发时(您可以将其设置为您支持的任何移动设备尺寸),最大高度被删除,并且里面的项目可以根据您指定的order
属性将它们自己设置在一个列中。
您可以将其放入代码笔中,调整窗口大小,它应该可以工作。
<body>
Desktop
<div class="normal">
<div id="a">A<br></div>
<div id="c">C<br><br><br><br><br></div>
<div id="b">B<br><br></div>
<div id="d">D<br><br><br>
</div>
</div>
* box-sizing: border-box;
body background-color: #444; color: white; font-family: sans-serif;
.normal
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-items: flex-start;
margin: 20px;
max-height: 200px;
.normal > div
color: white;
width: calc(50%);
.normal > div
background-color: #333;
padding: 10px;
margin: 10px;
@media (max-width: 500px)
.normal
display: flex;
flex-direction: column;
flex-wrap: none;
align-items: center;
max-height: none;
#a
order: 1
#b
order: 2
#c
order: 3
#d
order: 4
【讨论】:
谢谢,但问题是我不知道最大高度。这些列显示用户生成的内容,所以我不能硬编码高度约束。但是,我也许可以用 javascript 计算最大高度。我更喜欢纯 CSS,但看起来我需要一些 javascript 来解决这个或另一种方式。以上是关于响应式 flexbox 和重新排序子子项的主要内容,如果未能解决你的问题,请参考以下文章