CSS 변수 기반의 다크모드를 구현하고, 사용자가 직접 테마를 선택할 수 있는 테마 시스템을 만든다. prefers-color-scheme 미디어 쿼리와 JavaScript 토글을 모두 다룬다.
이번 강에서 배울 것
- CSS 변수 기반 다크모드 설계 원리
- 시스템 설정 연동 (prefers-color-scheme)
- 다크모드 토글 버튼 구현
- localStorage로 사용자 선택 저장
- 멀티 테마 시스템으로 확장하기
다크모드의 두 가지 방식
| 방식 | 장점 | 단점 | 적합한 상황 |
|---|---|---|---|
| CSS 변수 + 클래스 토글 | 유연함, 멀티 테마 확장 가능 | 초기 설계 필요 | 신규 프로젝트 |
| prefers-color-scheme만 | 구현 간단 | 사용자 수동 전환 불가 | 빠른 프로토타입 |
| Tailwind dark: 접두어 | 클래스 기반 편리 | Tailwind 의존 | Tailwind 프로젝트 |
CSS 변수 기반 다크모드 구조
/* 라이트 테마 (기본) */
:root {
--bg-primary: #ffffff;
--bg-secondary: #f9fafb;
--text-primary: #111827;
--text-secondary: #6b7280;
--border: #e5e7eb;
--card-bg: #ffffff;
--card-shadow: 0 1px 3px rgba(0,0,0,0.1);
}
/* 다크 테마 */
[data-theme="dark"] {
--bg-primary: #0f172a;
--bg-secondary: #1e293b;
--text-primary: #f1f5f9;
--text-secondary: #94a3b8;
--border: #334155;
--card-bg: #1e293b;
--card-shadow: 0 1px 3px rgba(0,0,0,0.4);
}
/* 시스템 설정 자동 연동 */
@media (prefers-color-scheme: dark) {
:root:not([data-theme="light"]) {
--bg-primary: #0f172a;
--text-primary: #f1f5f9;
/* ... */
}
}
실습 1 — 다크모드 토글 구현
실습 프롬프트 1
FRESH:ON 랜딩 페이지에 다크모드를 추가해줘.
구현 방식:
- CSS 변수(:root, [data-theme="dark"]) 기반
- 토글 버튼: 달/해 아이콘 SVG 인라인, 내비게이션 오른쪽에 배치
- JavaScript: document.documentElement.setAttribute("data-theme", ...)
- localStorage에 선택 저장, 페이지 로드 시 복원
- 시스템 설정도 초기값으로 감지 (prefers-color-scheme)
다크모드에서 바꿔야 할 색상 목록:
- 배경: #ffffff -> #0f172a
- 카드 배경: #f9fafb -> #1e293b
- 텍스트: #111827 -> #f1f5f9
- 테두리: #e5e7eb -> #334155
- 그림자: 연한 -> 진한
전환 애니메이션: transition: background-color 0.3s, color 0.3s
실습 2 — 멀티 테마 시스템
실습 프롬프트 2
다크모드를 확장해서 3가지 테마를 선택할 수 있는 테마 피커를 만들어줘. 테마 3가지: 1. light: 기본 흰색 테마 2. dark: 다크 슬레이트 테마 3. green: FRESH:ON 브랜드 초록 테마 (배경 초록 계열) UI: 내비게이션에 색상 원 3개 버튼 (선택된 것에 체크 표시) 저장: localStorage의 "fresho-theme" 키 페이지 로드 시 저장된 테마 자동 적용
다크모드 디자인 팁
/* 순수 검정(#000)보다 짙은 회색 계열 사용 */
/* 눈의 피로 감소 효과 */
--bg-dark: #0f172a; /* slate-900 */
--bg-card: #1e293b; /* slate-800 */
/* 흰색 텍스트 대신 약간 회색빛 사용 */
--text-dark: #f1f5f9; /* slate-100 */
/* 이미지에 다크모드 오버레이 */
.dark-overlay img {
filter: brightness(0.85);
}
/* 그림자는 다크모드에서 색상 기반으로 */
[data-theme="dark"] .card {
box-shadow: 0 0 0 1px rgba(255,255,255,0.05),
0 4px 16px rgba(0,0,0,0.4);
}
다크모드에서 가장 흔한 실수는 색을 단순히 반전시키는 것입니다. 흰 배경의 그림자(box-shadow)는 다크 배경에서 빛 번짐(glow)으로 표현해야 자연스럽습니다.
강의 핵심 요약
- CSS 변수 기반 설계 = 테마 전환이 코드 한 줄
- 시스템 설정 감지 + 사용자 선택 저장의 조합이 베스트 UX
- 다크모드는 색 반전이 아닌 별도 색상 시스템 설계
- 다음 강: 마이크로인터랙션으로 UX 생동감 더하기
관련 검색어 · CSS 다크모드 구현, prefers-color-scheme, 다크모드 토글, CSS 변수 테마, localStorage 테마 저장, 다크모드 디자인 팁