log(open, reason)} />
```
1. 카탈로그 §5의 데이터로 메뉴를 쓴다. 화면마다 타일·섹션·제목을 따로 만들지 않는다.
2. 메뉴 데이터 변경: 항목 추가·삭제는 `items` 배열, 숨김은 `hidden`, 비활성은 `disabled`, 실행만 하는 버튼은 `toggle: false`, 켜고 끄는 버튼은 기본값. Active를 직접 제어하려면 `homeMenu.activeIds` + `onActiveChange`.
3. 최근파일 패널은 선택 기능이다. 필요한 타일에만 `panel: `를 준다. 파일을 열면 메뉴가 닫힌다(`closeOnOpen`).
4. 로고 클릭은 메뉴만 연다. `onHomeClick`의 홈 이동은 `homeMenu`가 있으면 실행되지 않는다. 메뉴 항목에 홈 이동이 필요하면 항목 `onSelect`에서 한다.
5. New / Open은 문서 Dropdown에 그대로 둔다(`documentOpenPlacement` 기본 `"menu"`). 로고 오른쪽에 별도 Open 버튼을 두지 않는다. 메뉴의 찾아열기·새파일은 같은 handler를 연결한다.
6. 위치·폭은 `SWHeader`가 정한다. 소비 코드에서 메뉴 위치를 계산하거나 겹치는 wrapper를 만들지 않는다.
## 10. Footer (일반 모드) — [ExampleI-Footer.tsx](./examples/ExampleI-Footer.tsx)
상세는 [FOOTER.md](./FOOTER.md). 화면 = `SWHeader` → 도면 영역 → `SWFooter`(바 안 명령창 `command`, 위 왼쪽 좌표 `status`, 위 오른쪽 `SWFooterLayoutTabs`). 실제 SW 화면(2026-10-20) 구성입니다.
```tsx
{/* 소비 레이아웃: flex column, 높이 100% */}
{/* flex: 1 */}
}
categories={categories} categoryId={categoryId} onCategoryChange={setCategoryId}
activeToolId={running} onToolSelect={toolId => run(toolId)} onSlotAdd={openRegister}
auxItems={aux} onAuxPressedChange={toggleAux} commandAll={{ onClick: () => setListOpen(open => !open), pressed: listOpen }}
layoutTabs={} />
```
1. 명령·분류·보조기능은 데이터입니다. 프로젝트마다 바꾸고 Footer 외형은 그대로 둡니다.
2. 명령 실행·등록·Layout 생성은 Callback에서 호스트가 처리하고 Props를 갱신합니다(`activeToolId`, `categories`, `layouts`).
3. Figma 아이콘은 `swFooterToolIcons`·`swFooterAuxIcons`, 새 명령 아이콘은 프로그램 제공 18 × 18 요소.
4. 좁은 화면 처리(빈 칸 축소, ▲ 패널, 분류 ◀ ▶, 보조기능 아이콘만)는 `SWFooter`가 합니다. 소비 코드에서 명령 수를 줄이거나 media query로 다시 배치하지 않습니다.
5. 일부만 필요하면(보조기능만, 분류 탭만) `` 안에서 `SWFooterAuxGroup`·`SWFooterMenu`·`SWFooterToolButton`을 씁니다. `SWFooterMenu` 단독은 부모 면을 `var(--hm-sw-footer-group-background)`로 둡니다.
## 11. 테마(토큰) 설정 — [ExampleJ-Theme.tsx](./examples/ExampleJ-Theme.tsx)
일반·뷰어 모드 공통입니다. 토큰 기본값은 가장 바깥 SW 범위에서만 선언되고 안쪽 SW 요소는 상속합니다([AI_USAGE.md](./AI_USAGE.md) §3.1).
```tsx
const appSWTheme = { "--hm-sw-header-font-family": '"Malgun Gothic", sans-serif' } as CSSProperties // 프로그램이 정한 값만
{/* 가장 바깥 범위: 여기서만 지정 */}
{/* Dropdown·More까지 상속 */}
… {/* 패널·안쪽 컨트롤 상속 */}
{createPortal(…, document.body)} {/* Portal은 같은 객체로 다시 감쌈 */}
```
- 일반 모드도 같습니다: `` 안의 `SWHeader`(Dropdown·창 이동 Tooltip)·`SWFooter`(`SWFooterCommandLine`·명령 등록 안내)가 같은 값을 씁니다.
- 기본 글꼴은 Noto Sans KR입니다(2026-10-20 확정). 기본값을 쓸 때는 글꼴 토큰을 지정하지 않습니다. Web UI 글꼴 토큰(`--hm-font-family-base`)을 SW 화면에 넣지 않습니다.
- `hm-sw-*` class 선택자로 토큰을 덮거나 `!important`, 컴포넌트마다 같은 값 반복 지정을 하지 않습니다.
## 12. 프로세스 단계 Header (일반 모드)
`SWHeader` 대신 쓰는 독립 Header입니다(한 화면에 Header 하나). 상태는 모두 프로그램이 갖고 Callback으로 갱신합니다. 로고 메뉴·Layer Popup·도구 Popup은 프로그램이 직접 엽니다([COMPONENT_CATALOG.md](./COMPONENT_CATALOG.md) §11).
```tsx
const groups: SWProcessGroup[] = [
{ id: "modeling", number: "01", label: "Modeling", steps: [{ id: "structure", label: "Structure" }, { id: "loads", label: "Loads" }] },
{ id: "analysis", number: "02", label: "Analysis Result", steps: [{ id: "results", label: "Results" }] },
]
setStep(s.id) }}
layer={{ label: "Layer", value: layerName, visible: layerVisible, open: layerPopupOpen }}
onLayerClick={toggleLayerPopup} onLayerVisibilityChange={setLayerVisible}
tools={<>
{/* ViewPropertyIcon: the program's own icon (the package ships no product icons). */}
} pressed={viewProperty} onClick={toggleViewProperty}>View Property
>}
onWindowMoveStart={startWindowDrag} maximized={maximized}
onMinimize={minimize} onMaximizeToggle={toggleMaximize} onClose={closeWindow} />
```
1. 도구 아이콘은 프로그램이 그린 24 × 24 요소입니다. 버튼 상태 색(기본 `#B6D0C9`, Hover·눌림 `#FFC600`)을 따르려면 `currentColor`로 칠하고, 색이 고정된 이미지 아이콘이면 `hoverIcon`에 `#FFC600` 그림을 함께 줍니다(SW 인쇄 버튼과 같은 방식). 시안의 아이콘을 고를 때는 [AI_USAGE.md](./AI_USAGE.md) §5.2 순서(제공 에셋 → 공개 Export → 없으면 사용자에게 먼저 확인)를 따릅니다. 확인 전에는 임의로 만들거나 대체·생략하지 않습니다. Storybook `SW / Step Header`의 도구 아이콘은 공개 API가 아닙니다(§5.3).
2. 화면 분할은 `SWProcessSplitButton`을 `tools`의 원하는 자리에 둡니다(두 appearance 공통). 고른 값으로 실제 창을 나누는 일은 프로그램이 합니다. 분할 아이콘·선택 패널을 직접 그리지 않습니다.
3. 프로세스 영역만 다른 곳에 둘 때는 `` 안에 `SWProcessBar`를 둡니다.
4. 다른 테마(Strana Dark 등)는 11처럼 가장 바깥 범위 `style`에 `--hm-sw-process-*`·`--hm-sw-header-*` 토큰을 지정합니다.
5. `SWHeader`의 메뉴(레이어·색상·선/문자/치수스타일 Dropdown)를 이 Header에 넣지 않습니다. 필요하면 `SWHeader`를 씁니다.
6. **그룹·단계가 많은 다중 Step 화면**(StrAna-SW Figma 873:16481 등)은 `appearance="multi"`입니다. 같은 `process` 데이터 구조를 쓰고, 제목이 없는 그룹은 `labelHidden`, 호스트가 막아야 한다고 명시한 단계만 `disabled: true`(생략하면 선택 가능, 새 프로젝트·파일명 없음은 비활성 조건이 아님 — [COMPONENT_CATALOG.md](./COMPONENT_CATALOG.md) 11절 "단계 활성화"), 문서가 없을 때는 `documentTitle=""` + `documentEmptyLabel`입니다. Figma 프레임에는 Layer 필드와 최대화 버튼이 없으므로 `layer`를 주지 않고 `hiddenControls={["maximize"]}`를 씁니다. 그룹·단계가 많아도 데이터를 줄이거나 접기·스크롤·More를 만들지 않습니다(넘침 정책: 선택 단계 포함 비례 축소 + `…`, 2026-11-03 개정).
7. **창 제어 버튼은 시안에 보이는 것만** 둡니다. 위 예시의 창 이동·최소화·종료는 그 Figma 프레임에 있기 때문이며 모든 화면의 기본이 아닙니다. 시안에 없는 버튼은 `hiddenControls`(`"windowMove"`·`"minimize"`·`"maximize"`·`"close"`)로 빼고, 잘린 시안·웹/데스크톱 구분은 [AI_USAGE.md](./AI_USAGE.md) §5.5, 예시는 §5.6을 따릅니다. 기존 화면의 창 버튼은 시안에 없다는 이유만으로 빼지 않습니다(AI_USAGE §5.1). 컴포넌트 기본값은 바꾸지 않습니다.
```tsx
// helpIcon / helpIconHover: 사용자·소비 프로젝트가 제공한 에셋(패키지에 도움말 아이콘 Export 없음, AI_USAGE §5.2)
setStep(s.id) }}
tools={} hoverIcon={
} onClick={openHelp}>도움말}
hiddenControls={["maximize"]} onWindowMoveStart={startWindowDrag} onMinimize={minimize} onClose={closeWindow} />
```
## 9. 하지 말 것
- `hm-sw-*` class를 소비 코드에 쓰거나 CSS로 덮어쓰기(토큰 변경도 class 선택자가 아니라 가장 바깥 SW 범위의 `style` — 11)
- `dist` 구현·`styles.css` 블록 복사로 같은 컴포넌트 재작성
- `@hm-design/sw/dist/...`·`src/...` 내부 경로 Import
- 문서에 없는 Props 추측, 새 색·크기 값 도입
- Storybook 데모 아이콘·파일을 Import·복사하거나, 공식 아이콘이 없을 때 외부 아이콘 라이브러리·AI 생성 SVG로 대체([AI_USAGE.md](./AI_USAGE.md) §5.2·§5.3)
- 시안에 없는 창 제어 버튼을 예시·기본 구성에 있다는 이유로 만들기([AI_USAGE.md](./AI_USAGE.md) §5.5)
- 같은 화면에 `SWHeader`와 조합 Header를 겹쳐 두 개의 Header 만들기
- 같은 화면에 `SWHeader`와 `SWViewerHeader`를 함께 두기, 일반 모드 화면에 `SWViewer*` 사용, 뷰어 화면에서 `SWHeader`·`SWPopup` 재스타일(AI_USAGE §0.3)