Using Container Queries in CSS

Abstract image used to represent Using Container Queries in CSS
Image by Teng Yuhong.

Although support is currently limited at best, CSS container queries (also sometimes referred to as 'element queries'), allow us to apply styles to an element based on the size of its parent container. Essentially; it's like conventional media queries, but instead of being limited to updating your layout and styling based on viewport dimensions (and other global media attributes), you can isolate parts of the page and tailor its specific look and behaviour to the context of its container.

Consider this HTML. The CSS examples below decide whether the two boxes stack or sit side by side:

<section class='container'>
  <div class='box'>
    <p>Box 1</p>
  </div>
  <div class='box'>
    <p>Box 2</p>
  </div>
</section>

Using traditional media queries, we could change the layout of these boxes based on the size of the viewport, using something like:

.container {
  display: flex;
  flex-wrap: wrap;
}

.box {
  width: 100%;
}

@media (min-width: 500px) {
  .box {
    width: 50%;
  }
}

The media query tests the viewport width, but each box's 50% width is still relative to its containing block. Container queries change what we test: an eligible ancestor container's size. That lets a narrow component stack its boxes even on a wide screen.

To start with, we would first set up containment context on the .container element using container-type. In this instance, we use inline-size so that we can measure based on the inlineaxis of the container, but container-type also accepts size and normal based on your use case. See the documentation here.

.container {
  display: flex;
  flex-wrap: wrap;
  container-type: inline-size;
}

Use this setup instead of the mediaquery example above. flex-wrap: wrap lets the fullwidth boxes occupy separate rows. When the container is at least 500px wide, the @container rule changes each .box from 100% to 50% width and reduces its text size:

.box {
  width: 100%;
  font-size: 1.8rem;
}

@container (min-width: 500px) {
  .box {
    width: 50%;
    font-size: 1.2rem;
  }
}

You can of course also use Sass nesting if you happen to be using Sass for your CSS generation:

.box {
  width: 100%;
  font-size: 1.8rem;

  @container (min-width: 500px) {
    width: 50%;
    font-size: 1.2rem;
  }
}

Graceful Degradation

As with any new CSS feature where support is not yet great, consider what happens when a visitor's browser does not support container queries. A @supports rule can separate the enhancement from a usable fallback:

@supports (container-type: inline-size) {
  /* container query styles here */
}

@supports not (container-type: inline-size) {
  /* fallback, non-container query styles here */
}

Google Chrome Labs also offers a polyfill you can bring into your project which uses ResizeObserver to support the @container syntax.

However, from my personal experience, I've found that this can lead to quite a noticeable slowdown and jankiness in the interface especially if you are already doing quite a lot of animation or reactivetype computations.

It may be that you find as I did that it's better to continue down traditional mediaquery routes for responsive development (at least for now) and enhance using @supports, than it is to bring a resourceintensive polyfill into the mix.

Postscript

June 2026: Since I wrote this article, CSS container queries have become part of everyday frontend development rather than an emerging feature with patchy support. I'm keeping the article here for context, but for current work I would treat container queries as a normal responsivelayout tool and check only for projectspecific browser support requirements.

Looking for technical direction?

I support teams that need senior judgement on React, Next.js, headless CMS architecture, performance, migrations, and technical SEO.