๐ข Update (July 1, 2025):
This article has been completely revised and upgraded with:
- Real working code examples
- 100% accurate visual diagrams for all major properties
- Deep explanations of
fr
,minmax()
,auto-fill
,auto-fit
, track alignment, and moreIf youโve seen the earlier version, I highly recommend checking it again. Itโs now a complete visual guide to mastering two-dimensional layouts with CSS Grid.
Introduction
CSS Grid is a powerful layout system that enables web developers to create complex, responsive two-dimensional layouts with ease. Introduced as a game-changer in web design, CSS Grid allows for the division of a container into rows and columns, creating a flexible grid structure that can be populated with child elements. This system not only simplifies layout creation but also enhances the readability and maintainability of the code. Unlike traditional layout methods, CSS Grid eliminates the need for deeply nested HTML and cumbersome float-based designs.
CSS Grid vs. Flexbox: Complementary Layout Tools
While both CSS Grid and Flexbox are layout models in CSS, they serve distinct purposes and are often used together in modern web design. Flexbox is ideal for one-dimensional layouts, where you need to align items in a single row or column. On the other hand, CSS Grid excels in two-dimensional layouts, where you need to manage both rows and columns simultaneously. Understanding when to use each can significantly improve the efficiency and organization of your design.
Creating a Grid Container
To start using CSS Grid, you first need to define a grid container. This is done by setting the display
property of an element to grid
:
.container { display: grid; }
Once a grid container is established, all its direct child elements automatically become grid items. These grid items can be positioned and manipulated within the grid using various CSS Grid properties.
Understanding Grid Axes
CSS Grid operates on two primary axes:
- Row Axis: Defines the horizontal placement of grid items.
- Column Axis: Defines the vertical placement of grid items.
Unlike Flexbox, where the direction of the main and cross axes can be altered (using properties like flex-direction
), the direction of the row and column axes in CSS Grid is fixed. Rows always run horizontally, and columns always run vertically.
Grid Cells: The Building Blocks of the Grid
The intersections of the grid lines form grid cells, which are the individual units of the grid. A grid cell is the space between two adjacent row lines and two adjacent column lines. Even if a grid cell isnโt filled by a grid item, it still exists within the grid structure.
Grid Lines: The Backbone of CSS Grid
Grid lines are the invisible lines that define the boundaries between rows and columns within the grid. These lines are crucial for placing grid items precisely where you want them. Grid lines are numbered sequentially, starting from 1.
.container { display: grid; grid-template-columns: 100px 100px 100px; grid-template-rows: 50px 50px; }
๐ก To make your layout more responsive, consider using flexible units like fr
and auto
instead of fixed pixel values.
The Magic of fr
: Creating Flexible Grids
The fr
unitโshort for fractionโis one of CSS Gridโs most powerful features. It allows the browser to divide available space proportionally:
grid-template-columns: 1fr 2fr 1fr;
This example creates three columns, where the middle column takes twice as much space as the others.
You can also use:
grid-template-columns: repeat(4, 1fr);
This evenly splits space into four equal parts.
The fr
unit can also be used with auto
, or inside rows if the grid container has an explicit height:
.container { height: 300px; grid-template-rows: 1fr 1fr; }
Spacing and Gaps
Use the gap
shorthand to set consistent spacing between columns and rows:
gap: 10px;
You can also use row-gap
and column-gap
separately if needed.
Grid Container with Explicit Rows and Columns
The foundation of any CSS Grid layout starts with explicitly defining the number of rows and columns in the grid container. This method provides full control over the layout structure, making it easier to manage and predict how elements will be positioned.
๐ What This Demonstrates
This example illustrates how to use grid-template-columns
and grid-template-rows
to define a grid with fixed dimensions. We also add spacing between the items using the gap
property and visually outline the grid with background and borders for clarity.
๐งฑ Complete Code
<div class="grid grid-basic"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div> <style> .grid-basic { display: grid; grid-template-columns: 100px 100px 100px; grid-template-rows: 60px 60px; gap: 10px; border: 2px solid #ccc; padding: 10px; background: #f9fafb; width: max-content; } .item { background: #4f46e5; color: white; text-align: center; font-weight: bold; line-height: 60px; } </style>
๐ Visual Breakdown
In this layout:
- There are 3 columns, each exactly 100px wide.
- There are 2 rows, each 60px high.
- A 10px gap separates all grid cells.
- The container is constrained to the content width using
width: max-content
.
๐ผ๏ธ Diagram
Flexible Grids Using fr
CSS Grid introduces the fr
unit, which stands for fraction of the remaining space. This enables the creation of flexible and responsive layouts without relying on fixed pixel values.
๐ What This Demonstrates
This example shows how the fr
unit can proportionally divide available space between columns. It allows certain columns to expand or shrink depending on their assigned fractions relative to others.
๐งฑ Complete Code
<div class="grid grid-fr"> <div class="item">1fr</div> <div class="item">2fr</div> <div class="item">1fr</div> </div> <style> .grid-fr { display: grid; grid-template-columns: 1fr 2fr 1fr; gap: 10px; width: 600px; border: 2px solid #ccc; padding: 10px; background: #f9fafb; } .item { background: #4f46e5; color: white; text-align: center; font-weight: bold; line-height: 60px; } </style>
๐ Visual Breakdown
- There are three columns.
- The first and third columns take up 1 part each of the available space.
- The second column takes up 2 parts, making it twice as wide as the others.
- The total space is divided into 4 parts, distributed as:
1fr 2fr 1fr
.
๐ผ๏ธ Diagram
Implicit Rows
When the number of grid items exceeds the defined rows or columns, CSS Grid automatically creates implicit rows to accommodate the extra content. This feature ensures layouts remain structured even when content overflows.
๐ What This Demonstrates
This layout shows how implicit rows are generated when the number of grid items goes beyond the defined grid structure. It also highlights how the items continue to flow naturally within the grid context.
๐งฑ Complete Code
<div class="grid implicit-rows"> <div class="item">A</div> <div class="item">B</div> <div class="item">C</div> <div class="item">D</div> <div class="item">E</div> <div class="item">F</div> <div class="item">G</div> </div> <style> .implicit-rows { display: grid; grid-template-columns: repeat(3, 100px); gap: 10px; background: #f9fafb; border: 2px solid #ccc; padding: 10px; width: max-content; } .item { background: #4f46e5; color: white; text-align: center; font-weight: bold; line-height: 60px; } </style>
๐ Visual Breakdown
- The grid defines only 3 columns.
- No
grid-template-rows
is explicitly declared. - As more items are added, new rows are automatically created.
- These newly created rows are implicit rows, generated by the browser to accommodate overflowing items.
๐ผ๏ธ Diagram
Item Positioning with grid-column
and grid-row
CSS Grid provides precise control over where each grid item should be placed. You can define a grid itemโs exact position within the layout by specifying the grid lines it should start and end on using grid-column
and grid-row
.
๐ What This Demonstrates
This example showcases how to manually position items within a grid using grid-column
and grid-row
, including spanning across multiple columns or rows. This gives you total layout freedom, allowing items to break out of the normal grid flow.
๐งฑ Complete Code
<div class="grid position-demo"> <div class="item a">A</div> <div class="item b">B</div> <div class="item c">C</div> </div> <style> .position-demo { display: grid; grid-template-columns: repeat(4, 1fr); grid-template-rows: repeat(2, 80px); gap: 10px; width: 600px; background: #f9fafb; border: 2px solid #ccc; padding: 10px; } .item { background: #0ea5e9; color: #083549; text-align: center; font-weight: bold; line-height: 80px; } .a { grid-column: 1 / 3; /* spans columns 1 and 2 */ } .b { grid-column: 3 / 5; /* spans columns 3 and 4 */ grid-row: 1 / 3; /* spans both rows */ } .c { grid-column: 2 / 4; /* spans columns 2 and 3 */ grid-row: 2; /* placed in the second row */ } </style>
๐ Visual Breakdown
- Item A spans two columns (
1 / 3
) on the first row. - Item B spans two columns (
3 / 5
) and also spans two rows vertically (1 / 3
). - Item C is placed on the second row, spanning two columns (
2 / 4
).
This shows how grid items can overlap vertically or horizontally, and how custom placement enhances layout control.
๐ผ๏ธ Diagram
Alignment Within Items
CSS Grid allows not only for aligning entire rows or columns but also for aligning the content inside individual grid cells. This is done using justify-self
and align-self
.
๐ What This Demonstrates
This example highlights how to control the alignment of individual items inside a grid cell, independently from other cells. This is useful for centering, stretching, or pinning content inside each grid area.
๐งฑ Complete Code
<div class="grid alignment"> <div class="item">Aligned</div> <div class="item">Aligned</div> </div> <style> .alignment { display: grid; grid-template-columns: 150px 150px; grid-template-rows: 150px; border: 2px dashed #999; justify-items: start; align-items: end; background: #f9fafb; padding: 10px; } .item { background: #f97316; color: white; font-weight: bold; padding: 10px; } </style>
๐ Visual Breakdown
- The grid has two cells, each measuring 150px by 150px.
-
justify-items: start
aligns each item to the left inside its cell. -
align-items: end
aligns each item to the bottom vertically. - This configuration allows fine-grained control over where the content appears within its space.
๐ผ๏ธ Diagram
Track Alignment (Container-Level Alignment)
Beyond aligning individual items, CSS Grid also enables alignment of entire rows and columns within the grid container. This is controlled by justify-content
and align-content
.
๐ What This Demonstrates
This example demonstrates how to align the full collection of grid tracksโboth horizontally and verticallyโusing justify-content
and align-content
. This is especially useful when the grid container is larger than the combined size of its tracks.
๐งฑ Complete Code
<div class="grid track-align"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> </div> <style> .track-align { display: grid; grid-template-columns: repeat(2, 100px); grid-template-rows: repeat(2, 100px); justify-content: space-evenly; align-content: space-between; height: 300px; border: 2px solid #ccc; background: #f9fafb; padding: 10px; } .item { background: #10b981; color: white; font-weight: bold; text-align: center; line-height: 100px; } </style>
๐ Visual Breakdown
- The grid defines 2 columns and 2 rows, each 100px in size.
-
justify-content: space-evenly
horizontally distributes the entire set of columns with equal space before, between, and after them. -
align-content: space-between
vertically spreads the rows so the first row touches the top and the last row touches the bottom, with even spacing in between. - The total grid size (200ร200px) is smaller than the container size (300px tall), so alignment is clearly visible.
๐ผ๏ธ Diagram
Named Grid Areas
CSS Grid provides a powerful feature known as grid template areas, which allows you to assign semantic names to regions of the grid. This method improves readability, reduces complexity, and makes layout structures easier to visualize and maintain.
๐ What This Demonstrates
This example illustrates how to define and use named grid areas to create a clear and semantically meaningful layout. Each part of the layoutโheader, sidebar, main content, and footerโis assigned to a named area.
๐งฑ Complete Code
<div class="container area-layout"> <div class="header">Header</div> <div class="sidebar">Sidebar</div> <div class="main">Main Content</div> <div class="footer">Footer</div> </div> <style> .area-layout { display: grid; grid-template-columns: 1fr 3fr; grid-template-rows: 60px 1fr 40px; grid-template-areas: "header header" "sidebar main" "footer footer"; height: 300px; gap: 10px; padding: 10px; border: 2px solid #ccc; background: #f9fafb; } .header { grid-area: header; background: #4f46e5; color: white; font-weight: bold; text-align: center; line-height: 60px; } .sidebar { grid-area: sidebar; background: #0ea5e9; color: white; text-align: center; line-height: 100%; padding: 20px; } .main { grid-area: main; background: #10b981; color: white; text-align: center; padding: 20px; } .footer { grid-area: footer; background: #f97316; color: white; font-weight: bold; text-align: center; line-height: 40px; } </style>
๐ Visual Breakdown
- The grid has 2 columns: the left column (
1fr
) and the right column (3fr
). - The rows are defined as
60px
,1fr
, and40px
respectively. - Each grid area is given a name, making the layout declaration more semantic and easier to understand.
- The header and footer span across both columns, while the sidebar and main content occupy their respective sides in the middle row.
This type of layout is highly readable and especially helpful for larger, structured designs such as dashboards or multi-pane interfaces.
๐ผ๏ธ Diagram
minmax(): Defining Flexible Column Sizes
The minmax()
function is an essential feature in CSS Grid for creating responsive layouts. It defines a column (or row) that grows and shrinks between a minimum and maximum size based on available space.
๐ What This Demonstrates
This section demonstrates how to define columns that are never smaller than a minimum size but can expand proportionally to fill the space as needed. This method ensures flexibility while preserving usability on smaller screens.
๐งฑ Complete Code
<div class="grid minmax-grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> </div> <style> .minmax-grid { display: grid; grid-template-columns: minmax(150px, 1fr) minmax(150px, 1fr) minmax(150px, 1fr); gap: 10px; border: 2px solid #ccc; width: 100%; max-width: 900px; margin-bottom: 2rem; background: #f9fafb; padding: 10px; } .item { background: #4f46e5; color: white; text-align: center; padding: 20px; font-weight: bold; } </style>
๐ Visual Breakdown
- Each column is set to a minimum width of 150px.
- The maximum width is set to 1fr, which means it can grow to fill the remaining space proportionally.
- The layout is highly responsive and adjusts based on the screen width without breaking.
This approach is particularly effective when creating cards, lists, or dynamic columns that must remain readable even on narrow viewports.
๐ผ๏ธ Diagram
auto-fill vs. auto-fit: Responsive Grids Without Media Queries
One of the most powerful features of CSS Grid is the ability to create responsive column layouts without writing a single media query. This is made possible using the functions auto-fill
and auto-fit
in combination with repeat()
and minmax()
.
These two keywords look similar but behave differently when handling empty space and unused grid tracks.
๐น 1. Using auto-fill
๐ What This Demonstrates
This example illustrates how auto-fill
works by automatically fitting as many columns as possible into a row. If there is leftover space and fewer items than columns that could be displayed, auto-fill
will leave the remaining columns as empty tracks, keeping the layout structure intact. This can be useful when you want to maintain a consistent grid layout, even if some content is missing.
๐งฑ Complete Code
<div class="grid autofill-grid"> <div class="item">A</div> <div class="item">B</div> <div class="item">C</div> </div> <style> .autofill-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 15px; width: 100%; max-width: 900px; padding: 10px; background: #f9fafb; } .item { background: #0ea5e9; color: white; text-align: center; padding: 20px; font-weight: bold; } </style>
๐ Visual Breakdown
- The
minmax(150px, 1fr)
ensures each column will never shrink below 150px. -
auto-fill
determines how many such columns can fit within the container. - When there are fewer items than columns that can fit,
auto-fill
leaves those extra columns as empty tracks. - These empty tracks remain part of the grid, maintaining structure but appearing blank.
๐ผ๏ธ Diagrams
Wide screen (max-width: 900px
)
Medium screen (max-width: 450px
)
Narrow screen (max-width: 200px
)
๐ก Clarification: On medium and narrow screens, the layout behaves the same as
auto-fit
because the grid has no spare space left for empty tracks. The difference becomes visually apparent only on wider containers when fewer items are present.
๐น 2. Using auto-fit
๐ What This Demonstrates
This example is nearly identical to the auto-fill
layout, except that it uses auto-fit
. While both calculate how many columns fit into the available space, auto-fit
behaves differently when there are fewer items than columns. It will collapse the empty tracks, allowing the existing items to stretch and occupy all available space.
This makes auto-fit
especially useful when you want the layout to be compact and dynamic, without preserving blank slots.
๐งฑ Complete Code
<div class="grid autofit-grid"> <div class="item">A</div> <div class="item">B</div> <div class="item">C</div> </div> <style> .autofit-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 15px; width: 100%; max-width: 900px; padding: 10px; background: #f9fafb; } .item { background: #10b981; color: white; text-align: center; padding: 20px; font-weight: bold; } </style>
๐ Visual Breakdown
- Uses the same
minmax(150px, 1fr)
logic asauto-fill
. - However, if there is extra space and not enough items,
auto-fit
collapses the unused columns. - Existing items stretch to fill the newly available space.
- This gives a cleaner, tighter layout especially in responsive scenarios.
๐ผ๏ธ Diagrams
Wide screen (max-width: 900px
)
Medium screen (max-width: 450px
)
Narrow screen (max-width: 200px
)
๐ก Clarification: On medium and narrow screens,
auto-fill
andauto-fit
appear the same because no unused columns exist. But on wider screens,auto-fit
collapses unused columns, whileauto-fill
keeps them as empty space.
Summary Table: Comparing minmax()
, auto-fill
, and auto-fit
Concept | Behavior Explained | Ideal Use Case |
---|---|---|
minmax() | Sets a minimum size that never shrinks and a maximum size that flexes | Prevents layout breakage while maintaining flexibility |
auto-fill | Fills available row space with as many columns as possible, leaving empty tracks | Keeps structure even when items are missing |
auto-fit | Fits as many columns as possible, collapsing empty columns to reclaim space | Expands content naturally by removing unused tracks |
Common Properties Applied to the Grid Container
The grid container is the foundation of any CSS Grid layout. It controls the overall structure by defining rows, columns, spacing, and alignment rules. Below is a visual reference summarizing the most commonly used grid container properties:
Property | Description |
---|---|
display: grid | Turns an element into a grid container |
grid-template-columns | Defines the columns of the grid (number, width, and sizing) |
grid-template-rows | Defines the rows of the grid |
grid-template-areas | Defines named areas in the grid |
grid-auto-columns | Sets size for implicitly created columns |
grid-auto-rows | Sets size for implicitly created rows |
grid-auto-flow | Controls how items are auto-placed (row , column , dense ) |
gap / row-gap / column-gap | Sets spacing between rows and columns |
justify-items | Aligns grid items horizontally within their cells |
align-items | Aligns grid items vertically within their cells |
justify-content | Aligns entire grid horizontally within the container |
align-content | Aligns entire grid vertically within the container |
Common Properties Applied to the Grid Items
Each grid item can be individually positioned and aligned within the grid using a set of powerful properties. These let you control how a specific item behaves within its assigned cell or how it spans across multiple rows or columns. Hereโs a visual overview of the key properties you can apply to grid items:
Property | Description |
---|---|
grid-column | Defines on which column lines the item starts and ends |
grid-row | Defines on which row lines the item starts and ends |
grid-area | Assigns the item to a named grid area |
justify-self | Aligns the item horizontally within its grid cell |
align-self | Aligns the item vertically within its grid cell |
place-self | Shorthand for setting both justify-self and align-self |
z-index | Controls stacking order of grid items |
order | Controls visual order (rarely used in Grid, more common in Flexbox) |
margin | Useful for spacing or alignment tweaks (e.g. margin: auto ) |
Conclusion
CSS Grid has fundamentally changed the way we approach web layout. Unlike previous techniques that relied heavily on floats, positioning hacks, or deeply nested flex containers, CSS Grid offers a native, two-dimensional layout system that is both intuitive and powerful. It allows developers to define precise layouts with rows and columns, place elements exactly where they should go, and create responsive interfaces that adapt beautifully to different screen sizesโall without media queries in many cases.
By understanding the core concepts of CSS Gridโsuch as explicit and implicit tracks, grid lines, named areas, alignment options, and flexible sizing with units like fr
and functions like minmax()
โyou gain the ability to design interfaces that are not only functional but also structurally elegant.
This guide has covered:
- The foundational setup for grid containers
- Defining fixed and flexible columns using
fr
units - How implicit rows behave when content overflows
- Manual item placement using
grid-column
andgrid-row
- Aligning individual items versus aligning entire tracks
- Named areas for semantic, readable layouts
- Responsive design patterns using
auto-fill
andauto-fit
When used thoughtfully, CSS Grid makes it possible to craft layouts that were previously complex or even impossible using only Flexbox. It encourages a structured, modular approach to web design and empowers developers to focus on layout intent rather than implementation workarounds.
Whether you are building landing pages, dashboards, component libraries, or entire application layouts, mastering CSS Grid gives you a level of control and clarity that elevates both your development workflow and your users' experience.
This article is intended to be a complete and lasting reference. With each example paired with visual diagrams and explanation, you now have a resource that you can return to whenever you're planning or debugging grid-based layouts.
๐ฌ Letโs Connect
๐ Portfolio: paulanik.com
๐ผ LinkedIn: Anik Paul
๐ GitHub: anikpaul99
๐ฉ Email: hello@paulanik.com
Top comments (1)
๐ Update Notice (July 1, 2025):
Thanks to everyone who read the original version of this guide!
Iโve just published a major update with:
โ Fully working code examples
โ Real screenshots for every core concept and layout behavior
โ Deep breakdowns of
fr
,minmax()
,auto-fill
,auto-fit
, track alignment, grid areas, and moreThe article is now a comprehensive and visual reference for understanding CSS Grid from beginner to advanced.
๐ Iโd love to know what you think of the updated version!