# v0.1.257 — 39th Stable Seal (협업자 잔존 QA + critic PASS)

**날짜**: 2026-05-21
**범위**: v0.1.251 ~ v0.1.257 7 사이클
**Ribbon 8 탭 명령 누계**: 46 (38th seal 동일, sim-play +1 v0.1.248 이후 변경 0)

## 사이클별 변경

### v0.1.251 — critic 보류 결함 일괄

- hud-root Space 가드 주석 강화 (Blur가 실질 방어선 명시 — NavigationSubmit 경로 차단)
- sim-play 핸들러 closure 주석 (simPauseBtn null 시 무음 실패 동작 명시)
- SettingsPanelViewModel `_label*` -> `_value*` rename (FloatField 타입과 prefix 정합)
- BindSlider FloatField null LogWarning (UXML name mismatch 디버깅 가이드)

### v0.1.252 — DeleteCommand 다중 선택 풀 처리

- `DeleteCommand(host, List<Part> targets)` 시그니처 변경
- 단일은 List.Count=1로 wrap, 다중은 모두 일괄 Execute/Undo
- selection snapshot (`_selectedPart` + `_selectedParts`) 새 List로 deep copy -> Undo 시 reference 공유 0
- 토스트: 단일 "삭제: {name}" / 다중 "삭제: {N}개 일괄"

### v0.1.253 — QA-053 RotaryActuator Inspector + QA-034 답변

- `RenderActuatorBlock` hasRotary 분기 추가 (v0.1.161/162 Inspector UI 누락분 완결)
- `RenderRotaryCard` 신설 (~115라인, ServoAxisCard 패턴 미러)
  - 회전 파라미터: RPM / 정격토크 / 감속비
  - 각도: Home(°) / RLS(°) / FLS(°)
  - 가속 프로파일 슬라이더
  - Command 4 버튼 (◀ ■ ▶ ⌂)
  - Coil 4 + Reg Angle Modbus 매핑
  - 런타임 상태 / 현재각도 / 각속도
- QA-034 답변: Present Tab = 리본 탭 8번째 (가장 우측), 미구현 X

### v0.1.254 — QA-054/057/058 일괄

- **QA-054**: model-add-sensor에 `alreadySensor` 가드 (Add Servo/Pneumatic/Rotary 패턴 미러)
- **QA-057**: "Show Hidden" -> "Unhide All" (PM 정책 A안 — 영구 해제)
- **QA-058**: Collision 텍스트 사용자 친화 (`0/N쌍 겹침` -> `충돌 없음`)

### v0.1.255 — QA-055 부품 리스트 eye click 단일 처리

- `ToggleVisibilityWithSelection(Part, bool singleOnly = false)` 시그니처 확장
- PM 정책 분기:
  - 부품 리스트 eye click (L2947) — `singleOnly: true` (클릭한 행만)
  - 씬 우클릭 컨텍스트 메뉴 (L6766) — 기본 (다중 선택 반영)

### v0.1.256 — QA-056 hide 부품 raycast 관통

- `PickPartUnderMouse` Physics.Raycast -> RaycastAll (이후 v0.1.257에서 NonAlloc으로 최적화)
- distance sort 후 hidden 부품 skip -> 가장 가까운 visible 부품 반환
- fallback 경로 동일 패턴 (bounds.IntersectRay sort + hidden skip)
- Collider 유지 (물리/이벤트 영향 0)

### v0.1.257 — critic 치명-1 + 중대 2건 fix

- **치명-1 (정합성 주석)**: `DeleteCommand.Execute()` SetActive(false)는 spec QA-021 ④ 정합. v0.1.172 코멘트 "SetActive 금지"는 visibility toggle 도메인 한정 — Delete는 별도 도메인. _partHidden dict가 SSOT.
- **중대-2 (성능)**: RaycastAll -> `RaycastNonAlloc` + `RaycastHit[64]` 정적 buffer + `IComparer<RaycastHit>` 정적 인스턴스. GC alloc 0.
- **중대-1 (정확성)**: `ToggleVisibilityWithSelection` 토스트 카운트 `_selectedParts.Count` -> `targets.Count`. cachedTransform null 가드 통과한 실제 처리 수 표시.

## 협업자 PM 회신 처리 (v0.1.251~257)

| QA | 우선순위 | 처리 사이클 | 상태 |
|----|---------|-------------|------|
| QA-053 | [P1] | v0.1.253 | [완료] |
| QA-034 | [P2] | v0.1.253 (답변만) | [완료] |
| QA-054 | [P1] | v0.1.254 | [완료] |
| QA-057 | [P2] | v0.1.254 | [완료] |
| QA-058 | [P2] | v0.1.254 | [완료] |
| QA-055 | [P1] | v0.1.255 | [완료] |
| QA-056 | [P1] | v0.1.256 | [완료] |

**처리 총 7건** (38th seal 12건 + 본 사이클 7건 = 누적 19건).

**잔존**:
- QA-014 Persp/Ortho 회귀 (PM 회신 대기)
- QA-040 Signal Simulator UX 개편 (spec 분석 필요)

## critic 코드리뷰 결과

| 등급 | 건수 | 처리 |
|---|---|---|
| 치명 | 1 | 정합성 주석 (Delete vs Visibility 도메인 차이 명시) |
| 중대 | 2 | RaycastNonAlloc + 토스트 카운트 fix |
| 중간 | 1 | Color switch 캐시 (v0.1.259 예정) |
| 사소 | 0 | — |

판정: **PASS** (v0.1.257 fix 후).

## 핵심 패턴 SSOT 강화

### IEditCommand List<T> 패턴 일관

DuplicateCommand (단일) / DeleteCommand (List<Part>) / VisibilityCommand (List<Part>) — 다중 처리 패턴 통일.

### SetActive vs Renderer.enabled 도메인 분리

| 도메인 | 메커니즘 | spec |
|---|---|---|
| Delete | SetActive(false) | QA-021 ④ — 물리·이벤트·폴링 모두 정지 |
| Visibility | Renderer.enabled = false | parts-visibility spec — 물리·이벤트 유지 |

`_partHidden` dict가 두 도메인 모두 SSOT.

### RaycastNonAlloc SSOT

`static RaycastHit[] _pickHitsBuf = new RaycastHit[64]` + `IComparer<RaycastHit>` 정적 인스턴스 = GC pressure 0.

## 다음 단계

- v0.1.258 — 39th stable seal 영구 보존 + commit
- v0.1.259 — critic 중간-1 (Color switch 캐시) + QA-040 Signal Simulator spec 분석
- v0.1.260+ — QA-014 (PM 회신 받으면)
