CSS Container Queries 실전 가이드
Media Query vs Container Query, @container 문법, 실전 레이아웃 예시와 폴백 전략.
한 줄 요약: CSS Container Queries는 부모 컨테이너의 크기를 기준으로 스타일을 조건부 적용하는 기능으로, 재사용 가능한 컴포넌트 기반 레이아웃을 구축할 때 Media Query보다 훨씬 정확하다.
- 같은 컴포넌트가 사이드바와 메인 영역에서 다르게 보여야 하는 레이아웃을 구현 중인 개발자
- Media Query만으로 해결이 안 되는 반응형 컴포넌트 문제를 겪고 있는 경우
@container문법과 브라우저 지원 현황을 실무 기준으로 파악하려는 경우- CSS Container Queries를 도입할 때 폴백 전략이 필요한 팀
※ 브라우저 지원 현황은 2026년 3월 기준입니다. Can I Use 기준 전 세계 지원율 약 93%.
Media Query vs Container Query — 근본 차이
Media Query는 뷰포트(viewport) 크기를 기준으로 스타일을 바꾼다. 문제는 같은 컴포넌트가 메인 영역(넓음)과 사이드바(좁음)에 동시에 존재할 때, 뷰포트 폭은 동일하지만 컴포넌트가 놓인 공간은 다르다는 점이다. 이 경우 Media Query로는 컨테이너별 스타일링이 불가능하다.
Container Query는 부모 컨테이너의 크기를 기준으로 스타일을 조건부 적용한다. 컴포넌트가 어디에 배치되든 자신이 차지하는 공간에 반응한다.
| 항목 | Media Query | Container Query |
|---|---|---|
| 기준 대상 | 뷰포트 폭/높이 | 부모 컨테이너 폭/높이 |
| 컴포넌트 재사용성 | 낮음 (배치 위치에 따라 별도 처리) | 높음 (어디에나 동작) |
| 사용 목적 | 페이지 레이아웃 전환 | 컴포넌트 내부 레이아웃 전환 |
| 중첩 레이아웃 처리 | 어려움 | 자연스럽게 지원 |
@container 문법 완전 정리
Container Query를 사용하려면 두 단계가 필요하다. 1) 부모 요소에 container-type을 선언해 컨테이너로 등록한다. 2) 자식 요소에 @container 규칙으로 조건을 작성한다.
기본 문법 — container-type 선언 + @container 조건/* 1. 부모를 컨테이너로 등록 */ .card-wrapper { container-type: inline-size; /* 폭 기준 */ container-name: card; /* 이름 (선택) */ } /* 단축 속성 */ .card-wrapper { container: card / inline-size; } /* 2. 자식에 조건부 스타일 적용 */ @container card (min-width: 400px) { .card { display: grid; grid-template-columns: 1fr 2fr; } } @container card (max-width: 399px) { .card { display: flex; flex-direction: column; } }
container-type 값:
inline-size: 인라인 축(보통 폭) 기준으로 쿼리. 가장 많이 사용.size: 인라인 + 블록 축(폭 + 높이) 모두 쿼리 가능. 높이 기반 쿼리 시 사용.normal: 컨테이너로 등록하되 사이즈 쿼리 불가. style 쿼리(실험적)에만 사용.
실전 레이아웃 예시 — 카드 컴포넌트
카드 컴포넌트 — 사이드바(좁음)와 메인 영역(넓음) 동시 대응/* 컨테이너 등록 */ .article-card-wrapper { container: article-card / inline-size; } /* 기본 스타일 — 좁은 공간 (세로 레이아웃) */ .article-card { display: flex; flex-direction: column; gap: 8px; } .article-card img { width: 100%; aspect-ratio: 16 / 9; object-fit: cover; } /* 컨테이너 폭 >= 480px — 가로 레이아웃 */ @container article-card (min-width: 480px) { .article-card { flex-direction: row; align-items: flex-start; } .article-card img { width: 180px; aspect-ratio: 4 / 3; flex-shrink: 0; } } /* 컨테이너 폭 >= 700px — 제목 폰트 확대 */ @container article-card (min-width: 700px) { .article-card__title { font-size: 1.25rem; } }
이 패턴의 핵심은 .article-card-wrapper를 사이드바에 배치하든 메인 영역에 배치하든, 카드 컴포넌트 CSS를 수정할 필요가 없다는 점이다. .article-card는 자신이 놓인 공간 폭에 알아서 반응한다.
Container Query 단위 — cqw, cqh, cqi, cqb
Container Queries와 함께 컨테이너 크기 기반 단위도 사용할 수 있다.
| 단위 | 의미 |
|---|---|
cqw | 컨테이너 폭의 1% |
cqh | 컨테이너 높이의 1% |
cqi | 컨테이너 인라인 축(보통 폭)의 1% |
cqb | 컨테이너 블록 축(보통 높이)의 1% |
예시: font-size: clamp(0.9rem, 3cqi, 1.5rem) — 컨테이너 폭에 비례해 폰트 크기가 유동적으로 변한다. vw와 달리 컨테이너 폭 기준이므로 사이드바 안의 텍스트가 뷰포트 크기에 끌려다니지 않는다.
브라우저 지원 현황과 폴백 전략
| 브라우저 | 지원 버전 | 지원 여부 |
|---|---|---|
| Chrome | 105+ | 지원 |
| Edge | 105+ | 지원 |
| Firefox | 110+ | 지원 |
| Safari | 16+ | 지원 |
| Samsung Internet | 21+ | 지원 |
2026년 3월 기준 Can I Use 전 세계 지원율 약 93%. 한국 내 주요 브라우저 기준으로는 지원되지 않는 브라우저를 만날 확률이 낮다. 단, IE11과 구형 안드로이드 WebView는 지원하지 않는다.
폴백 전략:
폴백 — @supports로 Container Query 지원 여부 분기/* Container Query 미지원 브라우저용 기본 스타일 */ .card { display: flex; flex-direction: column; } /* Container Query 지원 브라우저에서만 적용 */ @supports (container-type: inline-size) { .card-wrapper { container-type: inline-size; } @container (min-width: 480px) { .card { flex-direction: row; } } }
container-type: size를 설정하면 해당 요소의 블록 축 크기가 내용에 의해 결정되지 않는다. 레이아웃이 무너지면 inline-size만 사용하는지 먼저 확인할 것.요약 및 참고 자료
- Container Query는 뷰포트가 아닌 컨테이너 크기 기반으로 스타일을 적용한다
container-type: inline-size선언 →@container조건 작성 두 단계로 완성- 컨테이너 단위(cqw, cqi 등)로 유동적 타이포그래피도 구현 가능
- 2026년 기준 주요 브라우저 모두 지원,
@supports로 안전하게 폴백 처리 가능