Flexbox vs Grid
Flexbox lays out items along one dimension and sizes to their content. Grid defines a two-dimensional grid of rows and columns that you place items into.
Side-by-side comparison
#Number of dimensions
Starting point
Placing items
Spacing between items
Aligning on both axes at once
Typical use
Example
#.flex-row {
display: flex;
gap: 8px;
}
.grid-area {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 8px;
}<p style="margin: 0 0 6px; color: #a1a1aa;">Flexbox: a row</p>
<div class="flex-row stage">
<div class="box">1</div><div class="box">2</div><div class="box">3</div>
</div>
<p style="margin: 10px 0 6px; color: #a1a1aa;">Grid: a 3-column grid</p>
<div class="grid-area stage">
<div class="box">1</div><div class="box">2</div><div class="box">3</div>
<div class="box">4</div><div class="box">5</div><div class="box">6</div>
</div>Definition and usage
#Both technologies replaced the old tricks with float and tables, but they solve a different problem. Flexbox works along a single axis, a row or a column, and lays out items according to their natural size. Grid thinks in two dimensions from the start: you first draw a grid of rows and columns, then place items into it, even in a way that makes them overlap.
In practice, Flexbox works well where you have an unknown number of items that should flow one after another: a menu, a list of tags, a row of buttons. Grid wins when you know the layout up front: an entire page with a header, a sidebar and content, or a grid of cards with equal columns and rows.
Nothing stops you from using both at once. A common pattern is Grid for the whole page and Flexbox inside a single card, where all that matters is one row with an icon and some text.
Syntax
#.flex { display: flex; flex-direction: row | column; }
.grid { display: grid; grid-template-columns: ...; grid-template-rows: ...; }More examples
#.toolbar {
display: flex;
flex-wrap: wrap;
gap: 8px;
}<div class="toolbar stage" style="width: 220px;">
<span class="box">HTML</span><span class="box">CSS</span><span class="box">JavaScript</span>
<span class="box">TypeScript</span><span class="box">Python</span>
</div>Narrow the preview window: the items move to the next line on their own. Grid would require you to define how many columns the grid should fit.
.layout {
display: grid;
grid-template-columns: 120px 1fr;
grid-template-areas:
"header header"
"menu content";
gap: 8px;
}
.layout header { grid-area: header; }
.layout nav { grid-area: menu; }
.layout main { grid-area: content; }<div class="layout stage">
<header class="box" style="grid-area: header">CodeWorlds</header>
<nav class="box" style="grid-area: menu">Menu</nav>
<main class="box" style="grid-area: content">Lesson 6: Flexbox vs Grid</main>
</div>A two-dimensional layout like this (a full-width header, a sidebar and content) would require nesting several containers in Flexbox.
Good practices
#- Ask yourself: am I laying out a single row of items, or a whole grid in two dimensions? The answer points to the right tool.
- A single-column Grid (
grid-template-columns: 1fr) behaves almost like a column Flexbox. In simple cases, the difference is cosmetic. - Combine both technologies: Grid for the page layout, Flexbox inside a single component.
Related entries
#- flexA shorthand that sets an item’s flex-grow, flex-shrink, and flex-basis.
- grid-template-columnsDefines the grid’s columns: their number and widths.
- displayDetermines how an element behaves in the page layout and how it lays out its children.
- gapSets the spacing between items in a flex, grid, or multi-column container.
- place-itemsA shorthand that sets align-items and justify-items at the same time.
Spotted a mistake or missing an example? Write to us.