考虑以下 HTML/css 代码示例:
<div id="container">
<div id="up">Text<br />Text<br />Text<br /></div>
<div id="down">Text<br />Text<br />Text<br /></div>
</div>
#container { width: 300px; height: 300px; border:1px solid red;}
#up { background: green; }
#down { background:pink;}
我有一个带有两个孩子的容器 div
(也在这里:http://jsfiddle.net/S8g4E/)。第一个孩子有一个给定的身高。如何让第二个孩子占据容器 div
的“可用空间”而不给出特定高度?
在示例中,粉红色的 div
也应该占据空白区域。
与此问题类似:How to make div occupy remaining height?
但我不想给出绝对的位置。
根据您希望实现的浏览器支持以及 #up
是否具有定义的高度,可以通过多种方式扩展 #down
子项以填充 #container
的剩余空间。
样品
.container { 宽度:100px;高度:300px;边框:1px 纯红色;向左飘浮; } .up { 背景:绿色; } .down { 背景:粉红色; } .grid.container { 显示:网格;网格模板行:100px; } .flexbox.container { 显示:弹性;弹性方向:列; } .flexbox.container .down { flex-grow: 1; } .calc .up { 高度:100px; } .calc .down { 高度:计算(100% - 100px); } .overflow.container { 溢出:隐藏; } .overflow .down { 高度:100%; }
网格
CSS 的 grid
布局提供了另一种选择,尽管它可能不像 Flexbox 模型那样简单。但是,它只需要设置容器元素的样式:
.container { display: grid; grid-template-rows: 100px }
grid-template-rows
将第一行定义为 100 像素的固定高度,其余行将自动拉伸以填充剩余空间。
我很确定 IE11 需要 -ms-
前缀,因此请确保验证您希望支持的浏览器中的功能。
弹性盒
CSS3 的 Flexible Box Layout Module (flexbox
) 现在得到了很好的支持,并且很容易实现。因为它很灵活,它甚至可以在 #up
没有定义的高度时工作。
#container { display: flex; flex-direction: column; }
#down { flex-grow: 1; }
需要注意的是,IE10 和 IE11 对某些 flexbox 属性的支持可能有问题,而 IE9 或更低版本则根本不支持。
计算高度
另一个简单的解决方案是使用 CSS3 calc
功能单元 as Alvaro points out in his answer,但它要求第一个孩子的高度是一个已知值:
#up { height: 100px; }
#down { height: calc( 100% - 100px ); }
它得到了相当广泛的支持,唯一值得注意的例外是 <= IE8 或 Safari 5(不支持)和 IE9(部分支持)。其他一些问题包括将 calc 与 transform 或 box-shadow 结合使用,因此如果您担心,请务必在多个浏览器中进行测试。
其他选择
如果需要较旧的支持,您可以将 height:100%;
添加到 #down
将使粉红色 div 全高,但需要注意一点。它将导致容器溢出,因为 #up
将其向下推。
因此,您可以将 overflow: hidden;
添加到容器中来解决此问题。
或者,如果 #up
的高度是固定的,您可以将其绝对定位在容器内,并为 #down
添加一个 padding-top。
而且,另一种选择是使用表格显示:
#container { width: 300px; height: 300px; border: 1px solid red; display: table;}
#up { background: green; display: table-row; height: 0; }
#down { background: pink; display: table-row;}
我问这个问题已经快两年了。我刚刚提出了解决我遇到的这个问题的 css calc(),并认为添加它会很好,以防有人遇到同样的问题。 (顺便说一句,我最终使用了绝对位置)。
http://jsfiddle.net/S8g4E/955/
这是CSS
#up { height:80px;}
#down {
height: calc(100% - 80px);//The upper div needs to have a fixed height, 80px in this case.
}
在此处了解更多信息:http://css-tricks.com/a-couple-of-use-cases-for-calc/
浏览器支持:http://caniuse.com/#feat=calc
calc
,其中广泛的浏览器支持不那么重要(IE8 及更低版本和 Safari 5 不支持它)。
#up
高度做类似的事情吗?
抽象的
我没有找到一个完全令人满意的答案,所以我不得不自己找出答案。
我的要求:
当元素的内容大小小于或大于剩余空间大小时(在第二种情况下应显示滚动条),该元素应完全占用剩余空间;
该解决方案应在计算父高度且未指定时起作用;
calc() 不应该被使用,因为剩下的元素不应该知道其他元素的大小;
应该使用现代和熟悉的布局技术,例如 flexbox。
解决方案
将所有具有计算高度(如果有的话)的直接父级和指定高度的下一个父级变成 flexbox;
将 flex-grow: 1 指定给所有具有计算高度(如果有)和元素的直接父级,以便当元素内容大小较小时它们将占用所有剩余空间;
为所有固定高度的弹性项目指定 flex-shrink: 0 ,这样当元素内容大小大于剩余空间大小时,它们不会变小;
指定 overflow: hidden 对所有具有计算高度(如果有)的直接父项以禁用滚动并禁止显示溢出内容;
为元素指定溢出:自动以启用在其中滚动。
JSFiddle (element has direct parents with computed height)
JSFiddle (simple case: no direct parents with computed height)
我的答案只使用 CSS,它不使用溢出:隐藏或显示:表行。它要求第一个孩子确实有一个给定的高度,但是在你的问题中你说只有第二个孩子需要没有指定它的高度,所以我相信你应该觉得这是可以接受的。
#container { 宽度:300px;高度:300px;边框:1px 纯红色; } #up { 背景:绿色;高度:63px;向左飘浮;宽度:100% } #down { 背景:粉色;填充顶部:63px;高度:100%; box-sizing:边框框; }
查看演示 - http://jsfiddle.net/S8g4E/6/
使用 CSS -
#container { width: 300px; height: 300px; border:1px solid red; display: table;}
#up { background: green; display: table-row; }
#down { background:pink; display: table-row;}
除非我误解,否则您可以将 height: 100%;
和 overflow:hidden;
添加到 #down
。
#down {
background:pink;
height:100%;
overflow:hidden;
}
编辑:由于您不想使用 overflow:hidden;
,因此您可以在这种情况下使用 display: table;
;但是,它在 IE 8 之前不受支持。(display: table;
support)
#container {
width: 300px;
height: 300px;
border:1px solid red;
display:table;
}
#up {
background: green;
display:table-row;
height:0;
}
#down {
background:pink;
display:table-row;
}
注意:您说过希望 #down
高度为 #container
高度减去 #up
高度。 display:table;
解决方案正是这样做的,this jsfiddle 将非常清楚地描述这一点。
overflow:hidden
以隐藏额外内容。
您可以使用浮动来下推内容:
你有一个固定大小的容器:
#container {
width: 300px; height: 300px;
}
允许内容在浮动旁边流动。除非我们将浮动设置为全宽:
#up {
float: left;
width: 100%;
}
虽然 #up
和 #down
共享顶部位置,但 #down
的内容只能在浮动 #up
的底部之后开始:
#down {
height:100%;
}
#up
上不需要圆形边框或其他花哨的东西,那么它可能是可以接受的。
<div class='parent'>
<div class='child'>
<div class='child last'>
</div>
<style>
.parent {
display: flex;
flex-direction: column;
.child {
&.last {
flex-grow: 1;
}
}
}
</style>
我不确定它是否可以纯粹用 CSS 来完成,除非你愿意用幻觉来伪装它。也许使用 Josh Mein 的答案,并将 #container
设置为 overflow:hidden
。
对于它的价值,这是一个 jQuery 解决方案:
var contH = $('#container').height(),
upH = $('#up').height();
$('#down').css('height' , contH - upH);
position: relative;
的容器内的元素相对于容器而不是窗口定位它。所以,这应该是一个可行的选择。