Contents
see List다크 모드를 적용했는데 입력창·스크롤바·날짜 선택기가 흰색으로 남으면, 배경색만 바꾼 상태일 가능성이 큽니다. CSS의 color-scheme으로 페이지가 지원하는 색 체계를 브라우저에 알리고, prefers-color-scheme으로 사용자 설정에 맞는 토큰을 선택하면 기본 컨트롤까지 같은 방향으로 정리할 수 있습니다. 핵심은 다크 색상을 선언하는 것과 브라우저에 다크 UI를 허용한다고 선언하는 것을 분리하는 것입니다.
배경색만 바꾸면 생기는 문제
웹페이지의 background, color만 변경해도 일반 텍스트는 어둡게 보입니다. 하지만 input, select, textarea, 스크롤바, 일부 날짜·시간 입력 UI는 브라우저 또는 운영체제가 그리는 영역입니다. 페이지가 어떤 색 체계를 지원하는지 알 수 없으면 이 영역은 기본 밝은 모양을 유지할 수 있습니다. 흰 입력창에 밝은 글자색을 상속하면 입력값이 읽기 어려워지고, 반대로 어두운 입력창에 기본 검은 글자가 남는 문제도 생깁니다.
전역 선언은 html에 두는 것이 안전합니다. light dark는 두 색 체계를 모두 지원하며, 브라우저가 사용자의 시스템 설정에 맞는 기본 컨트롤 모양을 선택할 수 있음을 뜻합니다. 이 선언만으로 사이트의 브랜드 색상이나 모든 컴포넌트 색상이 자동 변환되지는 않습니다. 색상 토큰은 별도로 작성해야 합니다.
:root {
color-scheme: light dark;
--page-bg: #ffffff;
--surface-bg: #f6f7f9;
--text: #1a1d21;
--border: #c7cbd1;
--focus: #0b6bcb;
}
@media (prefers-color-scheme: dark) {
:root {
--page-bg: #15171a;
--surface-bg: #22262b;
--text: #f3f5f7;
--border: #69727d;
--focus: #7db8ff;
}
}
body {
margin: 0;
background: var(--page-bg);
color: var(--text);
}
input, select, textarea {
box-sizing: border-box;
background: var(--surface-bg);
color: var(--text);
border: 1px solid var(--border);
}
input:focus-visible, select:focus-visible, textarea:focus-visible {
outline: 3px solid var(--focus);
outline-offset: 2px;
}
구현 순서와 확인 기준
- 첫째,
html또는:root에color-scheme: light dark를 선언합니다. 운영체제 설정을 따르지 않고 밝은 화면만 제공할 페이지는color-scheme: light처럼 한 가지 값만 선언할 수 있습니다. - 둘째, 배경·표면·본문·테두리·포커스 색상을 CSS 변수 5개 이상으로 분리합니다. 컴포넌트마다 색상값을 직접 넣으면 다크 모드 수정 때 누락이 늘어납니다.
- 셋째,
prefers-color-scheme: dark미디어 쿼리에서 변수 값만 바꿉니다. 이미지, 로고, 차트처럼 밝기 차이가 큰 자산은 별도 파일 또는 명시적 스타일을 검토합니다. - 넷째, 로그인·검색·주문서처럼 실제 입력이 있는 화면에서 텍스트, placeholder, 비활성 상태, 오류 메시지, 키보드 포커스를 각각 확인합니다. 밝은 배경과 어두운 글자, 어두운 배경과 밝은 글자 모두에서 테두리가 구분되어야 합니다.
배포 전에는 프로젝트에서 선언 위치와 중복 규칙을 먼저 찾습니다. 다음 명령으로 전역 선언과 미디어 쿼리가 여러 파일에 흩어져 있는지 확인할 수 있습니다.
grep -R -n -E "color-scheme|prefers-color-scheme" src public styles
출력에 페이지별로 서로 다른 color-scheme 값이 반복되면 전역 정책과 예외 정책을 구분해야 합니다. 예를 들어 외부 결제 위젯을 감싼 영역에 color-scheme: only light를 적용하면, 그 영역에서는 브라우저가 다크 기본 UI로 바꾸지 않도록 제한할 수 있습니다. 다만 이 값은 전체 페이지에 일괄 적용할 설정이 아니라, 다크 모드를 처리하지 못하는 특정 위젯을 격리할 때만 사용합니다.
테스트할 때 놓치기 쉬운 조건
Chrome DevTools의 Rendering 도구에서 prefers-color-scheme을 light와 dark로 각각 강제해 같은 화면을 비교합니다. 최소한 텍스트 입력, 선택 상자, 날짜 입력, 스크롤 가능한 영역, 모달 안의 폼을 확인합니다. 시스템 테마를 바꾼 뒤 새로고침했을 때도 동일해야 하며, 자동 모드와 사이트 내부 테마 전환 버튼을 함께 제공한다면 사용자 선택값이 시스템 설정을 덮어쓰는 우선순위도 문서화해야 합니다.
color-scheme은 색 대비를 보장하지 않습니다. 변수 색상 조합의 대비, 아이콘의 식별성, 포커스 표시, 이미지 안의 글자는 별도로 점검해야 합니다. 특히 단순히 filter: invert(1)로 화면 전체를 뒤집으면 사진·브랜드 색·아이콘까지 반전되어 운영 화면의 의미가 바뀔 수 있으므로 장기적인 방식으로 적합하지 않습니다.
소프트모아는 다크 모드와 접근성을 고려한 웹 화면 및 업무 시스템을 구축합니다. 문의하기
소프트모아의 서비스와 포트폴리오는 softmoa.com에서 확인할 수 있습니다.
소프트모아는 해당 시스템을 구축합니다. 문의하기
html
| No | 작성일 | Title |
|---|---|---|
| 3494 | 2026. 09. 20. | CSS 다크 모드에서 입력창 색상이 깨질 때: color-scheme 설정 방법 |
| 3460 | 2026. 09. 10. | HTML 폼 검증을 견고하게 만드는 방법: 제약 검증·접근성·서버 검증 실전 가이드 |
| 3428 | 2026. 09. 01. | HTML dialog로 접근 가능한 모달 창 만들기: 포커스·닫기·배경 처리 실전 가이드 |
| 3396 | 2026. 08. 24. | 반응형 이미지로 웹 성능 높이기: srcset·sizes와 CLS 방지 실전 가이드 |
| 3364 | 2026. 08. 16. | HTML 폼 오류를 누구나 이해하게 만드는 방법: label·aria-describedby·aria-live 실전 가이드 |
| 3332 | 2026. 08. 07. | CSS @layer로 스타일 충돌 줄이기: 대규모 웹 프로젝트 우선순위 설계 가이드 |
| 3300 | 2026. 07. 30. | CSS Container Query 실전 적용: 컴포넌트가 놓인 영역에 맞춰 반응형 만들기 |
| 3269 | 2026. 07. 22. | 접근성 있는 모달 만들기: HTML dialog와 포커스 관리 실전 가이드 |
| 3241 | 2026. 07. 14. | 반응형 이미지 최적화: picture·srcset·sizes로 모바일 전송량 줄이기 |
| 3186 | 2026. 07. 05. | HTML Popover API로 자바스크립트 드롭다운 메뉴 줄이기 |