feat(bearing): model C4/C5 and the front–back pair eccentricity (승인 2026-10-26)

- C4/C5 = distance from the coping edge to the bearing centre along the
  coping length, from the model; the drawing value is for comparison only.
- A pair is a front and back bearing of the same order within their row. A
  pair with an eccentricity above 100 mm forbids 일체 (분리 first).
- ② bearing card: read-only table of C4/C5 and the pair eccentricities.
- The 일체 block model is not built yet.

Co-Authored-By: Claude Haiku 5.5 <noreply@anthropic.com>
This commit is contained in:
ypshimandClaude Haiku 5.5 committed 2026-10-26 11:49:27 +09:00
1 parent d77f2bfd17
commit cd18665d6a
3 files changed
+132

No files matched your search

+55
View File
@@ -0,0 +1,55 @@
import type { BlockModel, PierModel } from './geometry';
/**
* 받침 배치 규칙 (승인 2026-10-26).
* - C4·C5: 코핑 가장자리와 받침 중심(받침좌표) 사이 거리, 교각축 방향 (s). 모델값을 쓰고 도면값과 비교한다.
* - 일체: 같은 순서끼리 (전열 1 · 후열 1, 전열 2 · 후열 2 …, 각 열의 번호 순) 두 받침의 편심거리가 100 mm를 넘으면 분리를 우선한다.
* (P1 은 전열 1–5, 후열 6–10 으로 번호가 매겨져 있어서 번호 자체가 아니라 열 안의 순서로 짝짓는다.)
* 편심거리 = 두 받침 중심의 교각축 방향 차이 |s(전열) − s(후열)|.
*/
export const PAIR_ECCENTRICITY_LIMIT_MM = 100;
export interface EdgeDistance {
no: number;
row: BlockModel['row'];
/** 코핑 시작(s = 0)에서 받침 중심까지 (mm). */
leftMm: number;
/** 받침 중심에서 코핑 끝(s = L)까지 (mm). */
rightMm: number;
}
export interface PairEccentricity {
/** 전열 번호 and 후열 번호 of the pair. */
frontNo: number;
backNo: number;
eccentricityMm: number;
/** true: 편심이 한계 이하, 일체 배치 가능. */
allowed: boolean;
}
/** C4·C5 from the model: distances from each coping edge to each bearing centre, along the coping length (mm). */
export function bearingEdgeDistances(m: PierModel): EdgeDistance[] {
const L = m.copingL * 1000;
return m.blocks.map((b) => ({
no: b.no,
row: b.row,
leftMm: b.s * 1000,
rightMm: L - b.s * 1000,
}));
}
/**
* Pairs by order within each row (전열 1 · 후열 1, 2 · 2 …) with their eccentricity.
* A bearing left without a partner (the rows have different counts) is not paired.
*/
export function pairEccentricities(blocks: BlockModel[]): PairEccentricity[] {
const byNo = (a: BlockModel, b: BlockModel) => a.no - b.no;
const front = blocks.filter((b) => b.row === '전열').sort(byNo);
const back = blocks.filter((b) => b.row === '후열').sort(byNo);
const out: PairEccentricity[] = [];
for (let i = 0; i < Math.min(front.length, back.length); i++) {
const e = Math.abs(front[i].s - back[i].s) * 1000;
out.push({ frontNo: front[i].no, backNo: back[i].no, eccentricityMm: e, allowed: e <= PAIR_ECCENTRICITY_LIMIT_MM });
}
return out;
}