fix(B06): 벽 폭 흡수 폴백 제거 — 좌우 단면이 서로 달라지던 문제

유입 벽을 조정창으로 밀면 유출 벽이 자동으로 관 길이를 맞추다가 **폭 흡수 폴백**에
걸려 0.45→0.85m로 부풀었다(4+4.3 화면 확인: 좌 0.45 / 우 0.85). 조정한 벽만 폭을
지키게 했던 앞 조치로는 반대편 벽이 보호되지 않았다.

폭 흡수를 아예 없앤다 — 벽 두께는 항상 0.45 고정이고, 자리를 더 못 옮기면 거기서
멈춘다. 남는 몫은 관이 벽을 조금 벗어나는 것으로 두는 게 기존 확정 규칙이다.

검증: 두 측점 이동 16케이스 전부 두께 0.450 고정(두께 이상 0건), 계획고 스윕
24케이스 문제 0. tsc 통과, pytest 148 pass.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-08-21 17:15:26 +09:00
co-authored by Claude Opus 5
parent bcdfde2a05
commit ce03edc180
@@ -501,8 +501,8 @@ export function computeCulvertLayout(
// 를 관 축 방향 바깥으로 민다(벽 두께는 0.45 고정 — 사용자 확정). 벽 상단이 사면선과
// 벌어지는 문제는 설계선 트림이 벽 상단을 따라오므로 생기지 않는다(사용자 ②).
const outletSlopeAt = outletSlopeFactory(outletInfo, invertAt, wallHeightFor(culvert.outlet));
/** 유출 벽 두께 — 자리 이동만으로 길이를 정수로 못 맞출 때만 0.45에서 벗어난다. */
let outletThickness = REVET_THICKNESS_M;
/** 유출 벽 두께 — 항상 0.45 고정(2026-08-21 사용자 확정). 폭으로 길이를 맞추지 않는다. */
const outletThickness = REVET_THICKNESS_M;
if (outletWall) {
const target = Math.ceil(cutLength(pipeCorners) - 1e-6);
const rebuild = (): void => {
@@ -550,27 +550,11 @@ export function computeCulvertLayout(
if (!outletWall) break;
continue;
}
// ② 자리를 더 옮기면 성토 물매가 1:1.2~2.0을 벗어나거나 사면이 5m를 넘는다 —
// 자리는 그대로 두고 ****으로 나머지를 흡수한다(2026-08-21 사용자 폴백).
// 전면(관을 자르는 변)은 두께를 t 늘리면 t의 1.5배만큼 바깥으로 간다
// (이음선 t/2 + 전면 t). 관 축에 투영한 몫만 길이에 반영된다.
const grip = Math.max(Math.abs(axis.offset), 0.2) * 1.5;
const wanted = outletThickness + gap / grip;
// 폭은 0.45의 0.6~2배까지만 — 남는 몫은 관이 벽을 조금 벗어나는 것으로 둔다.
let capped = Math.min(Math.max(wanted, REVET_THICKNESS_M * 0.6), REVET_THICKNESS_M * 2);
// 폭을 넓히면 이음선도 바깥으로 밀려 사면이 길어진다 — **5m 한계가 우선**이라
// 넘는 몫은 포기한다(별표2). 그 경우 관은 표기 길이보다 짧게 벽을 조금 벗어난다
// (2026-08-20 확정 규칙 그대로).
while (
capped > outletThickness &&
outletSlopeAt(outletWallAnchor.offset, capped).lengthM > FILL_SLOPE_MAX_LENGTH_M
) {
capped -= 0.01;
}
if (capped <= outletThickness + 1e-4) break;
outletThickness = capped;
rebuild();
if (!outletWall) break;
// ② 더 옮기면 물매가 범위를 벗어나거나 사면이 5m를 넘는다 — 여기서 멈춘다.
// **폭으로 흡수하지 않는다**:을 건드리면 좌·우 벽 단면이 서로 달라지고
// (2026-08-21 사용자 지적 — 유입을 밀었더니 유출 벽이 0.45→0.85로 부풀었다),
// 남는 몫은 관이 벽을 조금 벗어나는 것으로 두는 게 기존 확정 규칙이다.
break;
}
// 표기 길이 = **실제 그려진 관**의 올림값(목표를 적으면 도면보다 길게 적힌다).
lengthM = Math.max(1, Math.ceil(cutLength(pipeCorners) - 1e-6));