Make a div as large as possible in flexLayout - html

#container {
display: flex;
flex-direction: column;
align-items: center;
height: 200px;
width: 100px;
background-color: red;
}
#stack{
display: flex;
flex-direction: column;
align-items: center;
max-height: 200px;
}
.item {
display: flex;
height: 30px;
width: 100px;
background-color: green;
flex-shrink: 0;
}
.spacer {
display: flex;
height: 200px;
flex-shrink: 1000;
}
<div id="container">
<div class="stack">
<div class="item">a</div>
<div class="spacer"></div>
<div class="item">b</div>
</div>
</div>
As the code shows above, parent had a max-height as the height of it is undefined.
I want the height of spacer was as large as possible. And what I expect is 160px in this situation.
I had tried flex-grow, but it doesn't work as the container has no height.
I had tried flex-shrink and a large height like the code in snippet either. But I found that sometime flex-shrink not work, or sometimes it looks scary with a very large height.

it does not work because you use a wrong selector for "stack" - it is a class, not id!
This should work: https://jsfiddle.net/bL5w81d4/1/
#container {
display: flex;
flex-direction: column;
align-items: center;
height: 200px;
width: 100px;
background-color: red;
}
.stack{
display: flex;
flex-direction: column;
align-items: center;
max-height: 200px;
}
.item {
display: flex;
height: 30px;
width: 100px;
background-color: green;
flex-shrink: 0;
}
.spacer {
display: flex;
height: 200px;
flex-shrink: 1000;
}

Related

flexbox justify-content causes overflow: auto not work correctly

I have a container div that its content can grow vertically. I used overflow-y: auto for the container to make my page look good. But I need to place everything in the center when the content's height is smaller than the container's. So I used flexbox to do that. But the problem is that I can't scroll completely to see the top part of the contents.
Here is a simple example of the problematic code:
<html lang="en">
<head>
<style>
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: center;
flex-direction: column;
align-items: center;
overflow-y: auto;
}
.child {
width: 10rem;
height: 40rem;
background-color: blue;
flex-shrink: 0;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
</style>
</head>
<body>
<div class="container">
<div class="child">
<div class="top"></div>
</div>
</div>
</body>
</html>
One of the solutions to this problem is to use the reverse order of the elements in the flex-container, i.e. in your case, using flex-direction: column-reverse instead of flex-direction: column.
Example #1 below:
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: center;
flex-direction: column-reverse;
align-items: center;
overflow-y: auto;
}
.child {
width: 10rem;
min-height: 0;
height: 40rem;
background-color: blue;
flex-shrink: 0;
max-height: 150%;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
<div class="container">
<div class="child">
<div class="top">test</div>
</div>
</div>
The second solution is to consider using for center alignment, you can also use justify-content: space-between and pseudo-elements ::after and ::before.
Example #2 below:
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: space-between;
flex-direction: column;
align-items: center;
overflow-y: auto;
}
.container::before,
.container::after {
content: '';
}
.child {
width: 10rem;
min-height: 0;
height: 40rem;
background-color: blue;
flex-shrink: 0;
max-height: 150%;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
<div class="container">
<div class="child">
<div class="top">test222</div>
</div>
</div>

How can I force center specific element in flex container?

I want to center specific div inside flex container. You will understand me better with the code:
Here is my code:
<html>
<head>
<style>
div.flex_container {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
align-items: baseline;
align-content: stretch;
}
div.red_box {
background-color: red;
width: 100px;
height: 100px;
}
div.blue_box {
background-color: blue;
width: 100px;
height: 100px;
}
div.yellow_box {
background-color: yellow;
width: 100px;
height: 100px;
}
</style>
</head>
<body>
<div class="flex_container">
<div class="red_box"></div>
<div class="blue_box"></div>
<div class="yellow_box"></div>
</div>
</body>
</html>
Alternatively here is the JSFiddle code.
Currently, Blue Box is in the center location, but I want a Red Box in the center and others on the right of it.
How can achieve this, how can I force center specific element inside flex container?
EDIT: Without changing order.
Thanks in advance!
You can use CSS order property.
Just by adding order: number; to your boxes properties. Like this:
div.flex_container {
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
align-items: baseline;
align-content: stretch;
}
div.red_box {
background-color: red;
width: 100px; height: 100px;
order: 2;
}
div.blue_box {
background-color: blue;
width: 100px; height: 100px;
order: 1;
}
div.yellow_box {
background-color: yellow;
width: 100px; height: 100px;
order: 3;
}
<div class='flex_container'>
<div class='red_box'></div>
<div class='blue_box'></div>
<div class='yellow_box'></div>
</div>
Check this link for more details about Ordering Flex Items
Remove the justify-content: center and add margin-left to red_box
div.flex_container {
display: flex;
flex-direction: row;
flex-wrap: wrap;
align-items: baseline;
align-content: stretch;
}
div.red_box {
background-color: red;
width: 100px; height: 100px;
/* ↓ width / 2) */
margin-left: calc(50% - 50px);
}
div.blue_box {
background-color: blue;
width: 100px; height: 100px;
}
div.yellow_box {
background-color: yellow;
width: 100px; height: 100px;
}
<div class='flex_container'>
<div class='red_box'></div>
<div class='blue_box'></div>
<div class='yellow_box'></div>
</div>

Flex Box Behavior

I cannot understand WHY I am not getting this:
.container {
width: 600px;
height: 400px;
border: 3px solid green;
}
.cg-panel {
display: flex;
flex-flow: column;
align-items: stretch;
justify-content: center;
}
.cg-panel .content {
flex: 1;
background-color: tomato;
}
<div class="container">
<div class="cg-panel">
<div class="content"></div>
</div>
</div>
I, for the life of me, cannot understand why the content panel does not vertically stretch the entire container. What is the purpose of "flex:1" if it isn't going to work? Am I not reading the documentation correctly?
There's nothing in your CSS that is expanding the height of .cg-panel to fit its parent .container.
Adding height: 100%; to .cg-panel fixes this:
.container {
width: 600px;
height: 400px;
border: 3px solid green;
}
.cg-panel {
display: flex;
flex-flow: column;
align-items: stretch;
justify-content: center;
height: 100%; /* add this */
}
.cg-panel .content {
flex: 1;
background-color: tomato;
}
<div class="container">
<div class="cg-panel">
<div class="content"></div>
</div>
</div>

How to stretch div to full height with flex

How do I stretch the divs with a yellow background to full height? It should cover up the green but it is not working. I tried adding height: 100% on it but then it adds up the height from the search bar?
https://jsfiddle.net/nuy20j1h/
.block {
width: 80%;
margin: 0 auto;
display: flex;
flex-wrap: wrap;
}
.sidebar {
height: 600px;
width: 25%;
background: red;
}
.home {
display: flex;
flex-wrap: wrap;
align-items: flex-start;
width: 75%;
background: green;
}
.search-bar {
width: 100%;
padding: 25px;
background: blue;
}
.content-wrap {
display: flex;
flex-wrap: wrap;
width: 100%;
align-items: flex-stretch;
}
.content,
.single {
width: 50%;
background: yellow;
}
<div class="block">
<div class="sidebar">sidebar</div>
<div class="home">
<div class="search-bar">search bar</div>
<div class="content-wrap">
<div class="content">lorem ipsum</div>
<div class="single">test</div>
</div>
</div>
</div>
First you should add a style reset, I'm using this now * {} as you can se below. The trick here is to run flex-direction: column; on .home and you can tell .content-wrap to take up the rest of that space after the search with flex-grow: 1;
box-sizing: border-box; is, if you add let's say width: 200px; to a element, and add padding: 20px;, the element will stay 200px with the padding included. If you don't have that, it will take up 200px + 40px.
if you want the fiddle, here it is
* {
padding: 0;
margin: 0;
box-sizing: border-box;
}
.block {
width: 80%;
margin: 0 auto;
display: flex;
flex-wrap: wrap;
}
.sidebar {
height: 600px;
width: 25%;
background: red;
}
.home {
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-items: flex-start;
width: 75%;
background: green;
}
.search-bar {
width: 100%;
padding: 25px;
background: blue;
}
.content-wrap {
display: flex;
flex-grow: 1;
flex-wrap: wrap;
width: 100%;
align-items: flex-stretch;
}
.content,
.single {
width: 50%;
background: yellow;
}
<div class="block">
<div class="sidebar">sidebar</div>
<div class="home">
<div class="search-bar">search bar</div>
<div class="content-wrap">
<div class="content">lorem ipsum</div>
<div class="single">test</div>
</div>
</div>
</div>
As mentioned in other answers, there is one main issue here:
flex-direction: column;, which I added to home, to enable the usage of flex properties instead of height, to make the .content-wrap fill the available space left in home
That will make the .search-bar and .content-wrap stack vertical, and enable the use of flex: 1 on .content-wrap, which will make it fill the remaining space/height.
So even if you got answers already, and since there are some properties with wrong value, or not needed, I decided to post an answer to clarify the changes made.
See my notes made in the CSS for further clarifications and what I changed.
Stack snippet
.block {
width: 80%;
margin: 0 auto;
display: flex;
flex-wrap: wrap;
}
.sidebar {
height: 600px;
width: 25%;
background: red;
}
.home {
display: flex;
flex-direction: column; /* added */
/*flex-wrap: wrap; removed, not needed */
/*align-items: flex-start; removed, items should fill parent's,
in this changed case, width */
width: 75%;
background: green;
}
.search-bar {
/*width: 100%; not needed, default for column
item is to fill parent width as
its "align-items" is "stretch" */
padding: 25px;
background: blue;
}
.content-wrap {
flex: 1; /* added, take the remaining space left
left of its parent (height in this case) */
display: flex;
flex-wrap: wrap;
/*width: 100%; not needed, default for column
item is to fill parent width as
its "align-items" is "stretch" */
/*align-items: flex-stretch; wrong value, should be "stretch",
though since that is the default,
it is not needed */
}
.content,
.single {
width: 50%;
background: yellow;
}
<div class="block">
<div class="sidebar">sidebar</div>
<div class="home">
<div class="search-bar">search bar</div>
<div class="content-wrap">
<div class="content">lorem ipsum</div>
<div class="single">test</div>
</div>
</div>
</div>
flex-direction: column; is your friend. Here is a reworked fiddle of your code: https://jsfiddle.net/vsjktmms/1/
Using the same HTML structure you provided:
.block {
display: flex;
width: 80%;
margin: 0 auto;
background-color: gray;
align-items: stretch;
}
.sidebar {
width: 25%;
height: 600px;
background-color: red;
}
.home {
display: flex;
flex-direction: column;
align-items: stretch;
width: 75%;
background-color: green;
}
.search-bar {
padding: 25px;
background-color: blue;
}
.content-wrap {
flex: 1 1 auto;
display: flex;
flex-wrap: wrap;
width: 100%;
background-color: pink;
}
.content,
.single {
width: 50%;
background: yellow;
}

Flexbox "align-items : center" shrinks a child's max-width

I have a flexbox div container with align-items: center, with three childs. One of them has max-width: 200px (in the code, second-ch), and it's also a flex with two childs distributed with justify-content: space-between, but second-ch is not following its max-width. If I remove align-items: center from container, second-ch takes again the width desired but the remaining elements are not in the center anymore. How can I solve that?
.container {
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: center;
}
.first-ch {
width: 70px;
height: 70px;
background-color: grey;
}
.second-ch {
max-width: 200px;
height: 80px;
background-color: red;
display: flex;
justify-content: space-between;
}
.square {
width: 50px;
height: 50px;
background-color: yellow;
margin: 5px;
}
.third-ch {
width: 50px;
height: 50px;
background-color: blue;
}
<div class="container">
<div class="first-ch"></div>
<div class="second-ch">
<div class="square"></div>
<div class="square"></div>
</div>
<div class="third-ch"></div>
</div>
Citing the comment of Jason Deppen:
I solved it by also setting width: 100% along with my max-width value.
max-width: <your max width>;
width: 100%;
Why is this happening ?
It's not really the effect of align-items: center. It's the omision of the default value, align-items: stretch , that makes the child grow.
.container {
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: stretch; /* default */
}
.first-ch {
width: 70px;
height: 70px;
background-color: grey;
}
.second-ch {
max-width: 200px;
height: 80px;
background-color: red;
display: flex;
justify-content: space-between;
}
.square {
width: 50px;
height: 50px;
background-color: yellow;
margin: 5px;
}
.third-ch {
width: 50px;
height: 50px;
background-color: blue;
}
<div class="container">
<div class="first-ch"></div>
<div class="second-ch">
<div class="square"></div>
<div class="square"></div>
</div>
<div class="third-ch"></div>
</div>
If you want the child to grow until it reaches the width-max, do as bolverin says and set the width explicitly
I know this is old but for anyone reading this:
Using align-self: stretch; on the child element will also work :)
So in this case:
.container {
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: center;
}
...
.second-ch {
max-width: 200px;
align-self: stretch;
...
}
...
why do you use max-width: 200px;? try width: 200px;
when you use align-items : center the .second-ch has minimal needed width.
max-width limits max width of the block but doesn't set minimal width