UI
한 줄 소개: axelabs 의 모든 제품 화면이 공유하는 디자인 시스템 — 색·간격·타이포 토큰, 문서화된 컴포넌트 카탈로그, 그리고 페이지 전체의 골격을 규정하는 레이아웃 계약. 라이브 문서는 design.axelabs.ai 에서 바로 볼 수 있다.
공개 표면
| 주소 | 내용 |
|---|---|
| design.axelabs.ai | 디자인 시스템 문서 제품 — 쇼케이스 · 검색 · 테마 전환 |
/components | 컴포넌트 색인. /components/[slug] 에 컴포넌트별 문서 한 장씩 — props 표 · 클래스 계약 · 접근성 실측 · 예제 · 라이브 prop 조작 |
/contract | 클래스 안정성 계약 |
/patterns/* | 페이지 패턴 정본 (아래) |
/theme | 브랜드층 / 구조층 분리와 재스킨 규칙 |
/llms.txt · /docs.json | 기계가독 채널 — 에이전트·LLM 이 컴포넌트 목록과 계약을 그대로 읽는다. docs.json 은 자기 버전과 컴포넌트 수(version · count)를 스스로 싣고 있으니, 현재 수치는 이 문서 대신 그쪽을 본다 |
| ⌘K 팔레트 | 전 컴포넌트 실검색 → 문서 페이지 이동 |
무엇이 들어 있나
| 층 | 내용 |
|---|---|
| 토큰 | 색 · 타이포 · 간격 · 폰트를 CSS 변수로. 밝은/어두운 테마는 같은 변수 이름을 공유한다 |
| 컴포넌트 | React 컴포넌트 + 대응하는 CSS 클래스 그룹 |
| 레이아웃 chrome | .axe-app-shell — 상단바 · 사이드바 · 본문 · TOC · 푸터의 macro 골격 |
| primitives | .axe-stack · .axe-cluster · .axe-grid · .axe-container — chrome 안쪽의 micro 레이아웃 |
| 페이지 패턴 | 랜딩 · 인증 · 인증 후 애플리케이션 세 표면의 전체 계약 |
| 문서 템플릿 | .axe-doc — 화면이 아니라 인쇄물 용. 세로/가로 A4, 재무표 괘선, 서버 렌더 차트·다이어그램 |
다크 모드는 data-theme="dark" 로 켠다. 밝은 테마와 어두운 테마 모두에서 대비 기준을 통과하도록 색 램프 자체가 검증된다.
Chrome variants
한 애플리케이션이 세 종류의 골격 중 하나를 고른다.
| Variant | 형태 | 쓰는 곳 |
|---|---|---|
docs | 상단바 + 사이드바 + 본문(80ch) + TOC + 푸터 | 문서 사이트, 가이드 |
dashboard | 상단바 + 사이드바 + 본문(1280px) + 푸터 | 업무 애플리케이션 |
landing | 상단바 + 본문(전폭) + 푸터 | 제품 랜딩, 마케팅 |
폭은 CSS 변수로 노출된다 — 사이드바 240px, TOC 220px, 거터 32px, 상단바 높이 56px, 좁은 폭의 subnav 바 44px.
반응형 네비게이션
| 폭 | 상단바 | 좌측 내비 |
|---|---|---|
| 1024px 이상 | 1행 56px — 로고 · 항목(넘치면 스크롤) · 우측 슬롯 | 고정 좌측 컬럼 |
| 768–1023px | 동일 | subnav disclosure — 상단바 안 44px 바를 누르면 사이드바 + TOC 가 오버레이로 열린다 |
| 767px 이하 | 단일행 3칼럼 — [☰ 좌][브랜드 가운데][⋯ 우] | ☰ 는 내비 항목을, ⋯ 는 테마·계정 슬롯을 각각 좌·우 드로어로 펼친다 |
subnav 는 네이티브 details 기반이라 자바스크립트 없이도 동작한다. React 는 링크 클릭·ESC·바깥 탭으로 닫기 같은 향상만 얹는다.
Layout primitives
display:flex / grid + gap 을 매번 인라인 스타일로 재발명하지 않도록 흡수한 클래스다.
| 컴포넌트 | 클래스 | 역할 | 주요 prop |
|---|---|---|---|
Stack | .axe-stack | 세로 flex + gap | gap 0–10 (기본 4) · align · as |
Cluster | .axe-cluster | 가로 flex + wrap + gap (툴바·액션 줄) | gap 0–10 (기본 3) · align · justify · nowrap · as |
Grid | .axe-grid | 반응형 그리드 | cols 1–6 · gap 0–6 · auto + min · responsive |
Container | .axe-container | 최대폭 중앙 정렬 + 거터 | size sm/md/lg/xl/full |
ThemeToggle | .axe-theme-toggle | light / system / dark 전환 | mode segment 또는 cycle · size |
gap 은 간격 스케일과 1:1 로 대응한다 — gap=4 는 var(--space-4). 매직 픽셀값은 쓰지 않는다.
React 가 아닌 스택은 같은 클래스를 직접 쓴다.
<div class="axe-stack axe-stack--gap-4">
<div class="axe-cluster axe-cluster--gap-2 axe-cluster--justify-between">…</div>
<div class="axe-grid axe-grid--auto axe-grid--gap-3" style="--axe-grid-min: 220px">…</div>
</div>Page Pattern 소비자 계약
컴포넌트 하나가 아니라 페이지 전체의 위계·반응형·상태를 규정하는 살아있는 명세다. 각 패턴 페이지는 밝은/어두운 테마 × 데스크톱/모바일 × 여러 상태를 실제로 렌더해 보여준다.
| 패턴 | 정본이 규정하는 것 |
|---|---|
/patterns/landing | 공개 랜딩 — 가치 제안 · 운영 상태 · CTA. 자체 상단 내비 + 최대 76rem 본문 |
/patterns/authentication | 비밀번호 없는 인증 — 최소 브랜드 상단바 + 28rem 단일 컬럼. 카드 없이 로그인 목적·SSO·매직링크가 바로 읽히게 |
/patterns/gate-application | 인증 후 애플리케이션 — app chrome · 대시보드 · 워크플로 · 문서 |
Workspace shell
인증 후 애플리케이션의 공통 골격은 렌더러 중립 계약이다. 56px 상단바, 280px 좌·우 레일, 최대 68rem 중앙 캔버스, 30px 내비게이션 행 간격이 고정된다.
- 1024–1439px — 오른쪽 context 레일이 상단바의 접근 가능한 disclosure 로 접힌다.
- 1024px 미만 — navigation · context 양쪽 레일이 모두 disclosure 로 바뀐다. 모바일 상단바는 제품 아이덴티티를 유지한다.
세 표면(랜딩 · 인증 · 애플리케이션)은 같은 토큰과 컨트롤을 공유하되 서로의 chrome 을 중첩하지 않는다. 로그인 화면에 애플리케이션 사이드바가 딸려 오지 않는다는 뜻이다.
컨텍스트 레일의 3슬롯
오른쪽 context 레일은 탭이 아니라 위에서 아래로 쌓이는 스택이고, 슬롯은 셋이다 — ① 이 화면이 무엇인지 알려주는 도움말, ② 로컬 AI 에이전트에 붙여넣을 프롬프트 카드, ③ 하단 AI 도크. 슬롯 내용은 선택된 객체에 종속하고, 좌측 레일과 목적지가 겹치는 링크는 두지 않는다(패널이 두 번째 내비게이션이 되면 레일이 거짓말이 된다).
슬롯 ② 의 계약은 이름이 @axe/ui/context-panel@1 이고 소유가 디자인 시스템이다 — 소비자가 React·Rust 서버 템플릿으로 갈려 하나의 렌더러를 공유할 수 없으므로, 계약은 언어중립 JSON 으로 배달되고 같은 골든 벡터에 대해 각 구현이 같은 바이트를 내는 것으로 동등성을 증명한다. 카드가 내주는 복사 텍스트에는 기록 본문이 없다: 대상 식별자 하나와 그것을 다시 읽는 명령 한 줄뿐이고, 실제 조회는 붙여넣는 사람의 기기·로그인으로 일어난다 (붙여넣은 쪽이 실행하는 명령은 axe ref 다). 세 슬롯의 상태는 서로 독립한 축이라 한 축의 실패가 다른 축을 가리지 않는다.
조합 계약 (CSS-only)
제품마다 도메인 컴포넌트를 새로 만들지 않고, 기존 primitive 를 아래 계약으로 조합한다.
| 클래스 | 역할 |
|---|---|
.gate-resource-toolbar | 검색 · 필터 · 결과 수 · 주 행동을 한 영역에 묶는다 |
.gate-detail-layout | 정본 내용(main)과 상태·보조 행동(aside)을 분리한다 |
.gate-form-layout | 반응형 필드 · validation · 행동 위계를 정의한다 |
.gate-copy-field | 일회성 API 키 · 초대 URL · 서명 URL 의 값 · 설명 · 복사 · 결과 안내를 한 신뢰 표면으로 묶는다 |
.gate-secret-reveal | 한 번만 보이는 비밀의 경고 · 값 · 복사 · 확인 상태를 더 강한 disclosure 로 |
.gate-task-shell | 내부 내비가 필요 없는 외부 서명·집중 작성 화면 — 제한된 본문 + 고정 액션 푸터 |
이 계약은 Input · FormField · DataTable · Pagination · EmptyState · Timeline · StatusBanner 를 재사용한다. 상태는 populated · empty · loading · error · success 다섯으로 검증한다 — 오류를 빈 상태로 표현하거나 모바일에서 주요 행동을 숨기는 구현은 이 계약을 충족하지 않는다.
안정성 계약
.axe-*클래스는 마이너 버전 안에서 이름이 바뀌지 않는다. 폐기는 한 버전의 유예를 둔다.- 배포되는 CSS 번들은 import 그래프에서 생성한다 — 손으로 고른 concat 이 아니다.
- 패키지와 배포 키트에 외부 원격 URL 이 0개다. 폰트는 same-origin 으로 함께 배포하고 라이선스 고지를 동봉한다.
- 컴포넌트를 doc·specimen 없이 내보내거나, 하드코딩한 색을 넣거나, 색 대비 계약을 깨면 빌드가 실패한다. 색 램프의 단조성과 작은 텍스트 대비는 빌드 전에 기계로 검증한다.
다른 스택에서 쓰기
React 가 아닌 스택(서버 렌더 템플릿 등)도 같은 CSS 와 같은 markup 으로 동일한 chrome 을 얻는다.
<div class="axe-app-shell" data-shell="dashboard">
<div class="axe-app-shell__topbar">
<nav class="axe-topnav">…</nav>
</div>
<div class="axe-app-shell__main">
<aside class="axe-app-shell__sidebar"><nav class="axe-sidebar">…</nav></aside>
<main class="axe-app-shell__content">…</main>
</div>
<div class="axe-app-shell__footer">
<footer class="axe-footer">…</footer>
</div>
</div>소비하는 쪽은 선언 파일 하나(axe-ui.consumer.json)에 출력 위치와 자산 경로, 프로파일(modern 또는 구형 브라우저용 legacy-light)만 적는다. 내보내기 도구가 폰트 · 테마 · CSS · 잠금 파일을 한 묶음으로 만들고, 잠금 파일에 각 파일의 해시를 기록해 이후 드리프트를 실패로 잡는다.
문서 템플릿
화면이 아니라 인쇄물 쪽이다. 외부로 나가는 문서(메모 · 서한 · 계약서)를 .axe-doc 클래스 HTML 로 통일한다. React 쇼케이스와 서버 템플릿이 같은 markup 을 공유한다.
- 세로·가로 모두 —
.axe-doc--portrait(A4 210×297mm) /.axe-doc--landscape(297×210mm). 가로 본문에는 2단 조판을 적용할 수 있다. - 계약서 변형 —
.axe-doc--contract는 방향과 직교한다. 머리글을 숨기고 제목을 중앙 정렬하며 당사자 블록과 장·조·항 위계를 켠다. - 단위는 pt — 화면과 인쇄가 어긋나지 않는다.
- 테마 무관 — 문서는 자체 팔레트를 정의한다. 다크 모드에서도 흰 종이에 따뜻한 잉크로 보인다.
- 표 조판 — 재무표 우정렬 + 고정폭 숫자, 행 그룹 · 소계(윗 단선) · 합계(윗 단선 + 아래 이중선) 같은 회계 괘선 관례를 클래스로 제공한다.
- 차트·다이어그램 — 막대 · 선 · 도넛 · 투자구조도를 서버에서 SVG 로 렌더한다. 클라이언트 자바스크립트 0, 인쇄 시 선명. 접근성을 위해 같은 데이터의 표를 함께 넣는다 (인쇄에서는 숨김).