Grid
Purpose and Scope
Tailwind’s grid utilities provide the class-level vocabulary for building CSS Grid layouts without leaving markup. This page focuses on the utilities that define grid tracks, implicit track sizing, auto-placement direction, and item placement across columns and rows. The official docs describe these as part of the Flexbox and Grid family, but the important developer mental model is that Tailwind treats each class candidate as a small rule that maps to one CSS Grid property. You compose a container utility such as grid with track, flow, gap, and item-placement utilities to express the full layout.
Sources: packages/tailwindcss/src/utilities.ts, packages/tailwindcss/src/index.test.ts
The repository implementation keeps these grid APIs in the same utility registration system as the rest of Tailwind’s core framework. That matters when you use responsive variants, state variants, arbitrary values, or custom-property shorthand: grid classes are not a separate plugin with special parsing rules. They are candidates understood by the compiler and validated through the core test suite. As a result, a class like md:grid-cols-6 follows the same variant pipeline as md:flex, while a class like grid-cols-[200px_minmax(900px,_1fr)_100px] follows the same arbitrary-value handling conventions as other functional utilities.
Relevant Source Files
packages/tailwindcss/src/utilities.ts— defines the core utility registrations that turn grid-related class candidates into CSS declarations for template tracks, implicit tracks, flow, and column or row placement.packages/tailwindcss/src/index.test.ts— exercises compiler output at the package level, giving coverage that registered utilities produce the expected CSS when candidates are compiled together with other Tailwind features.
Core Grid Primitives
Grid layout starts with the container. In typical usage, grid establishes a grid formatting context and grid-specific utilities then define how children are placed inside it. Template utilities such as grid-cols-4 and grid-rows-3 describe explicit tracks. Auto-track utilities such as auto-cols-max and auto-rows-fr describe the size of implicitly created tracks. Flow utilities such as grid-flow-col tell the browser how auto-placed children should advance. Placement utilities such as col-span-3, col-start-2, row-span-full, and row-end-auto then override individual item placement when needed.
The template column family is usually the first grid API developers reach for. Numeric column utilities generate equal-width tracks, so grid-cols-4 represents four columns using repeated minmax(0, 1fr) tracks. The docs also expose grid-cols-none for disabling template columns and grid-cols-subgrid for adopting a parent grid’s column tracks. Arbitrary values and custom-property shorthand let you express non-uniform track lists when the fixed scale is not enough, for example a sidebar-content-rail layout with explicit pixel and flexible segments.
Rows mirror the column model. Numeric row utilities generate repeated row tracks, grid-rows-none clears row templates, and grid-rows-subgrid lets nested grids participate in parent row sizing when browser support is available. When content creates additional rows beyond the explicit template, auto-rows-auto, auto-rows-min, auto-rows-max, and auto-rows-fr define the implicit track size. The same pattern applies to implicit columns through auto-cols-*, which becomes especially useful with grid-flow-col when items should create new columns instead of filling rows first.
Utility Reference
| Family | Common classes | CSS behavior |
|---|---|---|
| Grid template columns | grid-cols-<number>, grid-cols-none, grid-cols-subgrid, grid-cols-[<value>], grid-cols-(<custom-property>) | Sets grid-template-columns; numeric values use repeated flexible tracks. |
| Grid template rows | grid-rows-<number>, grid-rows-none, grid-rows-subgrid, grid-rows-[<value>], grid-rows-(<custom-property>) | Sets grid-template-rows; arbitrary and custom-property forms support custom track lists. |
| Auto columns | auto-cols-auto, auto-cols-min, auto-cols-max, auto-cols-fr, auto-cols-<number>, auto-cols-[<value>], auto-cols-(<custom-property>) | Sets grid-auto-columns; numeric values are spacing-based implicit track sizes. |
| Auto rows | auto-rows-auto, auto-rows-min, auto-rows-max, auto-rows-fr, auto-rows-<number>, auto-rows-[<value>], auto-rows-(<custom-property>) | Sets grid-auto-rows; useful when auto-placement creates additional rows. |
| Auto placement | grid-flow-row, grid-flow-col, grid-flow-dense, grid-flow-row-dense, grid-flow-col-dense | Sets grid-auto-flow for row, column, and dense packing behavior. |
| Column placement | col-auto, col-span-<number>, col-span-full, col-start-<number>, col-start-auto, col-end-<number>, col-end-auto, arbitrary forms | Controls grid-column, grid-column-start, and grid-column-end. |
| Row placement | row-auto, row-span-<number>, row-span-full, row-start-<number>, row-start-auto, row-end-<number>, row-end-auto, arbitrary forms | Controls grid-row, grid-row-start, and grid-row-end. |
System-to-Code Mapping
The source mapping for grid is centered on utility registration rather than on a standalone grid module. In packages/tailwindcss/src/utilities.ts, static utilities cover fixed keywords such as none, subgrid, auto, min-content, max-content, and dense flow modes. Functional utilities cover parameterized families such as numeric track counts, spans, starts, ends, spacing-derived implicit track sizes, arbitrary bracket values, and custom-property shorthand. This organization is why grid classes participate naturally in Tailwind’s general candidate parsing, validation, and CSS emission pipeline instead of requiring custom user configuration.
Sources: packages/tailwindcss/src/utilities.ts
packages/tailwindcss/src/index.test.ts is important because grid utilities are only useful if they survive the complete compiler path: candidate collection, parsing, utility resolution, variant expansion, sorting, and CSS serialization. Package-level tests are where regressions often appear, because a utility can be correctly registered yet still serialize incorrectly when combined with variants or arbitrary values. For grid, the most important testing signal is that common fixed utilities and flexible forms compile into stable CSS declarations with the same escaping and ordering rules as the rest of Tailwind.
Sources: packages/tailwindcss/src/index.test.ts
Task Flow and Examples
A practical grid workflow begins by deciding whether the layout needs explicit tracks or browser-created implicit tracks. For a fixed card grid, use a template utility such as grid-cols-1 md:grid-cols-3 and let responsive variants change the track count at breakpoints. For an auto-flowing strip, combine grid-flow-col with auto-cols-max or auto-cols-fr so each additional item creates a predictable column. For masonry-like packing, a dense flow utility can ask the browser to fill earlier gaps, but developers should remember that dense packing may change visual order relative to source order.
<div class="grid grid-cols-1 gap-4 md:grid-cols-3">
<article class="col-span-1 md:col-span-2">Featured</article>
<article>Secondary</article>
<article class="md:col-start-2">Offset item</article>
</div>Custom values are the escape hatch when a design cannot be represented by Tailwind’s numeric grid scales. The docs show grid-cols-[200px_minmax(900px,_1fr)_100px] for a custom column template and auto-rows-[minmax(0,2fr)] for implicit row sizing. Custom-property shorthand, such as grid-cols-(--dashboard-columns), is equivalent to wrapping the property in var() for you. Use this when the track definition belongs in design tokens or component-level CSS variables, while keeping the layout decision visible in the class list.
Implementation Details and Edge Cases
There are two common edge cases to keep in mind. First, explicit templates and implicit track sizing solve different problems. grid-cols-3 defines three explicit columns; it does not decide how extra auto-created rows are sized. Pair it with auto-rows-* when row height for overflow content matters. Second, subgrid is a CSS feature with browser-dependent behavior, not a Tailwind-specific layout engine. Tailwind’s role is to emit subgrid for the relevant template property; the browser determines support and final layout behavior.
Placement utilities also require careful reading because spans, starts, and ends describe grid lines, not pixel positions. col-span-2 means the item spans two tracks from its auto-placed starting position, while col-start-2 pins the start line and lets other placement rules determine the end. Full-span utilities use the first and last grid lines, which is ideal for headers or footers across a grid. When mixing responsive variants, each breakpoint should describe a coherent placement strategy so items do not inherit an unintended start, end, or span from a smaller layout.
Related Pages and Next Steps
Read the spacing and alignment pages next when the grid structure is correct but the visual rhythm is not. Gaps, alignment, justification, and place utilities often complete the layout after tracks and placement are defined. For conditional layouts, pair this page with the responsive design and state-variant pages to understand how prefixes wrap the same grid utilities in media queries or selectors. If you are extending Tailwind itself, follow the package API and configuration/plugin API pages after reviewing packages/tailwindcss/src/utilities.ts, because custom utilities should match the same candidate and declaration conventions used by the built-in grid families.