17

I have a very simple CSS grid with just two rows: a header and a div. I want the second row to take up all remaining view port height. Here's a repro:

html, body { margin: 0; padding: 0; }
* { box-sizing: border-box; }

body {
  display: grid;
  height: 100vh;
  width: 100vw;
}

header {
  border: 1px solid red;
}

.content {
  border: 1px solid blue;
}
<header>
  <h1>IMG + Some header text</h1>
</header>

<div class="content">
  Here will be dynamic content (a grid on its own).
  Should take all the remaining height.
</div>

This uses way too much space for the header. I want it to take up at most as much space as needed for its content not to overflow.

How can I do this?

I'm interested about any spec-based solution, though practically I would like to be able to use it at least in Chrome (or Firefox) latest stable build.

Jeroen
  • 60,696
  • 40
  • 206
  • 339

2 Answers2

33

Specify auto sizing for the header row and 1fr to allocate all the remaining space to the content row.

html, body { margin: 0; padding: 0; }
* { box-sizing: border-box; }

body {
  display: grid;
  grid-template-rows: auto 1fr;
  height: 100vh;
  width: 100vw;
}

header {
  border: 1px solid red;
}

.content {
  border: 1px solid blue;
}
<header>
  <h1>IMG + Some header text</h1>
</header>

<div class="content">
  Here will be dynamic content (a grid on its own).
  Should take all the remaining height.
</div>
BoltClock
  • 700,868
  • 160
  • 1,392
  • 1,356
5

You need to make use of grid-template-rows which is used to declare the area occupied by each row where

  • minmax(10px, auto) defines that the minimum height is 10px and maximum height can be expanded as the content increases dynamically for the header row.
  • 1fr is 1 fraction of the entire remaining space for content row.

You can also make use of auto instead of minmax if you don't want to set a minimum height.

html,
body {
  margin: 0;
  padding: 0;
}

* {
  box-sizing: border-box;
}

body {
  display: grid;
  grid-template-rows: minmax(1px, auto) 1fr;
  height: 100vh;
  width: 100vw;
}

header {
  border: 1px solid red;
}

.content {
  border: 1px solid blue;
}
<header>
  <h1>IMG + Some header text</h1>
</header>

<div class="content">
  Here will be dynamic content (a grid on its own). Should take all the remaining height.
</div>
TylerH
  • 20,799
  • 66
  • 75
  • 101