CSS 강좌 / width, height, min, max, box-sizing으로 크기 조절하기
CSS의 width와 height는 요소의 너비와 높이를 정하고, min-*·max-*는 크기의 하한과 상한을 정합니다. 지정한 크기에 padding과 border가 포함되는지는 box-sizing에 따라 달라집니다. 본문처럼 내용이 늘어나는 요소는 높이를 고정하기보다 내용에 맡기거나 최소 높이를 주는 편이 다루기 쉽습니다.
content-box와 border-box를 같은 카드로 계산하기
콘텐츠 너비 300px, 좌우 padding 각각 20px, 테두리 각각 2px인 카드를 비교합니다. content-box는 여백과 테두리가 밖에 더해지고 border-box는 지정한 너비 안에 들어갑니다. 두 경우 모두 margin은 width에 포함되지 않습니다.
| box-sizing | 지정한 width | 콘텐츠 너비 | 테두리까지 너비 |
|---|---|---|---|
| content-box | 300px | 300px | 344px |
| border-box | 300px | 256px | 300px |
border-box가 내용을 사라지게 하는 것은 아닙니다. 같은 바깥 크기에서 여백을 늘리면 콘텐츠 공간이 줄어들어 문장이 더 많이 줄바꿈될 수 있습니다. padding과 border의 합이 width보다 커지는 극단적인 조건에서는 콘텐츠 너비가 음수가 될 수 없어 상자가 지정값보다 커질 수 있습니다. 일반적인 계산과 예외는 MDN의 box-sizing 설명에 설명되어 있습니다.
*, *::before, *::after { box-sizing: border-box; }
새 문서에서 계산 방식을 통일할 때 사용할 수 있는 공통 규칙입니다. 가상 요소도 같은 방식으로 계산하도록 포함했습니다. 기존 페이지에 일괄 적용하면 content-box를 전제로 만든 배치가 달라질 수 있으므로 필요한 영역부터 확인하세요. 전체 예제는 공통 규칙을 적용하되 비교용 .content에만 content-box를 다시 지정합니다.
유동 너비와 최소·최대 크기 선택하기
.fluid { width: 100%; max-width: 32rem; min-height: 10rem; }
.limits { width: 100%; min-width: 180px; max-width: 320px; }
width: 100%는 포함 블록의 너비를 기준으로 하고 max-width는 넓은 화면에서 더 커지지 않도록 제한합니다. 루트 글자 크기가 16px인 조건에서 32rem은 512px입니다. min-width는 작아질 수 있는 하한입니다. 화면이 180px보다 좁아도 최소 너비를 유지하면 가로 넘침이 생길 수 있습니다.
min-width와 max-width가 충돌하면 min-width가 우선합니다. 예를 들어 min-width: 360px, max-width: 320px이면 360px 아래로 줄지 않습니다. 높이에서도 min-height는 max-height보다 우선하므로 서로 모순되는 조건을 만들지 마세요. Flexbox·Grid 자식의 자동 최소 크기는 별도 조건이 있으며 해당 배치를 배울 때 필요한 대상의 min-width: 0을 검토합니다. MDN의 min-width 설명와 MDN의 min-height 설명를 참고하세요.
고정 높이와 최소·최대 높이는 어떻게 다를까요?
| 선언 | 내용이 늘어날 때 | 사용 기준 |
|---|---|---|
| height: auto | 내용에 맞춰 높이를 계산 | 일반적인 본문·설명 카드 |
| height: 96px | 상자 높이는 고정되어 내용이 넘칠 수 있음 | 콘텐츠 양과 넘침 처리가 정해진 경우 |
| min-height: 160px | 160px 이상으로 필요에 따라 커짐 | 최소 공간을 확보하되 내용은 보존 |
| max-height: 96px; overflow: auto | 높이를 제한하고 넘치면 내부 스크롤 | 별도로 읽는 제한된 패널 |
높이를 제한했다고 넘친 글자가 자동으로 사라지는 것은 아닙니다. 기본 overflow에서는 상자 밖으로 보일 수 있고, hidden을 쓰면 읽어야 할 정보가 잘릴 수 있습니다. 최대 높이와 스크롤을 함께 쓰는 경우에도 키보드 접근과 모바일 조작을 확인해야 합니다. 전체 예제는 고정 높이의 실패를 관찰할 수 있도록 뒤쪽에 여유 공간을 두었습니다.
% 높이는 부모의 어떤 높이를 기준으로 할까요?
.height-parent { height: 200px; }
.half { height: 50%; }
일반 블록 흐름에서 부모의 명확한 높이가 200px이면 자식의 height: 50%는 100px입니다. 부모의 높이를 내용에 맡긴 경우에는 이처럼 단순한 50% 계산이 성립하지 않고 보통 auto로 처리됩니다. min-height만 있다고 같은 조건이 되는 것도 아닙니다. 절대 위치나 Flexbox·Grid에서는 별도 계산 조건이 있으므로 이번 예제는 고정 높이를 가진 일반 블록으로 한정합니다. MDN의 height 설명에서 백분율 계산 조건을 확인할 수 있습니다.
전체 예제를 실행하고 크기 비교하기
아래 코드를 sizing.html에 UTF-8로 저장합니다. 너비 계산 두 가지, 크기 제한, 같은 문장을 넣은 높이 비교를 모두 포함했습니다.
<!doctype html>
<html lang="ko">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>너비와 높이 비교</title>
<style>
* { box-sizing: border-box; }
body { margin: 16px; font: 16px/1.6 sans-serif; color: #333; }
.compare { width: 300px; padding: 20px; border: 2px solid #3d6b89;
margin-block: 16px; background: #eef6fa; }
.content { box-sizing: content-box; }
.border { box-sizing: border-box; }
.fluid { width: 100%; max-width: 32rem; min-height: 10rem;
padding: 24px; border: 2px solid #3d6b89; }
.limits { width: 100%; min-width: 180px; max-width: 320px;
padding: 12px; border: 1px solid #777; margin-block: 16px; }
.height-box { width: 100%; max-width: 300px; padding: 12px;
border: 2px solid #b98022; margin-block-end: 16px; }
.height-box p { margin: 0; }
.fixed { height: 96px; margin-block-end: 120px; }
.minimum { min-height: 160px; }
.limited { max-height: 96px; overflow: auto; }
.height-parent { height: 200px; max-width: 300px; background: #eee; }
.half { height: 50%; background: #cbe8d7; }
</style>
</head>
<body>
<h1>요소 크기 비교</h1>
<h2>같은 width: 300px</h2>
<div class="compare content">content-box:테두리까지 344px</div>
<div class="compare border">border-box:테두리까지 300px</div>
<h2>유동 너비와 최소·최대 너비</h2>
<div class="fluid">최대 너비 32rem, 최소 높이 10rem입니다. 문장을 추가해 보세요.</div>
<div class="limits">너비는 최소 180px, 최대 320px입니다.</div>
<h2>고정 높이 96px</h2><div class="height-box fixed"><p>정원 안내문은 내용이 늘어날 수 있습니다. 운영 방법과 준비 사항을 자세히 적으면 여러 줄이 됩니다. 고정된 높이를 쓰면 이 문장이 상자의 경계 밖으로 넘칠 수 있으므로 마지막 문장까지 읽을 수 있는지 확인하세요.</p></div>
<h2>내용에 맞는 높이</h2><div class="height-box"><p>정원 안내문은 내용이 늘어날 수 있습니다. 운영 방법과 준비 사항을 자세히 적으면 여러 줄이 됩니다. 고정된 높이를 쓰면 이 문장이 상자의 경계 밖으로 넘칠 수 있으므로 마지막 문장까지 읽을 수 있는지 확인하세요.</p></div>
<h2>최소 높이 160px</h2><div class="height-box minimum"><p>정원 안내문은 내용이 늘어날 수 있습니다. 운영 방법과 준비 사항을 자세히 적으면 여러 줄이 됩니다. 고정된 높이를 쓰면 이 문장이 상자의 경계 밖으로 넘칠 수 있으므로 마지막 문장까지 읽을 수 있는지 확인하세요.</p></div>
<h2>최대 높이 96px와 스크롤</h2><div class="height-box limited" tabindex="0" role="region" aria-label="최대 높이 비교"><p>정원 안내문은 내용이 늘어날 수 있습니다. 운영 방법과 준비 사항을 자세히 적으면 여러 줄이 됩니다. 고정된 높이를 쓰면 이 문장이 상자의 경계 밖으로 넘칠 수 있으므로 마지막 문장까지 읽을 수 있는지 확인하세요.</p></div>
<h2>200px 부모의 50% 높이</h2><div class="height-parent"><div class="half">높이 100px</div></div>
</body>
</html>
- 넓은 창에서 .content와 .border의 실제 너비를 확인합니다. 각각 344px와 300px입니다. content-box의 padding만 30px로 바꾸면 364px, border-box의 바깥 너비는 같은 변경 후에도 300px입니다.
- 창 폭을 줄여 .fluid가 부모와 함께 줄어드는지 확인합니다. 루트가 16px인 넓은 창에서는 최대 512px입니다. .limits의 min-width를 잠시 360px로 바꾸면 max-width 320px보다 커집니다. 다시 180px로 되돌립니다.
- 네 높이 비교 상자에 같은 문장을 추가합니다. 고정 높이는 경계 밖으로 넘치고, auto와 min-height는 필요에 따라 커지며, max-height 패널은 내부 스크롤로 읽을 수 있어야 합니다.
- 부모의 height: 200px를 제거합니다. 자식의 50%가 계속 100px로 유지되는지 확인하고, 원래 선언을 복원해 다시 100px인지 확인합니다.
- 브라우저의 글자 크기 또는 확대 비율을 올립니다. 고정 높이에서 글자가 잘리거나 겹치지 않는지 확인하고, 크기 제한이 불필요한 본문에는 auto를 사용하는 판단을 연습합니다.
width: 100%인데 가로로 넘치면 box-sizing, 좌우 여백, 큰 min-width, 긴 문자열을 순서대로 확인합니다. 개발자 도구에서 표시되는 콘텐츠 크기와 테두리까지의 크기를 혼동하지 마세요. 값을 바꾼 뒤에는 원래 선언으로 되돌려 비교 조건을 유지합니다.










