← Back to the Flexbox Playground
Lesson

Flexbox, Visually

Flexbox is the tool for laying out items in a single row or column — navbars, button rows, centering, sidebars. This lesson teaches every core property with controls you can click to watch the layout respond in real time.

Step 1

Container, items & the two axes

Flexbox has two players: a flex container (the parent you put display: flex on) and its flex items (the direct children). Everything you do is either a container property or an item property.

The key mental model is the two axes. The main axis runs in the direction items flow (a row, by default). The cross axis runs perpendicular to it. justify-content works along the main axis; align-items works along the cross axis.

1
2
3
Remember: “justify” = main axis (usually horizontal), “align” = cross axis (usually vertical). Flip flex-direction to column and the two axes swap.
Step 2

Turning it on: display: flex

A plain div full of children stacks them vertically. Add one line to the parent and they snap into a row:

.row { display: flex; }   children now sit side by side
display: flex — that's it
1
2
3
That single declaration already does a lot: items sit in a row, shrink to fit, and stretch to equal height. The rest of this lesson is about controlling that default.
Step 3

flex-direction: row or column

flex-direction sets the main axis. row (default) flows left-to-right; column flows top-to-bottom. Click to flip it:

flex-direction: row
1
2
3
Watch the axis swap. In column mode, justify-content now controls vertical spacing and align-items controls horizontal — because the main axis turned vertical.
Step 4

justify-content (main axis)

This distributes items along the main axis — packing them or spreading the free space between them. Click each value:

justify-content: flex-start
1
2
3
space-between is the navbar classic (logo left, links right). center centers a group. The three space-* values differ only in the edge gaps.
Step 5

align-items (cross axis)

This aligns items across the main axis — vertically, in a row. The container is taller here so you can see it work. Click each value:

align-items: stretch
1
2
3
Centering anything is just justify-content: center + align-items: center — dead center on both axes, the answer to the web's oldest question.
Step 6

gap: spacing without margins

Old flexbox layouts used margins on every child (and fiddly “remove the last margin” hacks). gap replaces all that — one property, even spacing between items, none on the edges.

.row { display: flex; gap: 16px; }
Use gap as your default for spacing flex (and grid) children. It's cleaner than margins and never leaves a stray gap at the start or end.
Step 7

flex-wrap: let items break to new lines

By default flex items refuse to wrap — they squish to fit one line. flex-wrap: wrap lets them flow onto new lines when they run out of room, which is essential for responsive rows of cards. Toggle it (six cards that overflow one line):

flex-wrap: nowrap
card 1
card 2
card 3
card 4
card 5
card 6
Shorthand flex-flow: row wrap sets direction and wrap together. A wrapping flex row is the simplest responsive card layout you can write.
Step 8

Sizing items: grow, shrink, basis

Those were container properties. Now the items: how do they share space? The flex shorthand on each item bundles three things:

PartMeans
flex-growHow much of the leftover space this item takes (0 = none).
flex-shrinkHow willingly it shrinks when space is tight (1 = yes).
flex-basisIts starting size before grow/shrink (often auto or a width).

Click to change how item 2 grows relative to its siblings:

item 2 → flex: 1
1
2
3
.sidebar { flex: 0 0 240px; }  don't grow/shrink, fixed 240px
.main    { flex: 1; }         take all remaining space
flex: 1 on every item makes them equal width and fill the row — the quickest way to split a row into equal columns. Mix a fixed item with a flex: 1 one to get a sidebar + flexible main.
Step 9

Five patterns you'll use constantly

Navbar: logo left, links right

.nav { display: flex; justify-content: space-between; align-items: center; }

Perfect centering

.center { display: flex; justify-content: center; align-items: center; min-height: 100vh; }

Sidebar + flexible main

.layout { display: flex; gap: 24px; }
.layout .side { flex: 0 0 240px; }
.layout .main { flex: 1; }

Equal-width columns

.cols { display: flex; gap: 16px; }
.cols > * { flex: 1; }

Push one item to the end

.bar .last { margin-left: auto; }  auto margin eats the free space
Step 10

Flexbox cheat sheet

Where next

Keep going