All articles
CSS 4 min read

CSS clamp() for Fluid Typography: Responsive Text Without Media Queries

Learn how CSS clamp() makes text grow and shrink without a single media query. You only need this one CSS function and three values.

If you use are still using multiple media queries just to make a heading responsive on all screen sizes, stop.

CSS has a one-liner alternative called clamp() that you can use to create responsive typography without any media queries.

font-size: clamp(24px, 10vw, 48px)

This line makes the text grow with the screen. It also keeps the text between 24px and 48px. There are no sudden jumps and no long list of font sizes to keep up to date.

The problem with media queries for text sizes

A text size scale that uses breakpoints may look like this:

h1 {
  font-size: 24px
}

@media (min-width: 480px) {
  h1 { font-size: 32px }
}

@media (min-width: 768px) {
  h1 { font-size: 40px }
}

@media (min-width: 1200px) {
  h1 { font-size: 48px }
}

This works, but the text jumps from one size to the next.

When you slowly change the browser width, the heading jumps at each breakpoint. It does not grow or shrink in a smooth way. You also have more CSS to care for, and each new breakpoint adds one more number that you may need to change later.

How clamp() fixes it

clamp() accepts three values:

font-size: clamp(MINIMUM, PREFERRED, MAXIMUM)

For clamp(24px, 10vw, 48px), each value does a different job:

  • 24px is the smallest size. The text can’t get smaller than this.
  • 10vw makes the text grow and shrink. One vw is 1% of the screen width, so the value changes when the screen width changes.
  • 48px is the largest size. The text can’t get bigger than this.

Between the smallest and largest sizes, the browser uses 10vw. Below that range, it uses 24px. Above it, the browser uses 48px. One line replaces the media query block, and the text changes size in a smooth way.

One part of this example matters. 10vw reaches 24px when the screen is 240px wide. It reaches 48px when the screen is 480px wide. On wider screens, the heading stays at its largest size. This works well when the text should grow only on small screens. If the heading should keep growing on tablets and computers, use a smaller middle value.

A better mix: rem + vw

Using only screen units can make text hard to read. These units do not follow the reader’s browser text size. If a reader makes the default text bigger, a middle value that only uses vw can work against that choice.

Mix rem into the middle value instead:

font-size: clamp(1rem, 0.5rem + 2vw, 1.5rem)

The rem part follows the main text size, while 2vw makes the text grow with the screen. This is a better choice for a real site than a middle value that only uses screen units.

Test it at 200% zoom too. Even a good formula can make text wrap in a bad place inside a small card, or it can push nearby buttons off the screen.

Scale against a container with cqi

clamp() does not have to use the screen width. A unit such as cqi lets a value use the width of its parent box:

.card {
  container-type: inline-size
}

.card h2 {
  font-size: clamp(1rem, 0.5rem + 4cqi, 2rem)
}

Here, 1cqi is 1% of the card’s width. The heading now changes with the card instead of the screen. The same card can sit in a small side area or a wide top area without a new class.

Notes

If the smallest value is bigger than the largest value, the smallest value wins. The browser does not warn you, so check the numbers if a value seems stuck.

Most new browsers support clamp(). If you need to support an old browser, put a fixed value first:

h1 {
  font-size: 2rem
  font-size: clamp(1.5rem, 1rem + 2.5vw, 3rem)
}

Browsers that do not know clamp() skip the second line and keep 2rem.

clamp() works with media queries. It does not replace them. Use it for values that should grow and shrink, such as text sizes, space, gaps, and widths.

Try it

Open your browser tools and replace one responsive font-size block with a clamp() that mixes units. Then drag the browser across the old breakpoints. You will see the text change in a smooth way.

Wrap-up

clamp() turns many font-size media queries into one line. With rem + vw, the text grows in a smooth way and still follows the reader’s text size. With cqi, it can use the width of a box instead of the screen.

If you found this one useful, you’ll love WebDevVisuals.

Over 80+ simplified tips & tricks to level up your front-end development skills.

Join today for free!

CSS Responsive Grid Without Media Queries 👇
48
481
2.5K
1.1k
CSS Responsive Typhographies without Media Queries 👇
41
480
2.7K
1.1k
CSS Resizable Element 👇
36
322
1.9k
754
CSS Inset Property 👇
15
165
1K
257
CSS Smooth Scrolling 👇
26
246
1.4K
644
JavaScript script loading tag 👇
15
58
329
150
CSS Responsive Grid Without Media Queries 👇
48
481
2.5K
1.1k
CSS Responsive Typhographies without Media Queries 👇
41
480
2.7K
1.1k
CSS Resizable Element 👇
36
322
1.9k
754
CSS Inset Property 👇
15
165
1K
257
CSS Smooth Scrolling 👇
26
246
1.4K
644
JavaScript script loading tag 👇
Join Today

Ready to level up your web dev game?

Join 500+ developers already building better with WebDevVisuals. Join for free, upgrade whenever you are ready.