Giới thiệu
Đơn vị tương đối (relative units) xác định kích thước dựa trên ngữ cảnh (parent element, root element, viewport, font-size...). Khác với đơn vị tuyệt đối (px, pt, cm...), đơn vị tương đối cho phép layout responsive, accessible, scalable.
Bảng tổng hợp đơn vị tương đối
| Đơn vị | Viết tắt | Cơ sở tính toán | Dùng cho |
|---|---|---|---|
| Percent | % | Kích thước của parent element | Width, height, margin, padding, font-size (ít dùng) |
| Em | em | Font-size của parent element | Font-size, padding, margin, width/height component |
| Ex | ex | Chiều cao chữ 'x' của font hiện tại | Fine-tuning vertical rhythm, ít dùng |
| Root Em | rem | Font-size của root element (<html>) | Font-size toàn cục, spacing system, responsive typography |
| Viewport Width | vw | 1% chiều rộng viewport | Full-width layout, fluid typography, hero section |
| Viewport Height | vh | 1% chiều cao viewport | Full-height section, modal, sticky footer |
| Viewport Min/Max | vmin / vmax | 1% min/max (width, height) viewport | Responsive square, aspect ratio, fluid type scale |
| Character | ch | Chiều rộng ký tự '0' (zero) của font hiện tại | Input width, text container, reading line length |
| Grid | gd | Grid track size (CSS Grid) | Grid layout (hiếm dùng trực tiếp) |
So sánh: em vs rem
<style>
html { font-size: 16px; } /* Root = 16px */
.parent { font-size: 20px; } /* Parent = 20px */
.child-em { font-size: 1.5em; } /* 1.5 × 20px = 30px (kế thừa parent) */
.child-rem { font-size: 1.5rem; } /* 1.5 × 16px = 24px (luôn root) */
</style>
Khi nào dùng đơn vị nào?
- rem: Font-size global, spacing system (margin, padding), media query breakpoint — khuyên dùng chính
- em: Font-size component cục bộ, padding/margin internal component (scale theo font component)
- %: Width/height layout fluid, flex/grid child sizing
- vw/vh: Hero full-screen, fluid typography (
clamp(1rem, 2.5vw, 2rem)) - ch: Độ rộng input, max-width đọc thoải mái (
max-width: 65ch) - vmin/vmax: Kích thước vuông responsive, scale theo màn hình nhỏ hơn
Best Practice hiện đại
/* Fluid typography với clamp() */
html { font-size: clamp(14px, 1.2vw, 18px); }
/* Spacing system dựa trên rem */
:root { --space: 1rem; }
.m-1 { margin: var(--space); }
.p-2 { padding: calc(var(--space) * 2); }
/* Container responsive */
.container { width: min(100% - 2rem, 1200px); margin-inline: auto; }