"""After tools/space/paint_ship.sh: pack the painted copy (textures <= 1024, KTX2 + Draco like every library model), store it as a
blob and write the NEXT card version of the craft with files.painted_glb (card versions are immutable; the game model, its moving
parts and its Paint recolour are unchanged) + before/after strips for the review page.
usage: python3 tools/space/paint_card.py <job_dir> <editor gpt|nb2>"""
import hashlib, json, os, shutil, subprocess, sys, tempfile
from PIL import Image
ROOT = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
sys.path.insert(0, os.path.join(ROOT, 'lib'))
import glb, card as cardlib  # noqa: E402

EDITORS = {'gpt': 'GPT Image 2 (Codex)', 'nb2': 'Nano Banana 2', 'nbpro': 'Nano Banana Pro'}


def main(jd, editor):
    jd = os.path.abspath(jd); j = json.load(open(f'{jd}/job.json'))
    src = f'{jd}/painted/painted.glb'
    t = tempfile.mkdtemp(prefix='space-paint-')
    try:
        subprocess.run(['node', f'{ROOT}/tools/pack/pack_asset.mjs', src, f'{t}/p.glb', '--max', '1024', '--orm', '512', '--no-draco'],
                       check=True, capture_output=True)
        subprocess.run(['node', f'{ROOT}/tools/pack/pack-glb.mjs', t, '--ktx2', '--cache', f'{t}/cache'], check=True, capture_output=True)
        packed = f"{jd}/{j['slug']}-painted.glb"
        shutil.copyfile(f'{t}/p.glb', packed)
    finally:
        shutil.rmtree(t, ignore_errors=True)
    os.remove(src)   # the unpacked copy stays on gex44 (runs/space-20261016/out/<slug>/painted.glb); local disk is tight
    h = hashlib.sha256(open(packed, 'rb').read()).hexdigest()
    shutil.copyfile(packed, f'{ROOT}/store/blobs/{h}.glb')
    versions = cardlib.load_all(ROOT).get(j['id']) or []
    if not versions: sys.exit(f"no card for {j['id']}: run import_space.py first")
    c = json.loads(json.dumps(versions[-1]))
    if (c['files'].get('painted_glb') or '').endswith(h):
        print('painted copy already on', c['id'], 'v', c['version']); return
    rep = json.load(open(f'{jd}/painted/report.json')) if os.path.exists(f'{jd}/painted/report.json') else {}
    row = json.load(open(f'{jd}/painted-row.json')) if os.path.exists(f'{jd}/painted-row.json') else {}
    m = glb.measure(packed)
    c['version'] = max(v['version'] for v in versions) + 1
    c['files']['painted_glb'] = f'sha256:{h}'
    c['painted'] = {'editor': EDITORS.get(editor, editor), 'method': 'forge-repaint all-round (render, image edit, project back)',
                    'views_kept': row.get('kept'), 'views_tried': row.get('tried'), 'pictures': row.get('pictures'),
                    'outside_painted': rep.get('outside_painted'), 'tris': m['tris'], 'bytes': m['bytes'],
                    'gpu_mb_decoded': round(m['gpu_mb_decoded'], 1),
                    'how': 'files.painted_glb = a static one-material copy with the repainted texture: no moving parts and no Paint '
                           'recolour; use files.glb for gameplay'}
    c['techniques'] = sorted(set(c.get('techniques', [])) | {'repaint-all-round'})
    c['release'] = cardlib.release_hash(c)
    print(cardlib.write(ROOT, c), 'painted', m['bytes'], 'bytes')
    sheet = f'{jd}/painted/sheet.jpg'   # repaint sheet: BEFORE row (y 20..220) and AFTER row (y 240..440), 8 angles of 200 px
    if os.path.exists(sheet):
        im = Image.open(sheet).convert('RGB')
        im.crop((0, 20, 1600, 220)).save(f'{jd}/painted-before.jpg', quality=88)
        im.crop((0, 240, 1600, 440)).save(f'{jd}/painted-after.jpg', quality=88)


if __name__ == '__main__':
    main(sys.argv[1], sys.argv[2] if len(sys.argv) > 2 else 'gpt')
