"""Add the footing rebar (G3: B1~B12, centreline polylines) to the app pier '새재1교P1'. params = 판독/g3_bars.json (extract_g3_bars.py, Okseong rules F1-F5 applied again 2026-10-15); builder rebar_polylines.py (GATE G3) expected = schedule L / N, drawn position lists, schedule legs b, drawn levels and the B9 rule, typed in by hand. Backs up params.json / expected.json to data/새재1교P1/backup/2026-10-15_g3/ first. Refuses if G3 is in scope. """ import json import shutil import sys from pathlib import Path HERE = Path(__file__).resolve().parent D = HERE.parents[1] / "Code" / "교각모델링앱" / "data" / "새재1교P1" B = json.loads((HERE / "판독" / "g3_bars.json").read_text(encoding="utf-8")) V = json.loads((HERE / "판독" / "g3_values.json").read_text(encoding="utf-8")) P = json.loads((D / "params.json").read_text(encoding="utf-8")) X = json.loads((D / "expected.json").read_text(encoding="utf-8")) if "G3" in P["scope"]: sys.exit("G3 already in scope") bk = D / "backup" / "2026-10-15_g3" bk.mkdir(parents=True, exist_ok=True) for f in ("params.json", "expected.json"): shutil.copy2(D / f, bk / f) SCHED = {"B1": (10590, 31, "H25"), "B2": (12010, 31, "H25"), "B3": (10590, 30, "H25"), "B4": (12010, 30, "H25"), "B5": (11190, 27, "H25"), "B6": (13210, 27, "H25"), "B7": (11190, 26, "H25"), "B8": (13210, 26, "H25"), "B9": (6332, 45, "H19"), "B10": (32416, 4, "H19"), "B11": (7700, 11, "H19"), "B12": (7700, 23, "H19")} SHAPE = {m: "U" for m in SCHED} | {"B9": "tie-C", "B10": "loop"} P["scope"] = ["G1", "G2", "G3", "G5"] P["builders"]["G3"] = "rebar_polylines.py" P["rebar_marks"].update({m: {"dia": d, "shape": SHAPE[m]} for m, (_, _, d) in SCHED.items()}) P["footing_rebar"] = {"form": "polylines", "host": "FT", "group": "기초", "bars": B["bars"], "not_modelled": "UM 조립용 A자형 받침 H22 L 5,496 x 80 (F5: 기록만), 겹이음 j", "src": "Code/새재1교P1판독/extract_g3_bars.py -> 판독/g3_bars.json; 판독서 v0.1.02, 옥성교 결정 F1~F5 재적용, X방향 51곳 (R1)"} X["checkers"]["G3"] = "g3_sj.py" X["negative"]["G3"] = [{"mark": "B1", "d": [5, 0, 0]}, {"mark": "B10", "d": [0, 0, 5]}] X["planned_fail"] = [{"gate": "G3", "item": f"{m} bar count vs schedule", "reason": "작도 X방향 51곳(측면 점·사슬 '52@150=7.800 -300') 채택 vs 재료표 B5·B7 27·26, B6·B8 27·26 = 53 — OPEN #28", "approved": "사용자 2026-10-15"} for m in ("B5", "B6", "B7", "B8")] X["G3"] = { "schedule": {m: [L, n] for m, (L, n, _) in SCHED.items()}, "dia": {m: int(d[1:]) for m, (_, _, d) in SCHED.items()}, "half_a": 3750, "mats": {"y_bottom": {"marks": ["B2", "B4"], "axis": "Y", "z": 10132, "leg": 1800, "pos": V["y_bars_bottom"]["x"]}, "x_bottom": {"marks": ["B6", "B8"], "axis": "X", "z": 10154.5, "leg": 2400, "pos": V["x_bars_bottom"]["y"]}, "y_top": {"marks": ["B1", "B3"], "axis": "Y", "z": 12532, "leg": -900, "pos": V["y_bars_top"]["x"]}, "x_top": {"marks": ["B5", "B7"], "axis": "X", "z": 12509.5, "leg": -1200, "pos": V["x_bars_top"]["y"]}}, "mid": {"B12": {"axis": "Y", "lift": 19, "levels": V["mid_y_bars"]}, "B11": {"axis": "X", "lift": 0, "levels": V["mid_x_bars"]}}, "b10": {"levels": V["b10_levels"], "size": 7545}, "b9": {"rows": V["b9"]["rows"], "cols_even": V["b9"]["cols_even"], "cols_odd": V["b9"]["cols_odd"], "a": 1244, "height": 2444}, "src": "재료표 L·N·b; 정면 점 61(Y방향)·측면 점 51(X방향), 측면 EL +22.5 어긋남; 중간층 EL 10.732 / 11.332 / 11.632; B10 4단 ±3,772.5; " "B9 정면 연직선 15곳 @500 + 측면 다리 행 6 @1,200 (짝수 행 8·홀수 행 7); F3 교번; F4 B12 Y방향 +19; 상세 a 1,244 b 2,444"} (D / "params.json").write_text(json.dumps(P, ensure_ascii=False, indent=1), encoding="utf-8") (D / "expected.json").write_text(json.dumps(X, ensure_ascii=False, indent=1), encoding="utf-8") print("G3 added:", len(B["bars"]), "bars; backup", bk)