fix(440 B06 카드 고르기 차례): 암 경계선 판정 = 구조물 판정면 아래 — 구조물 아랫부분 누름이 구조물을 고름

- 화면 실측(검증_sub7 · 노선 초안): 암 경계 판정이 벽 판정면 40 % · 관 판정면 23 % 를 덮음 → 0
- 시험: test_440 ④ · 356 배선 꼴

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01TteK8mfYZetk5P3bEZkyVZ
This commit is contained in:
2026-10-18 18:37:35 +09:00
co-authored by Claude Opus 5.5
parent 476205757f
commit f44b12d62a
3 changed files with 22 additions and 4 deletions
@@ -3,7 +3,8 @@
* 횡단 카드 고르기 차례(295-1) — 고를 자리가 좁은 것이 위(모달 `pickAt` 과 같은 잣대).
*
* 판정면(구조물 · 띠 · 형상)을 다 꽂은 뒤 넓이 큰 것부터 아래로 다시 세움(작은 것 위) ·
* 보라 선 판정(넓이 0 · 요구 185 사면 손잡이)은 맨 위 · 면적 띠(절 · 성토)는 맨 아래 그대로.
* 보라 선 판정(넓이 0 · 요구 185 사면 손잡이)은 맨 위 · 면적 띠(절 · 성토)는 맨 아래 그대로 ·
* 암 경계선 판정(굵은 투명 선)은 판정면 아래 — 구조물 아랫부분을 덮지 않음(440).
* 끌고 뗀 누름(3 px 넘게 움직임)은 고름 아님.
* 맹암거(306-2) = 안쪽 판정면은 맨 아래(겹친 띠 · 구조물이 위) · 테두리 판정(투명 굵은 선)이 면 판정 맨 위.
* ========================================================================== */
@@ -15,6 +16,8 @@ import { CENTER_HIT_CLASS } from "./B06_Section_UI_Cross_Center";
const SURFACE_HIT_CLASSES = ["b06-chart__culvert-revet-hit", "b06-chart__shape-hit"];
/** 선 판정 — 보라 설계선 조각(`_Cross_Design_Pick`). */
const LINE_HIT_CLASS = "b06-chart__design-hit";
/** 암 경계선 판정(`_Cross_Design_Pick` `ROCK_HIT_CLASS`) — 판정면 아래(440). */
const ROCK_HIT_CLASS = "b06-chart__rock-hit";
/** 맹암거 몸(그림) · 테두리 판정 클래스(306-2). */
const UNDERDRAIN_GROUP = "b06-chart__underdrain";
const UNDERDRAIN_BODY = "b06-chart__underdrain-body";
@@ -69,9 +72,12 @@ export function stackPickTargets(layer: SVGElement): void {
.map((el) => ({ el, area: pointsArea(el.getAttribute("points")) }))
.sort((a, b) => b.area - a.area)
.map(({ el }) => el);
const lines = kids.filter((el) => el.classList.contains(LINE_HIT_CLASS));
const rocks = kids.filter((el) => el.classList.contains(ROCK_HIT_CLASS));
const lines = kids.filter(
(el) => el.classList.contains(LINE_HIT_CLASS) && !el.classList.contains(ROCK_HIT_CLASS),
);
const centers = kids.filter((el) => el.classList.contains(CENTER_HIT_CLASS)); // 중심점 = 맨 위(356-3)
layer.append(...surfaces, ...edges, ...lines, ...centers);
layer.append(...rocks, ...surfaces, ...edges, ...lines, ...centers);
let down: { x: number; y: number } | null = null;
layer.addEventListener(
"pointerdown",
+3 -1
View File
@@ -78,7 +78,9 @@ def test_중심점_좌우_없음_위아래만(ts):
def test_배선_걷음():
order = (B06 / "B06_Section_UI_Cross_Pick_Order.ts").read_text(encoding="utf-8")
assert "layer.append(...surfaces, ...edges, ...lines, ...centers);" in order
assert (
"layer.append(...rocks, ...surfaces, ...edges, ...lines, ...centers);" in order
) # 암 = 판정면 아래(440)
for gone in (
ROOT / "B05_Profile" / "B05_Profile_UI_RouteEdit_Shift.ts",
ROOT / "B05_Profile" / "logic" / "B05_Profile_RouteShift.ts",
@@ -4,6 +4,7 @@
(갈아끼운 캐시)에 모든 카드 번호가 있음 · 찾기 넷(카드 고름 · 목록 → 카드 · 넘김 · 풀기)은 지금 그린 상세.
② 평면 패널 빈 곳 누름 = 평면 마커가 고른 것만 풂(`test_409` 의 deselectOther · deselectOwn).
③ 바뀜 신호에서 B06 목록도 자리가 바뀌었으면 다시 실음.
④ 암 경계선 판정(굵은 투명 선)은 구조물 판정면 아래 — 구조물 아랫부분 누름이 구조물을 고름.
TS 셈은 `helper_440_draft_card_ids.cjs`.
./venv/Scripts/python.exe -m pytest resources/tester/test_440_cross_draft_pick.py -q
@@ -77,3 +78,12 @@ def test_평면_빈_곳_누름은_마커_고름만() -> None:
marks = _read("B05_Profile", "B05_Profile_UI_RouteEdit_StructureMarks.ts")
assert "deselect: () => planMarks(canvas)?.picked === ownPick && deselect()," in marks
assert "ownPick = mark.id;" in marks
def test_암_경계_판정은_구조물_판정면_아래() -> None:
order = _read("B06_Section", "B06_Section_UI_Cross_Pick_Order.ts")
assert "layer.append(...rocks, ...surfaces, ...edges, ...lines, ...centers);" in order
lines = order[order.index("const lines = kids.filter(") :]
assert "!el.classList.contains(ROCK_HIT_CLASS)" in lines[: lines.index(");")]
pick = _read("B06_Section", "B06_Section_UI_Cross_Design_Pick.ts")
assert 'export const ROCK_HIT_CLASS = "b06-chart__rock-hit";' in pick