CSS Grid Patterns
The Problem
CSS Grid is the most powerful layout system in CSS, but AI agents often underutilize it or apply it incorrectly. Common mistakes include confusing auto-fill with auto-fit, using fixed column counts instead of responsive patterns, avoiding grid-template-areas when it would dramatically improve readability, and reaching for JavaScript or media queries when minmax() handles responsiveness natively.
The Solution
CSS Grid is a two-dimensional layout system. Use it for page-level layouts, responsive card grids, and any scenario where items need to align across both rows and columns. The combination of auto-fill/auto-fit with minmax() enables responsive layouts without a single media query.
Code Examples
auto-fill vs auto-fit
The difference matters when there are fewer items than the grid can fit.
/* auto-fill: keeps empty tracks, preserving the grid structure */
.grid-fill {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
gap: 1rem;
}
/* auto-fit: collapses empty tracks, items stretch to fill space */
.grid-fit {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 1rem;
}
When 3 items are in a container wide enough for 5 columns:
auto-fillcreates 5 columns, 2 remain empty. Items stay at 200px-ish width.auto-fitcollapses the 2 empty columns. Items stretch to fill the full width.
Use auto-fit for card grids, gallery layouts, and most UI patterns where items should expand to use available space.
Use auto-fill when you want to maintain consistent column widths regardless of item count, such as form fields or data entry layouts.
Responsive Card Grid (No Media Queries)
.card-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(min(100%, 300px), 1fr));
gap: 1.5rem;
}
<div class="card-grid">
<article class="card">Card 1</article>
<article class="card">Card 2</article>
<article class="card">Card 3</article>
<article class="card">Card 4</article>
</div>
Named Grid Areas
Grid areas make complex layouts readable and maintainable.
.page-layout {
display: grid;
grid-template-areas:
"header header"
"sidebar main"
"footer footer";
grid-template-columns: 250px 1fr;
grid-template-rows: auto 1fr auto;
min-height: 100vh;
}
.header { grid-area: header; }
.sidebar { grid-area: sidebar; }
.main { grid-area: main; }
.footer { grid-area: footer; }
/* Responsive: stack on narrow viewports */
@media (max-width: 768px) {
.page-layout {
grid-template-areas:
"header"
"main"
"sidebar"
"footer";
grid-template-columns: 1fr;
}
}
<div class="page-layout">
<header class="header">Header</header>
<aside class="sidebar">Sidebar</aside>
<main class="main">Main Content</main>
<footer class="footer">Footer</footer>
</div>
grid-template Shorthand for Complex Layouts
The grid-template shorthand combines grid-template-rows, grid-template-columns, and grid-template-areas in one declaration.
.dashboard {
display: grid;
grid-template:
"nav nav nav" 60px
"side main aside" 1fr
"footer footer footer" 80px
/ 200px 1fr 250px;
min-height: 100vh;
gap: 1rem;
}
Spanning Multiple Rows or Columns
.featured-grid {
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-template-rows: auto;
gap: 1rem;
}
.featured-item {
grid-column: span 2;
grid-row: span 2;
}
Dense Packing (Filling Gaps)
.masonry-like {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
grid-auto-flow: dense;
gap: 1rem;
}
The dense keyword tells the browser to backfill empty cells with smaller items that appear later in the DOM, creating a tighter layout.
Common AI Mistakes
- Using
auto-fillwhenauto-fitis intended. Most UI patterns want items to stretch and fill available space (auto-fit). AI agents often pickauto-fill, which leaves empty tracks. - Writing
minmax(300px, 1fr)without amin()guard. On viewports narrower than 300px, this causes horizontal overflow. Always useminmax(min(100%, 300px), 1fr). - Avoiding
grid-template-areas. AI agents tend to use row/column numbers for placement, producing unreadable code. Named areas are self-documenting and easier to refactor. - Setting explicit column counts instead of using
repeat(auto-fit, ...). A fixedgrid-template-columns: repeat(3, 1fr)requires media queries to be responsive.auto-fitwithminmax()handles this automatically. - Using flexbox for a grid of cards. When cards need to align in both rows and columns with consistent sizing, CSS Grid is the correct tool.
- Forgetting
gapand using margin on grid items instead. Grid has built-ingapsupport. Margins on grid items add space outside the grid tracks, breaking alignment. - Not setting
min-height: 100vhon full-page grid layouts. Without it, the grid only takes up the height of its content, and areas like the footer will not reach the bottom.
When to Use
CSS Grid is ideal for
- Two-dimensional layouts (rows and columns simultaneously)
- Page-level layout with header, sidebar, main, footer
- Responsive card grids with auto-fit/auto-fill
- Layouts where items span multiple rows or columns
- Any layout that benefits from named areas for readability
Use Flexbox instead when
- You only need a one-dimensional layout (a single row or column)
- Items have unknown widths and need to distribute space (navigation, toolbars)
- You want items to wrap but do not need column alignment across rows
Tailwind CSS
Tailwind provides grid utilities with responsive breakpoint prefixes. While CSS Grid's auto-fit/auto-fill with minmax() isn't available as a utility, Tailwind's responsive prefixes (sm:, md:, lg:) offer an explicit breakpoint-based alternative.