import json, random, time

random.seed(42)
NOW = int(time.time() * 1000)
path = "/home/min/hermes_workspace/demo_review/ai_harness_final.excalidraw"
scene = json.load(open(path))

def text_dims(t, fs):
    lines = t.split("\n")
    width = max(sum(fs if ord(ch) > 0x2E80 else fs * 0.58 for ch in ln) for ln in lines)
    return round(width), round(fs * 1.25 * len(lines) + 2)

def base(e):
    e.setdefault("angle", 0)
    e.setdefault("strokeColor", "#1e1e1e")
    e.setdefault("backgroundColor", "transparent")
    e.setdefault("fillStyle", "solid")
    e.setdefault("strokeWidth", 2)
    e.setdefault("strokeStyle", "solid")
    e.setdefault("roughness", 1)
    e.setdefault("opacity", 100)
    e.setdefault("groupIds", [])
    e.setdefault("frameId", None)
    e.setdefault("roundness", None)
    e.setdefault("seed", random.randint(1, 2**31))
    e["version"] = 1
    e.setdefault("versionNonce", random.randint(1, 2**31))
    e["isDeleted"] = False
    e.setdefault("boundElements", None)
    e["updated"] = NOW
    e["link"] = None
    e["locked"] = False
    return e

out = []
for e in scene["elements"]:
    t = e["type"]
    if t == "text":
        base(e)
        e["fontFamily"] = 5  # current excalidraw hand font id (matches site exports)
        w, h = text_dims(e["text"], e["fontSize"])
        e["width"] = e.get("width") or w
        e["height"] = e.get("height") or h
        e.setdefault("textAlign", "center")
        e.setdefault("verticalAlign", "middle")
        e.setdefault("lineHeight", 1.25)
        e.setdefault("labelPosition", None)
        e.setdefault("containerId", None)
    elif t == "rectangle":
        base(e)
        e.setdefault("roundness", {"type": 3})
    elif t == "arrow":
        base(e)
        e.setdefault("startArrowhead", None)
        e.setdefault("lastCommittedPoint", None)
        e.setdefault("elbowed", False)
        for bk in ("startBinding", "endBinding"):
            if e.get(bk):
                e[bk].setdefault("mode", "orbit")
        pts = e["points"]
        e.setdefault("width", round(max(p[0] for p in pts) - min(p[0] for p in pts)))
        e.setdefault("height", round(max(p[1] for p in pts) - min(p[1] for p in pts)))
    out.append(e)

scene["elements"] = out
json.dump(scene, open(path, "w"), ensure_ascii=False, indent=2)

# report completeness
missing = []
req_text = {"width", "height", "lineHeight", "fontSize", "fontFamily", "text", "x", "y"}
for e in out:
    if e["type"] == "text" and not req_text.issubset(e.keys()):
        missing.append(e["id"])
print(f"normalized {len(out)} elements; text fields incomplete: {len(missing)}")