import json

path = "/home/min/hermes_workspace/demo_review/ai_harness_final.excalidraw"
scene = json.load(open(path))
els = scene["elements"]
by_id = {e["id"]: e for e in els}

def est_width(t, fs):
    lines = t.split("\n")
    return max(sum(fs if ord(ch) > 0x2E80 else fs * 0.55 for ch in ln) for ln in lines)

unbound = 0
for e in els:
    if e["type"] != "text":
        continue
    cid = e.get("containerId")
    if not cid:
        continue
    container = by_id.get(cid)
    if container is None:
        continue
    if container["type"] == "rectangle":
        w_est = est_width(e["text"], e["fontSize"])
        fs = e["fontSize"]
        lh = fs * 1.25
        n = len(e["text"].split("\n"))
        h_est = n * lh
        cx = container["x"] + container["width"] / 2
        cy = container["y"] + container["height"] / 2
        multi = n > 1 and ("・" in e["text"] or "•" in e["text"])
        e["x"] = int(cx - w_est / 2 - (10 if multi else 0))
        e["y"] = int(cy - h_est / 2 + fs * 0.35)
        e["textAlign"] = "left" if multi else "center"
    elif container["type"] == "arrow":
        pts = container["points"]
        cx = container["x"] + sum(p[0] for p in pts) / len(pts)
        cy = container["y"] + sum(p[1] for p in pts) / len(pts)
        w_est = est_width(e["text"], e["fontSize"])
        e["x"] = int(cx - w_est / 2)
        e["y"] = int(cy - e["fontSize"] * 1.1)
    # detach binding
    e["containerId"] = None
    e["labelPosition"] = None
    e["textAlign"] = e.get("textAlign", "center")
    if container.get("boundElements"):
        container["boundElements"] = [
            b for b in container["boundElements"] if b["id"] != e["id"]
        ] or None
    unbound += 1

scene["elements"] = els
json.dump(scene, open(path, "w"), ensure_ascii=False, indent=2)
print(f"unbound {unbound} texts to free positions")
# sanity: no containerIds left
left = [e["id"] for e in els if e.get("containerId")]
print("remaining bound texts:", left)