Grid Layout finally gives us the ability to define grids in CSS and place items into grid cells. This on its own is great, but the fact that we don’t have to specify each track and we don’t have to place every item manually makes the new module even better. Grids are flexible enough to adapt to their items.
This is all handled by the so called explicit and implicit grid.
All code samples in this post are accompanied by images in order to display grid lines and tracks. If you want to tinker with the code yourself, I recommend you download Firefox Nightly because it currently has the best DevTools to debug grids.
Explicit Grids
We can define a fixed number of lines and tracks that form a grid by using the properties grid-template-rows
, grid-template-columns
, and grid-template-areas
. This manually defined grid is called the explicit grid.
.grid {
display: grid;
grid-template-columns: 1fr 1fr 1fr 1fr;
grid-template-rows: 100px 100px;
grid-gap: 20px;
}
Repeating tracks
When we define grid-template-columns: 1fr 1fr 1fr 1fr;
we get four vertical tracks each with a width of 1fr
. We can automate that by using the repeat()
notation like so grid-template-columns: repeat(4, 1fr);
. The first argument specifies the number of repetitions, the second a track list, which is repeated that number of times.
A track list? Yes, you can actually repeat multiple tracks.
Automatic repetition of tracks
The repeat notation is quite useful, but it can be automated even further. Instead of setting a fixed number of repetitions we can use the auto-fill
and auto-fit
keywords.
Auto-filling tracks
The auto-fill
keyword creates as many tracks as fit into the grid container without causing the grid to overflow it.
.grid {
display: grid;
grid-template-columns: repeat(auto-fill, 100px);
grid-gap: 20px;
}
Note that repeat(auto-fill, 1fr);
will only create one track because a single track with a width of is an invalid declaration (maybe it changed? I dunno).1fr
already fills the whole grid container
Auto-fitting tracks
The auto-fit
keyword behaves the same way as auto-fill
, except that after grid item placement it will only create as many tracks as needed and any empty repeated track collapses.
.grid {
display: grid;
grid-template-columns: repeat(auto-fit, 100px);
grid-gap: 20px;
}
In the example used in this section the grid will look the same with repeat(auto-fit, 100px);
and repeat(4, 100px);
. The difference is visible when there are more than 4 grid items.
If there are more items, auto-fit
creates more columns.
On the other hand, if a fixed number of vertical tracks is used in the repeat notation and the number of items exceeds this value more rows are added. You can read more about that in the next section: implicit grids.
I’ve used grid-template-columns
in the above examples out of convenience, but all rules also apply to grid-template-rows
.
.grid {
display: grid;
grid-template-columns: repeat(auto-fill, 100px);
grid-template-rows: repeat(auto-fill, 100px);
grid-gap: 20px;
height: 100%;
}
html, body {
height: 100%;
}
Implicit Grids
If there are more grid items than cells in the grid or when a grid item is placed outside of the explicit grid, the grid container automatically generates grid tracks by adding grid lines to the grid. The explicit grid together with these additional implicit tracks and lines forms the so called implicit grid.
.item:first-child {
grid-column-start: -1;
}
.item:nth-child(2) {
grid-row-start: 4;
}
The widths and heights of the implicit tracks are set automatically. They are only big enough to fit the placed grid items, but it’s possible to change this default behavior.
Sizing implicit tracks
The grid-auto-rows
and grid-auto-columns
properties give us control over the size of implicit tracks.
.grid {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: 100px 100px;
grid-gap: 20px;
grid-auto-columns: 200px;
grid-auto-rows: 60px;
}
Implicit tracks will now always have a width of 200px
and a height of 60px
, no matter if the grid item fits or not.
You can make sized implicit tracks more flexible by specifying a range using the minmax()
notation.
.grid {
grid-auto-columns: minmax(200px, auto);
grid-auto-rows: minmax(60px, auto);
}
Implicit tracks are now at least 200px wide and 60px high, but will expand if the content demands it.
Extending the grid to the start
Implicit tracks may not just be added to the end of the explicit grid. It may also happen that the explicit grid needs to be extended to the start.
.item:first-child {
grid-row-end: 2;
grid-row-start: span 2;
}
.item:nth-child(2) {
grid-column-end: 2;
grid-column-start: span 2;
}
Each item ends on the second line and spans 2 cells (one vertically, the other horizontally). Since there is only one cell before the second line respectively another implicit track is added to the grid at the start of each side.
Automatic Placement
As already mentioned, implicit tracks are also added if the number of items exceeds the number of cells. By default, the auto-placement algorithm places items by filling each row consecutively, adding new rows as necessary. We can specify how auto-placed items get flowed into the grid by using the grid-auto-flow
property.
.grid {
display: grid;
grid-template-columns: repeat(4, 1fr);
grid-template-rows: 100px 100px;
grid-gap: 20px;
grid-auto-flow: column;
}
Instead of rows, columns are being filled with items and additional implicit columns are created.
Not defining an explicit grid
Due to the fact that it’s possible to automatically size cells using grid-auto-rows
and grid-auto-columns
it’s not obligatory to define an explicit grid.
.grid {
display: grid;
grid-auto-columns: minmax(60px, 200px);
grid-auto-rows: 60px;
grid-gap: 20px;
}
.item:first-child {
grid-row: span 2;
}
.item:nth-child(2) {
grid-column: 1 / span 2;
}
.item:nth-child(5) {
grid-column: 3;
}
Relying solely on the implicit grid can get confusing and difficult to understand in combination with explicit placement. In this example the first item is placed auto
and spans 2 rows, the second item is placed explicitly in the first column and spans 2 columns creating a second vertical track. The third and fourth item would actually both be placed automatically in the fourth row, but the fifth item is placed explicitly in the previously non-existent third column. This creates a third vertical track and due to Grids auto-placement, the third item moves up a row to fill the space.
Conclusion
This article doesn’t cover everything there is to know about the explicit and implicit grid, but it should give you more than a solid understanding of the concept. Knowing why and how implicit lines and tracks a created is vital for working with Grid Layout.
You can find all the examples used in this article in a Collection on CodePen.
If you want to learn more about Grids check out The Complete Guide to Grid, Getting Started with CSS Grid, Grid By Example and A Collection of Interesting Facts about CSS Grid Layout.
Thanks for the article! It just helped me with my little experiment.
I’m amazed how powerful grid is.
Cool! I’m glad it helped :)
Managing grids inside sections help content management more efficiently.
Grid is great! Now I just have to convince my friends to use it.
Thanks Manuel! Very to the point article on Grids difference. Now we can toss that Twitter Boot Strap out the window lol! I never used it though, made my own grid like 6 years ago. Finally HTML is being able to grow up via browsers discrimination!!! I Hope :)
Thanks for the nice feedback. Try it, it’s fun :)