# SPDX-License-Identifier: Apache-2.0
"""After pebble_enclosure.py: simplified meshes for the website (out_pebble/web/) and print.json."""
import json
from pathlib import Path
import trimesh

OUT = Path(__file__).parent / "out_pebble"
(OUT / "web").mkdir(exist_ok=True)
(OUT / "bed").mkdir(exist_ok=True)
FLIP = set()                 # every part prints the way up it sits in the device (checked: largest flat face on the bed)
SPEC = json.loads((Path(__file__).parent / "print_spec.json").read_text())["parts"]
MAT = {"top_shell": "PETG yellow", "bottom_shell": "PETG yellow", "eye_guide": "PETG white", "eye_lens": "PETG translucent",
       "read_button": "PETG yellow", "slider_caps": "PETG or TPU", "eye_cradle": "PETG any colour", "power_cap": "PETG white", "mic_cap": "PETG white", "bumper_band": "TPU 95A natural (translucent)", "foot": "TPU 95A", "post_washer": "TPU 95A",
       "test_coupons": "PETG yellow (the shells' spool)", "battery_deck": "PETG any colour", "board_straps": "PETG any colour"}
info = {}
N_POSTS = sum(1 for c in json.loads((OUT / "layout.json").read_text())["comps"] if c["name"].startswith("post"))
for n, mat in MAT.items():
    f = OUT / f"{n}.stl"
    if not f.exists():
        for stale in (OUT / "web" / f"{n}.stl", OUT / "bed" / f"{n}.stl"):
            stale.unlink(missing_ok=True)
        continue
    m = trimesh.load(f)
    m.merge_vertices()
    target = 40000 if "shell" in n else 20000
    w = m.simplify_quadric_decimation(face_count=target) if len(m.faces) > target else m
    if n not in ("post_washer", "test_coupons"):          # not drawn in the device
        w.export(OUT / "web" / f"{n}.stl")
    # print copy: on the bed (z = 0), centred, turned to its printing orientation
    b = m.copy()
    if n in FLIP:
        b.apply_transform(trimesh.transformations.rotation_matrix(3.141592653589793, [1, 0, 0]))
    if n in ("power_cap", "mic_cap"):            # lie on the head's flat face: the sleeve points up, the socket prints clean
        b.apply_transform(trimesh.transformations.rotation_matrix(3.141592653589793 / 2, [1, 0, 0]))
    lo, hi = b.bounds
    b.apply_translation([-(lo[0] + hi[0]) / 2, -(lo[1] + hi[1]) / 2, -lo[2]])
    b.export(OUT / "bed" / f"{n}.stl")
    dens = 1.21 if "TPU" in mat else 1.27
    qty = N_POSTS if n == "post_washer" else 1
    info[n] = {"size": [round(float(v), 1) for v in m.extents], "volume_cm3": round(float(m.volume) / 1000, 2),
               "mass_g": round(float(m.volume) / 1000 * dens * (N_POSTS if n == "post_washer" else 1), 1), "material": mat, "qty": qty, "faces": int(len(m.faces)),
               "file": f"{n}.stl", "src": f"bed/{n}.stl", "file_mb": round(f.stat().st_size / 1e6, 1), "spec": SPEC.get(n, {})}
json.dump(info, open(OUT / "print.json", "w"), indent=1)
print({k: v["mass_g"] for k, v in info.items()})

import stamps  # noqa: E402
stamps.write("web")
