In addition to the flex-grow
property we learned in the last lesson, there are two other rules that control the flexibility of elements inside a flex-container: flex-shrink
and flex-basis
.
As in the last lesson, we'll take three blocks and use CodePen to find out what the rules' values affect.
Don't forget to change the values to see how the elements change.
flex-basis
The flex-basis
property specifies how much space the element will occupy on the main axis by default.
It may seem that flex-basis
is a replacement for width
/height
, but it's actually a bit different. flex-basis
can only be applied to elements inside a flex-container, and the property works along the main axis. Also, unlike the width
or height
properties, the flex-basis
property only sets the optimal width or height of the element before the element goes inside the container.
For all elements inside the container, we give flex-basis
a value of 200px (flex-basis: 200px
). Since the size of our container is 600 pixels, the elements fit perfectly inside it.
And what happens if one of the elements has a flex-basis
which means that the total width of all the elements exceeds the width of the flex container? Let's try to change the flex-basis
value for the first element inside the container to 400 pixels:
An interesting thing has happened; the blocks have automatically shrunk to fit inside the flex container. Both the block with flex-basis: 400px
and the blocks with flex-basis: 200px
have been made smaller. This behavior isn't always unambiguous, so browsers figure out how much space to offer blocks inside flex containers automatically.
flex-shrink
The flex-shrink
property helps to control the ability of elements to shrink depending on the size of the flex container. If the flex-grow
property helped us allocate free space between elements, then flex-shrink
helps distribute space if there isn't enough space in the container. By default, all flex elements have a flex-shrink
value of one.
Let's go back to the last example, where the total flex-basis
of the elements was greater than the width of the container. To calculate how much space will be removed from each element, you first need to calculate the total negative width. The negative width is the width we lack, meaning we can't arrange all the elements according to their flex-basis
values:
Negative width = 600 - (400 + 200 + 200) = -200px
Now, the browser needs to compensate for this negative width by narrowing all the blocks inside the flex-container. To do this, the total weight of all elements is calculated using the following formula: flex-shrink
value multiplied by the width of the block. In our case, we have the following formula:
Total weight = 1 * 400 + 1 * 200 + 1 * 200 = 800.
Now, to find out the final width of each element in the container, we need to:
- Multiply the negative width by the
flex-shrink
value - Divide the base width of the element by the total weight
- Multiply the obtained values together
The values for block 1 will be as follows:
(-200 * 1) * (400 / 800) = -100px. This is the value by which the block will be shrunk if it does not have enough space.
For the other two blocks, you can calculate their values using the same formula and get -50px.
If the value is set to flex-shrink: 0
, it will prevent the block from shrinking.
flex
The flex
property is an abbreviated version of all the properties discussed in this lesson and the last lesson. This is a very convenient shorthand property that allows you to set all the parameters in one line, which is good for when people are reading your code. The specification also says that flex
is the preferable notation form. Properties within flex are written in the following order:
- flex-grow
- flex-shrink
- flex-basis
Docs
- flex
- flex-basis
- flex-shrink
For full access to the course you need a professional subscription.
A professional subscription will give you full access to all Hexlet courses, projects and lifetime access to the theory of lessons learned. You can cancel your subscription at any time.