Reputation: 8462
How to properly stretch a child to parent's height? I've tried a lot of variants I found (many quite complicated), but it never worked for me. I would prefer to do this with flex-box, as that seems the newest method. Here is my try:
<div class="main h-100">
<nav class="navbar navbar-expand-lg navbar-dark bg-primary">
<a href class="navbar-brand">Menu</a>
</nav>
<div class="container-fluid h-100">
<div class="row h-100">
<div class="col-xs-2 bg-light h-100 pr-3 menuContainer">
<button class="btn btn-outline-primary mt-3 btn-sm btn-block"> Test </button>
<nav class="navbar navbar-light list">
<ul class="navbar-nav flex-column">
<li class="nav-item"><a href="#" class="nav-link">A1</a></li>
<li class="nav-item"><a href="#" class="nav-link">A1</a></li>
</ul>
</nav>
</div>
<div class="col-xs-10 p-0">
Content
</div>
</div>
</div>
body {
height: 100vh;
}
.bg-light {
background-color: green !important;
}
.list {
overflow-y: auto;
height: 100%;
align-items:start
}
.menuContainer {
display: flex;
flex-flow: row wrap;
}
.list {
flex: 1;
background-color: red;
}
http://jsfiddle.net/x1hphsvb/2065/
In the end I'd like to remove the scroll, so that the menu (red box) starts where it starts now and ends exactly where the screen end is.
The aim is also to be able to put anything instead of Content
with height: 100%
so it does the same.
Both content and menu can be bigger - in that case I expect them to add a scroll on it's own - I use overflow-y: auto
for that.
Upvotes: 1
Views: 2723
Reputation: 362290
In Bootstrap 4.1 there is a flex-fill
utility class for this purpose.
.flex-fill {
flex: 1 1 auto;
}
In your case, add it to your container-fluid
and you won't need all the h-100
s. Also, make the container fluid
d-flex
so that flex-fill
can also be applied on the row
.
<div class="main h-100 d-flex flex-column">
<nav class="navbar navbar-expand-lg navbar-dark bg-primary">
<a href class="navbar-brand">Menu</a>
</nav>
<div class="container-fluid flex-fill d-flex">
<div class="row flex-fill">
<div class="col-xs-2 bg-light pr-3 menuContainer d-flex flex-column">
<button class="btn btn-outline-primary mt-3 btn-sm btn-block"> Test </button>
<nav class="nav navbar-light list">
<ul class="navbar-nav flex-column">
<li class="nav-item"><a href="#" class="nav-link">A1</a></li>
<li class="nav-item"><a href="#" class="nav-link">A1</a></li>
</ul>
</nav>
</div>
<div class="col-xs-10 p-0">
Content
</div>
</div>
</div>
</div>
https://www.codeply.com/go/GEiw0PABgi
Also, note that col-xs-*
is col-*
in Bootstrap 4 as the -xs
infix has been removed. Here's a simplified example w/o the extra CSS.
Related questions: Bootstrap 4 Navbar and content fill height flexbox
Upvotes: 1
Reputation: 371013
You're getting an overflow because you're giving many (if not all) of your elements height: 100%
. It's coming with the Bootstrap code:
.h-100 {
height: 100% !important;
}
As a result, when there is more than one element in a container, the siblings overflow the parent.
I would remove height: 100%
from elements that you want to have fill the height of the container. Flexbox offers a more efficient method.
When you set display: flex
on an element it applies align-items: stretch
on the child elements. This means that the children will automatically expand to fill the height of the container.
Set a height on one element (i.e., an ancestor). Then keep adding display: flex
to each child down the HTML structure. There is no problem nesting flex containers.
Upvotes: 2
Reputation: 66325
http://jsfiddle.net/x1hphsvb/2083/
html, body {
height: 100%;
}
.bg-light {
background-color: green !important;
}
.list {
overflow-y: auto;
align-items:start
}
.menuContainer {
display: flex;
flex-direction: column;
}
.list {
flex: 1;
background-color: red;
}
.site-content {
height: calc(100% - 56px);
}
Key differences:
flex-direction: column
on sidebar items.calc(100% - 56px)
which is the header height.Upvotes: 2