How to use Flex-grow with "justify-content: start" behavior [duplicate] - css

This question already has answers here:
Targeting flex items on the last or specific row
(10 answers)
Closed 1 year ago.
I have a flex container like this:
.container {
display: flex;
flex-flow: row wrap;
justify-content: start;
width: 100%;
}
.item {
border: 1px solid red;
flex: 1 1 33%;
height: 100px;
}
<div class="container">
<div class="item">#1</div>
<div class="item">#2</div>
<div class="item">#3</div>
<div class="item">#4</div>
<div class="item">#5</div>
</div>
The container holds more or less divs in a row depending on the size of the screen, so I chose to use the flex shorthand with flex-grow: 1 for smooth size changes.
My problem is that I want #4 and #5 to have the same width as #1, #2 and #3 instead of taking up the whole space.

Set flex grow to 0 and basis to 33.33%
flex: 0 1 33.33%;

Related

(inline/shrink/auto?)flex grandparent -> flex parent -> flex-basis (DOA)

I'm working on a custom <tab-view> with the following markup semantics:
#tab-wrapper, #slot {
display: flex;
flex-wrap: nowrap;
}
#slot {
flex: auto 1 auto;
}
.tab {
flex: 1 1 10em;
border: 1px solid gray;
}
#new {
flex: 0 0 auto;
}
<div id="tab-wrapper">
<div id="slot">
<div class="tab">test1</div>
<div class="tab">test2</div>
</div>
<span id="new">✚</span>
<div>
But what I want is something like this:
I need the flex-basis of the tabs to be 10em initially, but also allow them to shrink when more tabs are open than there is available space.
I'm not worried about overflow or anything like that, just that the #new element comes after the tabs with their preferred 10em flex basis.
I've tried flex-shrink: auto but it has the same effect as flex-shrink: 1.
flex-shrink: 0 is not an option because I want them to be able to shrink - and in this case flex-shrink: 0 makes the #new tab button go out of view completely.
Note: the tab items themselves are also custom elements and don't use any styling other than the default display: inline but that shouldn't matter here.
I'm glad you fixed your issue with width. But I think your problem was elsewhere.
div#slot has a property of flex: auto 1 auto which is not valid and ignored. div#slot is a child of a flex element div#tab-wrapper so its width is the minimum width of the content. This is why the tabs are shrinked.
Now if you replace flex: auto 1 auto by flex: 1 1 auto (flex-grow: 1) div#slot will have a width of 100% the width of div#tab-wrapper and flex: 1 1 10em will work as expected on tabs.
#tab-wrapper,
#slot {
display: flex;
flex-wrap: nowrap;
}
#slot {
/* previouly flex: auto 1 auto; */
flex: 1 1 auto;
}
.tab {
flex: 1 1 10em;
border: 1px solid gray;
}
#new {
flex: 0 0 auto;
}
<div id="tab-wrapper">
<div id="slot">
<div class="tab">test1</div>
<div class="tab">test2</div>
</div>
<span id="new">✚</span>
<div>

Prevent FlexChild from growing [duplicate]

This question already has answers here:
How to disable equal height columns in Flexbox?
(4 answers)
What are the differences between flex-basis and width?
(6 answers)
Closed 4 years ago.
Given the following code:
.outer-container {
display: flex;
justify-content: space-evenly;
}
.left-container {
height: 300px;
}
.right-container {
flex: 0 1 auto;
}
<div class='outer-container'>
<div class='left-container'>Lefto</div>
<div class='right-container'>Righto</div>
</div>
The right container will grow to be 300px high, despite the flex-grow property being set to 0. How do I prevent this from happening? I.E., I want the right container to only be as tall as its content.
Codepen: https://codepen.io/MaxMillington2/pen/PxOwxo
Add align-self: flex-start on the .right-container
.outer-container {
display: flex;
justify-content: space-evenly;
}
.left-container {
height: 300px;
border: 1px solid blue;
}
.right-container {
align-self: flex-start;
border: 1px solid red;
}
<div class='outer-container'>
<div class='left-container'>Lefto</div>
<div class='right-container'>Righto</div>
</div>
Note: flex-grow, flex-shrink and flex-basis are for controlling how the space is filled along the main axis. In this case, the main axis is left-right because the flex-direction is set to row by default.
The align-items property will align the items on the cross axis. The initial value for this property is stretch and this is why flex items stretch to the height of the tallest one by default.
MDN - Concepts of Flexbox
That is why you need to override either align-items on your .outer-container or align-self to the flex children.

Why is flex item wider than container? [duplicate]

This question already has answers here:
Why don't flex items shrink past content size?
(5 answers)
Closed 4 years ago.
When using flexbox, sometimes, like in the example below, when the viewport is not wide enough to contain the content, the flexbox items get higher width than the container.
When and why does this happen?
How can I limit the items to never be wider than the container?
Code:
.container {
display: flex;
flex-flow: row wrap;
justify-content: center;
}
.item-1 {
flex: 1 1;
background-color: yellow;
}
.item-2 {
flex: 1 0 100%;
background-color: green;
}
<div class="container">
<div class="item item-1">
item1item11item111item1111item11111item111111item1111111item11111111item111111111item1111111111
</div>
<div class="item item-2">
item2item22item222item2222item22222item222222item2222222
</div>
</div>
Here is a code pen:
https://codepen.io/anon/pen/MqdaoB
try to give some space between character or give word-break to .item
.item {
word-break: break-word;
}
https://codepen.io/anon/pen/YObyjq

Why flex container `flex: 1 0 0px` collapses on Chrome?

On Chrome I encountered Flexbox behaviour I don't understand. When a flex child which is also a flex container has flex: 1 0 0px, it collapses itself and it's contents.
Even though flex-basis is set to 0px, as far as I understand setting flex-grow to 1 (first number in flex shorthand) should make the item grow, when needed.
In my example .bottom-container has height set to 300px. That height is respected on Firefox, but collapsed to 0px on Chrome. Why?
.top-container {
display: flex;
flex-flow: column nowrap;
}
.middle-container {
flex: 1 0 0px;
display: flex;
flex-flow: column nowrap;
}
.bottom-container {
flex: 0 0 auto;
height: 300px;
}
<div class="top-container">
<div class="middle-container">
<div class="bottom-container"></div>
</div>
<div class="middle-container">
<div class="bottom-container"></div>
</div>
</div>
The problem is with the flex-basis component.
When you have flex-basis: 0, Chrome and Firefox compute to flex-basis: 0px.
However, the pixel value breaks your layout in Chrome.
Instead, for cross-browser compatibility, use this:
flex: 1 0 0%
Ok, so here's the logic.
You haven't specified a height of .top-container so it's child elements (.middle-container) cannot grow, because there is no room for them to grow into, despite having flex: 1 0 0 and, therefore, .middle-container elements will always maintain a height of 0.

Horizontally Center Title Over Unknown Number of Items that Wrap [duplicate]

This question already has answers here:
How to adapt div's width to content with flexbox
(4 answers)
How to change flexbox wrap?
(2 answers)
Targeting flex items on the last or specific row
(10 answers)
Closed 5 years ago.
I have what seems like a simple CSS question but has been rather vexing for me as a styles newbie. Any help is really appreciated. I tried to find another example on Stack Overflow and couldn't which surprised me, so if this is a dupe pls point me in the right direction.
I have a container element that contains some text and a list of elements with fixed dimensions.
<div class='container'>
<p> Title </p>
<div class='item'>1</div>
<div class='item'>2</div>
<div class='item'>3</div>
<div class='item'>4</div>
</div>
I don't know how many items I will actually have - it might be 3 - 9. I want the container to be centered on the page and the heading to be centered above the items, but I want the items to be added left to right. I want the items to align left so that they appear centered under the heading and on the page when the row is full, but should appear from left to right if a row is not full. So if the screen can fit three and there are four, the fourth should align with the first element and not be in the middle.
.container {
margin: 0 auto;
display: inline-flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: flex-start;
}
p {
margin: 0 auto;
text-align: center;
justify-content: center;
align-self: center;
display: block;
}
.item {
flex: none;
width: 200px;
height: 100px;
background-color: red;
margin: 20px;
}
The issue I'm having is that I can center the text, but because the width of the parent is not based on the width of the children, it always appears slightly off center. So, I read that I can force the parent's width to be based on the children's width by setting display: inline-flex on the parent. This accomplishes that, but unfortunately that then forces the heading to be in-line with the items, which defeats the purpose. The only reason I need the width of the parent to be calculated based on children's width is so that the text will know how to center itself inside the parent.
Any help would be really appreciated. I don't need to use flexbox - any other approach that works would be great...this is just the latest in a series of different things I've tried.
If i understood the question correctly, you were on the right track, setting display:block on the p was a good idea, but you also need to set width:100% so it won't stay inline with the other items.
See below or jsFiddle
.container {
margin: 0 auto;
display: inline-flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: flex-start;
}
p {
width: 100%;
margin: 0 auto;
text-align: center;
justify-content: center;
align-self: center;
display: block;
}
.item {
flex: none;
width: 200px;
height: 100px;
background-color: red;
margin: 20px;
}
<div class='container'>
<p> Title </p>
<div class='item'>1</div>
<div class='item'>2</div>
<div class='item'>3</div>
<div class='item'>4</div>
</div>

Resources