X Xerobit

CSS Grid minmax() — Flexible and Responsive Grid Tracks

CSS grid's minmax() function sets a minimum and maximum size for grid tracks. Combined with repeat() and auto-fill, it creates responsive grids without media queries. Here's...

Mian Ali Khalid · · 4 min read
Use the tool
CSS Grid Generator
Visual CSS Grid layout builder. Configure columns, rows, gaps, and named areas. Live preview with copyable CSS output.
Open CSS Grid Generator →

minmax(min, max) defines a size range for a grid track. The track won’t be smaller than min or larger than max. Combined with auto-fill or auto-fit, it’s the standard technique for creating responsive grids without media queries.

Use the CSS Grid Generator to build grid layouts visually.

Basic minmax() syntax

.container {
  display: grid;
  grid-template-columns: minmax(200px, 400px) 1fr;
}

The first column is at least 200px and at most 400px. The second column takes the remaining space.

minmax() values

Both min and max accept:

ValueMeaning
200pxFixed pixel size
1frFraction of available space
autoContent size (min: min-content, max: max-content)
min-contentSmallest the content can be without overflow
max-contentLargest the content needs to be without wrapping
%Percentage of the container

Note: fr units are not valid as the min value — only as max.

The responsive card grid pattern

The most common use case: a card grid that automatically adjusts column count:

.card-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: 1.5rem;
}

How it works:

  • auto-fill: creates as many columns as will fit
  • minmax(280px, 1fr): each column is at least 280px, at most 1fr of available space
  • At 840px container width: 3 columns (3 × 280 = 840)
  • At 560px: 2 columns
  • At 280px: 1 column

No media queries needed.

auto-fill vs auto-fit

Both create as many columns as fit, but they differ when there aren’t enough items to fill the row:

/* auto-fill: keeps empty columns (maintains column sizes) */
.auto-fill {
  grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
}

/* auto-fit: collapses empty columns (items stretch to fill) */
.auto-fit {
  grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
}

With 3 items in a 1000px container (would fit 5 columns):

  • auto-fill: 5 columns, 3 have content, 2 are empty ghost columns
  • auto-fit: 3 columns, all have content, items stretch to fill width

Use auto-fit when you want items to fill the full width. Use auto-fill when you want a consistent column grid.

minmax() with fixed column counts

Combine minmax() with explicit column counts for minimum size guarantees:

/* 3 columns, each at least 200px (will overflow if container < 600px) */
.three-col {
  display: grid;
  grid-template-columns: repeat(3, minmax(200px, 1fr));
  gap: 1rem;
}

/* Two columns, sidebar minimum 240px */
.sidebar-layout {
  display: grid;
  grid-template-columns: minmax(240px, 300px) 1fr;
  gap: 2rem;
}

Using minmax() for rows

minmax() works on rows too:

.variable-height-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-auto-rows: minmax(120px, auto);
  gap: 1rem;
}

grid-auto-rows: minmax(120px, auto) means each row is at least 120px tall but expands for taller content. This prevents very short rows for sparse content while accommodating tall content naturally.

Practical examples

.gallery {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
  grid-auto-rows: minmax(180px, auto);
  gap: 0.5rem;
}

.gallery img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

Feature cards section

.features {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
  gap: 2rem;
  padding: 2rem;
}

Data table columns

.data-grid {
  display: grid;
  grid-template-columns:
    minmax(40px, 60px)    /* checkbox/ID column */
    minmax(150px, 2fr)    /* name - gets 2× space */
    minmax(120px, 1fr)    /* email */
    minmax(80px, 100px)   /* status - constrained */
    minmax(120px, auto);  /* date */
}

Dashboard layout

.dashboard {
  display: grid;
  grid-template-columns: minmax(200px, 260px) 1fr;
  grid-template-rows: 56px 1fr;
  min-height: 100vh;
}

/* Content area has responsive widget grid */
.widgets {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));
  grid-auto-rows: minmax(200px, auto);
  gap: 1.5rem;
  padding: 1.5rem;
  align-content: start;
}

min() and max() as alternatives

CSS min() and max() functions can replace minmax() in some cases:

/* Column that's 30% but never less than 200px or more than 400px: */
grid-template-columns: clamp(200px, 30%, 400px) 1fr;

/* Equivalent minmax with a clamp: */
grid-template-columns: minmax(min(30%, 400px), 1fr);

Related posts

Related tool

CSS Grid Generator

Visual CSS Grid layout builder. Configure columns, rows, gaps, and named areas. Live preview with copyable CSS output.

Written by Mian Ali Khalid. Part of the Frontend & Design pillar.