我有一个基于flexbox的布局,其中两个面板(顶部和底部)分别占据视口的1/3和2/3。 (实际上有更多的面板,但我把它简化为最小的例子。)
顶部面板也是一个弹性容器,因为我希望它的孩子从上到下流动,并在有空间时垂直居中。当顶部面板中的东西多于其中的东西时,我希望它可以滚动,因此overflow: auto
。
问题:top
的内容缩小到其大小,即使使用flex-shrink: 0
,滚动条也不会弹出。
观察以下演示中content
是如何缩小的,即使它具有明确指定的高度:
html, body {
height: 100%;
width: 100%;
margin: 0;
padding: 0;
overflow: hidden;
}
.main {
display: flex;
height: 100%;
flex-direction: column;
}
.top {
display: flex;
flex-direction: column;
flex-basis: 33%;
border-bottom: 1px solid #ccc;
overflow: auto;
justify-content: center;
padding: 20px;
}
.bottom {
overflow: auto;
flex-basis: 67%;
}
.content {
height: 500px;
background-color: #eee;
}
<div class="main">
<div class="top">
<div class="content">Content</div>
</div>
<div class="bottom"></div>
</div>
问题:
如何在保留布局要求的同时解决此问题?禁用顶部面板的display: flex
可在演示中获得所需的效果。我可以以无flexbox方式定位top
的内容,但我失去了flex布局和自动垂直居中的好处。
为什么会这样?欢迎参考CSS规范。
答案 0 :(得分:1)
您写道:
问题:
top
的内容缩小到其大小,即使使用flex-shrink: 0
,滚动条也不会弹出。
实际上,解决方案是flex-shrink: 0
。所以问题就变成了,你在哪里应用它?
如果您将其应用于top
- 主容器中的flex-basis: 33%
(即height: 33%
,在这种情况下)的灵活项目,则无法使用 - 因为top
是一个百分比。因此,当百分比长度相对于父容器时,它将自然收缩/扩展。
您需要将flex-shrink: 0
应用于.content
- 嵌套容器中具有固定高度(height: 500px
/ flex-basis: 500px
)的弹性项目。
所以这会奏效:
.content {
height: 500px;
flex-shrink: 0;
}
或者这个:
.content {
flex-basis: 500px;
flex-shrink: 0;
}
或者,更好的是,这个:
.content {
flex: 0 0 500px; /* don't grow, don't shrink, stay fixed at 500px */
}
来自规范:
7.2. Components of Flexibility
鼓励作者使用
flex
简写来控制灵活性 而不是直接用它的速记属性,作为速记 正确地重置任何未指定的组件以容纳common uses。
body {
margin: 0;
}
.main {
display: flex;
flex-direction: column;
height: 100vh;
}
.top {
display: flex;
flex-direction: column;
flex-basis: 33%;
border-bottom: 1px solid #ccc;
overflow: auto;
justify-content: center;
padding: 20px;
}
.bottom {
overflow: auto;
flex-basis: 67%;
}
.content {
flex: 0 0 500px;
background-color: #eee;
}
<div class="main">
<div class="top">
<div class="content">Content</div>
</div>
<div class="bottom"></div>
</div>
然后你有第二个问题,即top
元素的上半部分被切断并且无法通过滚动访问。这是由容器上的justify-content: center
引起的。
这是一个已知问题。它通过使用flex auto
边距来解决。
所以不要这样:
.top {
display: flex;
flex-direction: column;
flex-basis: 33%;
border-bottom: 1px solid #ccc;
overflow: auto;
/* justify-content: center; <--- REMOVE */
padding: 20px;
}
这样做:
.content {
flex: 0 0 500px;
margin: auto 0; /* top & bottom auto margins */
background-color: #eee;
}
body {
margin: 0;
}
.main {
display: flex;
flex-direction: column;
height: 100vh;
}
.top {
display: flex;
flex-direction: column;
flex-basis: 33%;
border-bottom: 1px solid #ccc;
overflow: auto;
/* justify-content: center; USE AUTO MARGINS ON FLEX ITEM INSTEAD */
padding: 20px;
}
.bottom {
overflow: auto;
flex-basis: 67%;
}
.content {
flex: 0 0 500px;
margin: auto 0;
background-color: #eee;
}
<div class="main">
<div class="top">
<div class="content">Content</div>
</div>
<div class="bottom"></div>
</div>
以下是完整的解释:
答案 1 :(得分:0)
当有足够的.content
元素缩小到非常小的高度(在这种情况下为一行高度)时,会出现滚动条。
这并不是真的如何使用flex。 height
并未受到严格尊重。如果您仍想使用height
,则可以根据所需的最低身高将min-height
设置为.content
来解决此问题。
或者您可以在flex
上设置.content
(并摆脱height
):
css
flex: 100px 1 0;
这将设置最小高度(flex-basis)为100px,flex-grow为1以便占用所有可用空间,并将flex-shrink设置为0,以便元素始终至少为100px高。