From flow to flexbox: display: flex

Free preview 3 min to read

Three things normal flow struggles with

The last course covered normal flow: block boxes stacking and inline boxes flowing with text. It's good at both jobs. But three very common layout requests have no clean answer in normal flow. "Put these three items in a row, evenly spaced." "Center this box horizontally and vertically." "Make every card in this row the same height." Normal flow answers them with hacks like floats, negative margins and guesswork. Flexbox was built to close that gap.

Turning it on: display: flex

One declaration switches a container into flexbox layout:

.row {
  display: flex;
}
<div class="row">
  <div>One</div>
  <div>Two</div>
  <div>Three</div>
</div>

With no other CSS, those three <div>s, normally stacked one per line, snap into a horizontal row, each as wide as its content. display: flex swaps the layout algorithm for the container's direct children, from normal flow's stacking rules to flexbox's row-and-alignment rules.

Container and items: two different roles

Flexbox has two roles, and every property in this course applies to one of them. The element with display: flex is the flex container. Its direct children, and only those, are flex items.

<div class="row">        <!-- flex container -->
  <div>One</div>          <!-- flex item -->
  <div>Two</div>          <!-- flex item -->
  <div>
    <p>Nested, not a flex item</p>   <!-- normal flow still applies here -->
  </div>
</div>

The nested <p>, two levels deep, isn't a flex item. It follows normal flow, as the last course taught. Flexbox reaches only the container's immediate children.

Two axes worth naming

Flexbox arranges items along a main axis, and the perpendicular direction is the cross axis. By default the main axis runs left to right and the cross axis top to bottom, matching the row in the first example.

flowchart LR
  subgraph C["flex container — items flow along the main axis (left to right by default)"]
    direction LR
    I1["item"] --- I2["item"] --- I3["item"]
  end

justify-content positions items along the main axis, and align-items positions them along the cross axis. Every value in this course belongs to one of those two.

Turning the row into a column, which changes where the main axis points, is left to the next course in this series. Here the axes keep their default orientation so the alignment properties get your full attention.

Normal flow rules get suspended for flex items

Once an element becomes a flex item, some normal-flow behavior stops applying to it. The CSS box model course noted that margins never collapse between flex children. That's because margin collapsing is a normal-flow rule. Floats don't affect flex items either. Flexbox is its own layout mode with its own rules.

What this course covers

  • Lesson 1, From flow to flexbox: turning on display: flex, and the container/item, main-axis/cross-axis vocabulary (you are here)
  • Lesson 2, justify-content: positioning items along the main axis
  • Lesson 3, align-items: positioning items along the cross axis
  • Lesson 4, Centering with flexbox: solving the classic "center this both ways" problem in two lines
  • Lesson 5, align-self: overriding one item's cross-axis alignment individually
  • Lesson 6, gap: clean spacing between items, no margin hacks required
  • Lesson 7, Putting it together: a navbar and a centered overlay, built with everything above

By the end, the three requests that opened this lesson (a row, perfect centering, alignment without guesswork) will each take a handful of declarations.

Lesson 1 of 7 · free

Keep going with lesson 2

justify-content: positioning along the main axis

Shows how justify-content places items on the main axis using six values, from flex-start to space-evenly.

A free account also gives you the quizzes, your progress and notes, and the discussion.

Type to start searching...