import { describe, expect, it } from 'vitest'; import { buildPier } from '../src/core/geometry'; import { shearBarsMulti } from '../src/core/rebar/coping'; import { rebarSummary } from '../src/core/rebar/summary'; import { loadP1 } from './helpers'; // 2주형 and 3주형 on the P1 sheet with a 12 m coping (columns at L/5, 4L/5 and L/5, L/2, 4L/5). const two = buildPier({ ...loadP1(), type: '2주형', columnCount: 2, copingLengthMm: 12000 }); const three = buildPier({ ...loadP1(), type: '3주형', columnCount: 3, copingLengthMm: 12000 }); const count = (rows: ReturnType['rows'], name: string) => rows.find((r) => r.name === name)!.count; describe('다주형 철근 (2주형·3주형, 코핑철근.md §9)', () => { it('2주형: C10 2 × 9 = 18; C9 and C11 3 each outside; 18 between (추천안, Q-K2)', () => { const rows = rebarSummary(two).rows; expect(count(rows, 'C10')).toBe(18); expect(count(rows, 'C9')).toBe(3); expect(count(rows, 'C11')).toBe(3); expect(count(rows, 'C9·C11 사이')).toBe(18); }); it('3주형: C10 3 × 9 = 27; two gaps of 3 between', () => { const rows = rebarSummary(three).rows; expect(count(rows, 'C10')).toBe(27); expect(count(rows, 'C9·C11 사이')).toBe(6); }); it('column bars repeat per column: P1 230 × 2 and 230 × 3', () => { expect(count(rebarSummary(two).rows, 'P1')).toBe(460); expect(count(rebarSummary(three).rows, 'P1')).toBe(690); }); it('a multi-column pier gets the RB-M01 note about C14', () => { expect(rebarSummary(two).warnings.map((w) => w.code)).toContain('RB-M01'); }); it('the single column (T형) has no between row and no RB-M01', () => { const t = rebarSummary(buildPier(loadP1())); expect(t.rows.find((r) => r.name === 'C9·C11 사이')).toBeUndefined(); expect(t.warnings.map((w) => w.code)).not.toContain('RB-M01'); }); it('shear bars for a columns too close to share a Level are refused', () => { expect(() => shearBarsMulti(12000, [3000, 3500])).toThrow('겹칩니다'); }); });