I find the difference between align-items
and align-content
in CSS Flexbox properties extremely confusing. I've been looking at the documentation, and several examples online for hours, but I still can't fully grasp it.
To be more precise, align-items
makes total sense to me and it's completely clear how it behaves. On the other hand, align-content
is not clear at all. In particular, I don't understand why we should use two different properties depending on whether the content all fits in one line or multiple ones.
What is the explanation in layman's terms?
The align-content property determines how flex lines are aligned along the cross-axis while the align-items property determines how flex items are aligned within a flex line and along the cross-axis.
align-content manages the space between the lines when items wrap. align-items aligns the items relative to each other when sizes of items are different. When the size of the items are the same and there is only one line, they behave similarly.
The align-self applies to all flex items, allows this default alignment to be overridden for individual flex items. The align-content property only applies to multi-line flex containers, and aligns the flex lines within the flex container when there is extra space in the cross-axis.
The align-content property is a sub-property of the Flexible Box Layout module. It helps to align a flex container's lines within it when there is extra space in the cross-axis, similar to how justify-content aligns individual items within the main-axis.
The align-self applies to all flex items, allows this default alignment to be overridden for individual flex items. The align-content property only applies to multi-line flex containers, and aligns the flex lines within the flex container when there is extra space in the cross-axis. First you need to understand how Flexible box structure works.
justify-content and align-items are similar in their behviour, the difference being that justify-content works on the the main axis while align-items works on the cross axis. align-content works only on multi-line containers and has no effect on single line containers. w3.org documentation on Flexbox is pretty comprehensive and a good read.
The align-items property of flex-box aligns the items inside a flex container along the cross axis just like justify-content does along the main axis. (For the default flex-direction: row the cross axis corresponds to vertical and the main axis corresponds to horizontal. With flex-direction: column those two are interchanged respectively).
The align-content property only applies to multi-line flex containers, and aligns the flex lines within the flex container when there is extra space in the cross-axis. Here you have a snippet to play: Show activity on this post. First you need to understand how the Flexible box structure works. The below image is part of the Cheatsheet.
As described in 6. Flex Lines,
Flex items in a flex container are laid out and aligned within flex lines, hypothetical containers used for grouping and alignment by the layout algorithm. A flex container can be either single-line or multi-line, depending on the flex-wrap property
Then, you can set different alignments:
The justify-content
property applies to all flex containers, and sets the alignment of the flex items along the main axis of each flex line.
The align-items
property applies to all flex containers, and sets the default alignment of the flex items along the cross axis of each flex line. The align-self
applies to all flex items, allows this default alignment to be overridden for individual flex items.
The align-content
property only applies to multi-line flex containers, and aligns the flex lines within the flex container when there is extra space in the cross-axis.
Here you have a snippet to play:
var form = document.forms[0],
flex = document.getElementById('flex');
form.addEventListener('change', function() {
flex.style.flexDirection = form.elements.fd.value;
flex.style.justifyContent = form.elements.jc.value;
flex.style.alignItems = form.elements.ai.value;
flex.style.alignContent = form.elements.ac.value;
});
ul {
display: flex;
flex-flow: row wrap;
padding: 0;
list-style: none;
}
li {
padding: 0 15px;
}
label {
display: block;
}
#flex {
display: flex;
flex-wrap: wrap;
height: 240px;
width: 240px;
border: 1px solid #000;
background: yellow;
}
#flex > div {
min-width: 60px;
min-height: 60px;
border: 1px solid #000;
background: blue;
display: flex;
justify-content: center;
align-items: center;
color: #fff;
}
#flex > .big {
font-size: 1.5em;
min-width: 70px;
min-height: 70px;
}
<form>
<ul>
<li>flex-direction
<label><input type="radio" name="fd" value="row" checked /> row</label>
<label><input type="radio" name="fd" value="row-reverse" /> row-reverse</label>
<label><input type="radio" name="fd" value="column" /> column</label>
<label><input type="radio" name="fd" value="column-reverse" /> column-reverse</label>
</li>
<li>justify-content
<label><input type="radio" name="jc" value="flex-start" checked /> flex-start</label>
<label><input type="radio" name="jc" value="flex-end" /> flex-end</label>
<label><input type="radio" name="jc" value="center" /> center</label>
<label><input type="radio" name="jc" value="space-between" /> space-between</label>
<label><input type="radio" name="jc" value="space-around" /> space-around</label>
</li>
<li>align-items
<label><input type="radio" name="ai" value="flex-start" /> flex-start</label>
<label><input type="radio" name="ai" value="flex-end" /> flex-end</label>
<label><input type="radio" name="ai" value="center" /> center</label>
<label><input type="radio" name="ai" value="baseline" /> baseline</label>
<label><input type="radio" name="ai" value="stretch" checked /> stretch</label>
</li>
<li>align-content
<label><input type="radio" name="ac" value="flex-start" /> flex-start</label>
<label><input type="radio" name="ac" value="flex-end" /> flex-end</label>
<label><input type="radio" name="ac" value="center" /> center</label>
<label><input type="radio" name="ac" value="space-between" /> space-between</label>
<label><input type="radio" name="ac" value="space-around" /> space-around</label>
<label><input type="radio" name="ac" value="stretch" checked /> stretch</label>
</li>
</ul>
</form>
<div id="flex">
<div>1</div>
<div class="big">2</div>
<div>3</div>
<div>4</div>
<div class="big">5</div>
<div>6</div>
</div>
First you need to understand how the Flexible box structure works. The below image is part of the Cheatsheet.
Flexbox Structure
Flexbox was built to adapt both as a row and column.
Main-axis:
When flex-direction is row: the x-axis as on a graph. When flex-direction is column: the y-axis on a graph
Cross-axis:
When flex-direction is column: the x-axis as on a graph. When flex-direction is row: the y-axis on a graph
Justify-Content
justify-content
is used to align the items along with the main-axis.
.justify-content {
display: flex;
justify-content: center;
flex-wrap: wrap;
height: 500px;
width: 500px;
background: lightgray;
padding: 5px;
}
.box {
background: tomato;
width: 100px;
height: 100px;
margin: 10px;
}
<div class="justify-content">
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
</div>
Align-content
align-content
is used to align the items inside the flexbox along the cross-axis. Note that it applies to Multi-line containers
.align-content {
display: flex;
align-content: center;
flex-wrap: wrap;
height: 500px;
width: 500px;
background: lightgray;
padding: 5px;
}
.box {
background: tomato;
width: 100px;
height: 100px;
margin: 10px;
}
<div class="align-content">
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
</div>
Align-items
align-items
has the same functionality as align-content
but the difference is that it works to center every single-line container instead of centering the whole container. Check that in the snippet, the whole container is divided into 250 pixels height each and centered within, while in align-content
it is centered within 500 pixels height of the row.
.align-items {
display: flex;
align-items: center;
flex-wrap: wrap;
height: 500px;
width: 500px;
background: lightgray;
padding: 5px;
}
.box {
background: tomato;
width: 100px;
height: 100px;
margin: 10px;
}
<div class="align-items">
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
<div class="box"></div>
</div>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With