96

I need to fill the remaining vertical space of #wrapper under #first with #second div.

I need an only CSS solution.

#wrapper {
  width: 300px;
  height: 100%;
}

#first {
  width: 300px;
  height: 200px;
  background-color: #F5DEB3;
}

#second {
  width: 300px;
  height: 100%;
  background-color: #9ACD32;
}
<div id="wrapper">
  <div id="first"></div>
  <div id="second"></div>
</div>
reisdev
  • 3,215
  • 2
  • 17
  • 38
Airy
  • 5,484
  • 7
  • 53
  • 78
  • @Pete No, they are dynamic. Only first div is of fixed 200px height. while second div will fill the remaining height of wrapper – Airy Apr 30 '14 at 13:16
  • Do you want this? http://jsfiddle.net/K5n4U/ – laaposto Apr 30 '14 at 13:17
  • @laaposto no this isn't the thing. Wrapper should be 100% filling the entire vertical height of the screen. – Airy Apr 30 '14 at 13:19
  • this is a better example : https://codepen.io/micjamking/pen/QdojLz – Buddy Oct 16 '18 at 13:23
  • A nice and neat overview of some common solutions for this problem (quite an obvious issue in my opinion, I find it very surprising that there is not a clear, definitive css solution) https://www.whitebyte.info/programming/css/how-to-make-a-div-take-the-remaining-height – L. Bruce Apr 10 '21 at 10:55

8 Answers8

61

html, body {
  height: 100%;
  margin: 0;
}

.wrapper {
  display: flex;
  flex-direction: column;
  width: 300px;
  height: 100%;
}

.first {
  height: 50px;
}

.second {
  flex-grow: 1;
}
<div class="wrapper">
  <div class="first" style="background:#b2efd8">First</div>
  <div class="second" style="background:#80c7cd">Second</div>
</div>
Reggie Pinkham
  • 11,985
  • 4
  • 38
  • 36
57

You can use CSS Flexbox instead another display value, The Flexbox Layout (Flexible Box) module aims at providing a more efficient way to lay out, align and distribute space among items in a container, even when their size is unknown and/or dynamic.

Example

/* CONTAINER */
#wrapper
{
   width:300px;
   height:300px;
    display: -webkit-box; /* OLD - iOS 6-, Safari 3.1-6 */
    display: -moz-box; /* OLD - Firefox 19- (buggy but mostly works) */
    display: -ms-flexbox; /* TWEENER - IE 10 */
    display: -webkit-flex; /* NEW - Chrome */
    display: flex; /* NEW, Spec - Opera 12.1, Firefox 20+ */
    -ms-flex-direction: column;
    -moz-flex-direction: column;
    -webkit-flex-direction: column;
    flex-direction: column;
}

/* SOME ITEM CHILD ELEMENTS */
#first
{
   width:300px;
    height: 200px;
   background-color:#F5DEB3;

}

#second
{
   width:300px;
   background-color: #9ACD32;
    -webkit-box-flex: 1; /* OLD - iOS 6-, Safari 3.1-6 */
    -moz-box-flex: 1; /* OLD - Firefox 19- */
    -webkit-flex: 1; /* Chrome */
    -ms-flex: 1; /* IE 10 */
    flex: 1; /* NEW, */
}

jsfiddle Example

If you want to have full support for old browsers like IE9 or below, you will have to use a polyfills like flexy, this polyfill enable support for Flexbox model but only for 2012 spec of flexbox model.

Recently I found another polyfill to help you with Internet Explorer 8 & 9 or any older browser that not have support for flexbox model, I still have not tried it but I leave the link here

You can find a usefull and complete Guide to Flexbox model by Chris Coyer here

jox
  • 2,218
  • 22
  • 32
xzegga
  • 3,051
  • 3
  • 25
  • 45
  • 1
    Flexbox model is only supported on higher version of IE10. If you can partial support for older versions of IE you need to use polyfill like flexie – xzegga Apr 30 '16 at 17:02
  • Will it work on IE10? caniuse.com suggests no, and unfortunately I have to support it for a little while longer. (Turns out the correct answer is 'sort of': https://msdn.microsoft.com/en-us/library/hh673531(v=vs.85).aspx) – Michael Scheper Jan 16 '18 at 05:55
  • If anyone is reading this and wants to make the wrapper div fill the height of the entire page, then simply change height: 300px; to height:100vh; – Paul Chris Jones Mar 26 '20 at 21:16
29

You can do this with position:absolute; on the #second div like this :

FIDDLE

CSS :

#wrapper{
    position:relative;
}

#second {
    position:absolute;
    top:200px;
    bottom:0;
    left:0;
    width:300px;
    background-color:#9ACD32;
}

EDIT : Alternative solution

Depending on your layout and the content you have in those divs, you could make it much more simple and with less markup like this :

FIDDLE

HTML :

<div id="wrapper">
    <div id="first"></div>
</div>

CSS :

#wrapper {
    height:100%;
    width:300px;
    background-color:#9ACD32;
}
#first {
    background-color:#F5DEB3;
    height: 200px;
}
Mathieu Dhondt
  • 8,405
  • 5
  • 37
  • 58
web-tiki
  • 99,765
  • 32
  • 217
  • 249
  • 4
    Not, it is not filling the remaining space of wrapper. If you suppose decrease the height of wrapper you can see that it is not filling it. – Airy Apr 30 '14 at 13:21
  • 2
    @AbdulJabbarWebBestow just add `position:relative;` to `#wrapper` like this http://jsfiddle.net/webtiki/Cb5bu/ and the div will fill the remaining space of wrapper. – web-tiki Apr 30 '14 at 13:24
  • 1
    Excellent Work. Thanks Dear Web-Tiki – Airy Apr 30 '14 at 13:30
  • @AbdulJabbarWebBestow - I should point out that if you have too much content in this olution, the overflow won't be handled well: http://jsfiddle.net/Cb5bu/7/ vs http://jsfiddle.net/3EjX8/2/ – Pete Apr 30 '14 at 13:33
  • @JimmyRare and why is that you don't see it as a flexible solution? will it make any problem? – Airy Apr 30 '14 at 13:38
  • 1
    @Pete Well the point here is to fill the remaining space because it lacks content... If it had to much content, there would not be any problem. – web-tiki Apr 30 '14 at 13:41
  • 1
    @Pete, I see that you are correct when it overflows with content. But fortunately, due to some limited content it will not be overflowed. – Airy Apr 30 '14 at 13:46
  • 1
    @AbdulJabbarWebBestow No worries, was just pointing out in case it did – Pete Apr 30 '14 at 13:48
  • 1
    Hey! Web-Tiki! your example really helped in many other problems. I got a sound understanding how to deal with such CSS issues. Thanks again. – Airy Apr 30 '14 at 15:12
  • 1
    For future readers who want to do this but don't know the height of #first you can use the display:flex css solution specified below which causes #second to expand to all remaining space even if #first's height changes. – owencm Mar 19 '15 at 23:41
  • Not working when you add some content. It does not stay inside the block. –  Dec 31 '16 at 14:16
  • I think this is not a working solution to the question. If the height of `#first` changes, `#second` does not change, and thus it does _not_ fill the remaining vertical space (see the first fiddle of the answer) – L. Bruce Apr 10 '21 at 10:49
12

If you can add an extra couple of divs so your html looks like this:

<div id="wrapper">
    <div id="first" class="row">
        <div class="cell"></div>
    </div>
    <div id="second" class="row">
        <div class="cell"></div>
    </div>
</div>

You can make use of the display:table properties:

#wrapper
{
   width:300px;
   height:100%;
   display:table;
}

.row 
{
   display:table-row;
}

.cell 
{
   display:table-cell;
}

#first .cell
{
   height:200px;
   background-color:#F5DEB3;
}

#second .cell
{
   background-color:#9ACD32;
}

Example

Pete
  • 57,112
  • 28
  • 117
  • 166
4

Have you tried changing the wrapper height to vh instead of %?

#wrapper {
width:300px;
height:100vh;
}

That worked great for me when I wanted to fill my page with a gradient background for instance...

  • The easiest, and most effective answer here. This worked perfectly. –  May 21 '22 at 06:13
0

If you don't want to have fix heights for your main-container (top, bottom, ....), you can simply use this css-file to get a flex-container which uses the remaining space incl. working!!! scrollbars

Fiddler

<!DOCTYPE html>
<html >
<head>
    <title>Flex Container</title>
    <link rel="stylesheet" href="http://demo.qooxdoo.org/5.0/framework/indigo-5.0.css">

  <style>
    .cont{
        background-color: blue;
        position: absolute;
        height: 100%;
        width: 100%;
    }

    .headerContainer {
        background-color: green;
        height: 100px;
        width: 100%;
    }

    .mainContainer {
        background-color: white;
        width: 100%;
        overflow: scroll
    }

    .footerContainer {
        background-color: gray;
        height: 100px;
        width: 100%;
    }
  </style>


  </head>

<body class="qx-flex-ready" style="height: 100%">
  <div class="qx-vbox cont">
    <div class="headerContainer">Cell 1: flex1</div>
    <div class="mainContainer qx-flex3">
    x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>
    x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>
    x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>
    x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>
    x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>x<br>

    </div>
    <div class="footerContainer" >Cell 3: flex1</div>
  </div>
</body>
</html>
Tobias Koller
  • 2,116
  • 4
  • 26
  • 46
-1

All you need is a bit of improved markup. Wrap the second within the first and it will render under.

<div id="wrapper">
    <div id="first">
        Here comes the first content
        <div id="second">I will render below the first content</div>
    </div>
</div>

Demo

JimmyRare
  • 3,958
  • 2
  • 20
  • 23
-3

You can just add the overflow:auto option:

#second
{
   width:300px;
   height:100%;
   overflow: auto;
   background-color:#9ACD32;
}