# design.md — 무월(霧月) 원두 정기구독 랜딩

> 6단계 산출물. 다음 실행(사람이든 에이전트든)은 이 파일을 읽고 같은 결정을 이어간다.

## 브리프 3줄
- **무엇을**: 수제 커피 로스터리 "무월"의 원두 정기구독 단일 랜딩 페이지
- **누구에게**: 홈카페 3년차 이상 30~40대. 여러 로스터리를 거쳤고 산미·로스팅 프로파일을 구분한다. 목표는 구독 신청
- **제약**: 한국어 / 정적 HTML·CSS(프레임워크 없음) / 사진 없음 / 모바일 트래픽 70% / 성능 예산 스킬 기본값

## 레퍼런스
| 슬롯 | 사이트 | 업종 | 가져온 축 |
|---|---|---|---|
| R1 · 구조 | https://coffeecollective.dk | 스페셜티 커피 D2C | 축 1(그리드), 축 6(시선·섹션 순서) |
| R2 · 톤 | https://fitzcarraldoeditions.com | 독립 문학 출판 | 축 2(타입 스케일), 축 3(컬러 역할) |
| R3 · 디테일 | https://tympanus.net/codrops/2024/01/17/a-practical-introduction-to-scroll-driven-animations-with-css-scroll-and-view/ | — | 축 5(모션) |

상세 수치와 변형 사유는 `01-references.md`.

## 한 문장 컨셉
**감상은 이름에만, 화면에는 수치만.**

## 프리셋
**`quiet-commerce` (커스텀 정의).** 기존 4개 프리셋이 전부 "전환이 목적인 커머스 랜딩"을 배제하거나 근거가 없어 새로 정의했다. 정의 전문은 `02-direction.md`.

## 감수한 리스크 하나
히어로에 이미지도 감성 카피도 없이 **원두 3종의 로스팅 프로파일 수치표**를 첫 화면에 올린다.
→ ⚠️ **현재 미완성**: 실제 수치를 확보하지 못해 표가 `—`로 비어 있다. 값이 들어와야 이 리스크가 성립한다. 지어내지 않았다(하드 게이트 11).

## 토큰
`03-tokens.css` 전문. 요약:
- 타입 비율 **1.333**, 본문 16px, 최대/본문 **4.2배**. 7개 정의 / **실사용 4개**
- 색 역할 8개. `--surface #F3F4F2` / `--ink #1A1C1A` / `--accent #7A3E1D` (강조 1개, hue 2개)
- 대비 실측: 본문 15.54:1 · 보조 5.80:1 · CTA 7.51:1 · 인터랙티브 경계 3.12:1 — 전부 통과
- 간격 8단계, 섹션:요소 = 1:4. 컨테이너 1120px, `--measure` 32ch(한글)
- 라인하이트 본문 **1.7**(한글), 음수 자간은 디스플레이 `-0.015em`만
- radius 어휘 **1개(2px)** — tokens.md에 radius 항목이 없어 직접 추가
- 재질 `--grain: 0.03` (필름 그레인 최약, data URI 배경)
- 다크 모드: 브리프 근거 없어 **지원하지 않음**

## 성능 — 예산과 실측
| 항목 | 예산 | 실측 | 판정 |
|---|---|---|---|
| 히어로까지 JS (gzip) | 150KB | **0KB** (script 태그 0개) | ✓ |
| WebGL/3D | +200KB | 0 (미사용) | ✓ |
| 총 전송량(첫 화면) | 1MB | **13.4KB** (폰트 캐시 상태) | ✓ |
| 폰트 패밀리 | 2개 이하 | 2개 (Fraunces, Pretendard) | ✓ |
| 폰트 **파일** 수 | 2개 이하 | **14개** | ✗ — 아래 참조 |
| 애니메이션 속성 | transform/opacity만 | opacity, transform | ✓ |
| LCP / CLS | 2.5초 / 0.1 | **미측정** | 측정 절차 없음 |

폰트 파일 14개는 Pretendard `dynamic-subset`이 유니코드 범위별로 분할된 결과다. **이것이 올바른 최적화**이며 실제 전송은 페이지에 쓰인 글자 범위만이다. tokens.md의 "폰트 파일 2개 이하"를 문자 그대로 적용하면 한글 프로젝트에서 잘못된 방향(단일 대용량 파일)으로 유도된다. 예산 항목을 **패밀리 수**로 읽고 통과 처리했으며, 그 사실을 여기 명시한다.

## 채택한 이펙트와 폴백
| 이펙트 | 구현 | 폴백 |
|---|---|---|
| 필름 그레인 | data URI SVG 배경, `opacity: .03`, `mix-blend-mode: multiply` | 없어도 무해. 배경색만 남는다 |
| 스크롤 진입 페이드+8px 상승 | `animation-timeline: view()`, JS 0 | Chromium 외에서는 **아무 일도 안 일어남**. 콘텐츠는 처음부터 visible |

이중 게이팅: `@media (prefers-reduced-motion: no-preference)` 안에 `@supports (animation-timeline: view())`.

## 5단계 감사 결과
- 기계 검사 3종: 이펙트 전부 끄기 **통과**(h1·CTA·표 3행 모두 렌더, 본문 401자) / 슬롭 grep 15개 패턴 **전부 0건** / 경쟁사 치환 **통과**
- 하드 게이트 12개: 전부 "아니오" (검사 근거는 `FINDINGS.md` §하드게이트)
- 감사 중 발견해 고친 것 2건:
  1. 히어로 헤드라인이 데스크톱에서 **5줄** → 카운트 규칙(≤2줄) 위반. 헤드라인을 두 컬럼 가로지르게 하고 `max-width: 20ch` 적용
  2. 320px에서 가로 오버플로 **31px** → 하드 게이트 5 위반. grid item `min-width: 0` + 표를 `overflow-x: auto` 컨테이너로 감쌈

## 의도적으로 하지 않은 것과 그 이유
- **다크 모드** — 브리프에 야간 사용·데이터 시각화 근거가 없다. tokens.md "다크를 기본값으로 삼지 마라"
- **한글 세리프 디스플레이(마루 부리)** — 폰트 패밀리 2개 예산을 지키려 버렸다. 그 결과 프리셋이 정한 "세리프 디스플레이"가 **한글에서는 실현되지 않는다**(Fraunces는 라틴만 커버). 예산을 3개로 올릴 수 있다면 되돌릴 결정이다
- **Switzer(라틴 본문)** — 같은 이유. Pretendard의 라틴 글리프로 대체
- **구매 CTA** — R1은 "구매"와 "구독"으로 갈라져 있다. 브리프가 구독 전환을 명시했으므로 CTA를 하나로 통합했다. 원두 낱개 판매를 나중에 붙이더라도 **이 페이지에는 넣지 않는다**
- **3D / WebGL** — 필터로 낼 수 없는 인상이 없다. 4-3 미실행
- **스크롤 애니메이션 폴리필** — JS 0 예산을 지키기 위해. Firefox·Safari 사용자는 모션 없이 본다
- **지표 배너 / 후기 / 로고월** — 검증 가능한 데이터가 없다. 생기기 전까지 섹션을 만들지 않는다
- **아이콘** — 이 페이지에 아이콘이 0개다. 정보를 아이콘으로 대체하지 않기로 했다

## 다음 실행이 해야 할 일
1. `05-structure-plan.md`의 "확보해야 할 실제 데이터"를 사용자에게 받는다
2. 히어로 표의 `—`를 채운다. **채우기 전까지 이 페이지는 배포하지 않는다**
3. 히어로 이후 섹션 6개를 계획대로 구현
4. 폰트 서브셋 파일을 자체 호스팅으로 옮긴다(현재 CDN 2곳 의존)
