Does CSS Grid Replace Flexbox?

Avatar of Robin Rendle
Robin Rendle on (Updated on )

📣 Freelancers, Developers, and Part-Time Agency Owners: Kickstart Your Own Digital Agency with UACADEMY Launch by UGURUS 📣

No. Well. Mostly No.

Grid is much newer than Flexbox and has a bit less browser support. That’s why it makes perfect sense if people are wondering if CSS grid is here to replace Flexbox.

To put a point on it:

  1. Grid can do things Flexbox can’t do.
  2. Flexbox can do things Grid can’t do.
  3. They can work together: a grid item can be a flexbox container. A flex item can be a grid container.

Even though Grid is pretty new, we have lots of articles about it, including a getting started article, an article about a basic layout done multiple ways, and a complete guide.

If you hadn’t heard the trumpets blaring, March 2017 was the banner month for Grid. It was released, completely unprefixed and ready-to-go, in Chrome, Opera, Firefox, and Safari. Even Edge supports it, albeit an older version of the spec, which you can get some support for by using Autoprefixer.

So.

Does Grid replace Flexbox?

It seems a little complicated at first. Especially if you’re just starting to get a grip on the weird, alien syntax of Flexbox. Now there is a whole other syntax to learn? Sheesh.

Here’s some things Grid is specifically better at than Flexbox:

  • Making whole page layouts. It’s better for that even just considering layout performance reasons.
  • Making literal grids. Like X columns with Y gap between them homegrown framework stuff. grid-gap is wonderful, as gutters are the main pain point of grid systems.
  • Requiring less media query intervention with really powerful functionality like auto layout, minmax(), repeat(), and auto-fill. Here’s a neat idea.

And another huge one: Grid can position elements in 2 dimensions. Both columns and rows. That’s a first. Rachel Andrew once made that very clear:

Flexbox is essentially for laying out items in a single dimension – in a row OR a column. Grid is for layout of items in two dimensions – rows AND columns.

Let’s see some demos.

Say we’re building a horizontal navigation component — that’s the perfect use case for Flexbox because it sets content in only one direction. In Chris’ demo below you can mess around with those properties and see just how powerful Flexbox is:

See the Pen Bar Navigation with Flexbox and SVG icons by Chris Coyier (@chriscoyier) on CodePen.

But there are some instances where those flexbox properties, such as justify-content or align-items, should be used in conjunction with Grid properties. Take this demo for instance:

See the Pen Flexbox and Grid  – First demo by Robin Rendle (@robinrendle) on CodePen.

First we’ve made a .wrapper that is set to display: flex;. That way we can set a max-width on our .grid and use justify-content: center; to place it in the middle of the viewport. Then we can make our grid with the right number of columns:

.wrapper {
  display: flex;
  justify-content: center;
}

.grid {
  display: grid;
  max-width: 800px;
  grid-template-columns: 1fr 2fr;
}

That’s just the first step.

Now let’s make that .ad take up the whole row of our grid. Well, we can do that by specifically targeting our

without messing up the rest of the children of our grid:

.ad {
  grid-column-start: 1;
  grid-column-end: 3;
}

What we’re saying with the code above is “start this div on the first column and end on the very last column.” That should look something like this:

See the Pen Flexbox and Grid by Robin Rendle (@robinrendle) on CodePen.

Further, let’s say that we always wanted our ad block to be twice the size of our first row – we can totally do that! We just need to use the grid-template-rows property:

.grid {
  display: grid;
  max-width: 800px;
  grid-template-columns: 1fr 2fr;
  grid-template-rows: 1fr 2fr 1fr;
}

That’s the equivalent of saying: “there are three rows in our grid. Always make sure that the second row is twice the size of the first and third.” In other words, we’re creating relationships between rows and other rows whilst also defining the number of columns in our grid!

See the Pen Flexbox and Grid by Robin Rendle (@robinrendle) on CodePen.

With CSS Grid we can set relationships horizontally (with grid-template-columns) and vertically (with grid-template-rows) but at the same time. Flexbox, on the other hand, is stuck doing either vertical or horizontal layouts (with flex-direction) – but that doesn’t mean we should ditch it.

Potentially Confusing: a “2D” Layout with Flexbox

What can get a little confusing is that it’s not impossible to make multi-dimensional layouts in just Flexbox. For example:

See the Pen A “Grid” with Flexbox by Chris Coyier (@chriscoyier) on CodePen.

There are certainly rows and columns there, even a final element that spans multiple columns. It’s easy to build and flexible. It’s done through allowing flex-wrap on the container, having the children’s flex-basis be 1/3 of the width of the container, and allowing flex-grow to stretch children if need by. (The flex property is shorthand for flex-grow, flex-shrink, and flex-basis.)

It’s not wrong, it’s just one way of doing something like this, and you could probably make an argument for it being less intuitive and adaptable.

Potentially Confusing: a “1D” Layout with Grid

Grid can do 2D layout, meaning defining both grid-template-rows and grid-template-columns, but it doesn’t have to use both. Here’s a demo of using it just to lay boxes in a horizontal row:

See the Pen Easy Columns with Grid by Chris Coyier (@chriscoyier) on CodePen.

This isn’t wrong either. In fact, you could easily make the argument that this is easier to understand and more succinctly expressed than doing it with flexbox. For example, no layout properties are needed on the child elements at all. But you could also argue that purely 1D layout like this is more powerful in Flexbox, because Flexbox allows us to move those elements around easier (e.g. move them all to one side or another, change their order, space them out evenly, etc).

About That Nesting

One more time to lock it in!

This is good to remember: grid items can be flex parents.

See the Pen Easy Columns with Grid by Chris Coyier (@chriscoyier) on CodePen.

And, flex items can be grid parents:

See the Pen Easy Columns with Grid by Chris Coyier (@chriscoyier) on CodePen.