"""TEST_01 用「輝度マップ形状の追跡」比較パネルを生成する.

各改善 Step での輝度マップの「形」を 2×2 グリッドで並べ，
タイトルに主要指標 (mean / CoV / 勾配 % / C/P) を併記する.

形を見せる目的なので各画像は個別正規化 (sm-evaluate デフォルト) のまま使う.
共有 colorbar にすると絶対値の差にばかり目が行き「形の異同」が見えにくくなる.

使い方:
    uv run python scripts/build_luminance_evolution_panel.py

出力:
    docs/06_TEST/figures/luminance_map_evolution.png

新しい改善 Step を追加する場合は PANELS リストに 1 エントリ追加するだけ.
"""

from __future__ import annotations

import csv
from pathlib import Path

import matplotlib.image as mpimg
import matplotlib.pyplot as plt

ROOT = Path(__file__).resolve().parents[1]


def _load_metrics(csv_path: Path) -> dict[str, float]:
    """sm-evaluate が書き出す metrics.csv から主要指標を取り出す."""
    with csv_path.open(encoding="utf-8") as f:
        row = next(csv.DictReader(f))
    return {
        "mean": float(row["mean"]),
        "CoV": float(row["cov"]),
        "grad": float(row["gradient_magnitude"]),
        "CP": float(row["center_periphery_ratio"]),
    }


# パネル定義. ここに新規 Step を追加すれば自動で並ぶ.
PANELS = [
    {
        "image": ROOT / "MiniTias-Evaluation" / "figures" / "luminance_map_sample.png",
        "title": "Real Measurement (TARGET)",
        "subtitle": "central peak, near-symmetric (camera optics anisotropy)",
        "metrics": {"mean": 146.71, "CoV": 0.0427, "grad": 6.10, "CP": 1.065},
    },
    {
        "image": ROOT / "output" / "baseline_linear_npy" / "figures" / "luminance_map.png",
        "title": "Step 8-1: Starting Point",
        "subtitle": "R=0.85, d=8, spp=1024, linear (no OETF)",
        "metrics_csv": ROOT / "output" / "baseline_linear_npy" / "metrics.csv",
    },
    {
        "image": ROOT / "output" / "eval_oetf_r085" / "figures" / "luminance_map.png",
        "title": "Step 8-3: After OETF Forward Application",
        "subtitle": "R=0.85, d=8, spp=1024, sRGB domain",
        "metrics_csv": ROOT / "output" / "eval_oetf_r085" / "metrics.csv",
    },
    {
        "image": ROOT / "output" / "emitter_real" / "figures" / "luminance_map.png",
        "title": "Step 8-7: Real-chip Emitter Size (Φe preserved)",
        "subtitle": "size 1.5x1.5 mm, linear",
        "metrics_csv": ROOT / "output" / "emitter_real" / "metrics.csv",
    },
]


def main() -> None:
    fig, axes = plt.subplots(2, 2, figsize=(14, 13))
    for ax, panel in zip(axes.flatten(), PANELS):
        img_path = panel["image"]
        if not img_path.is_file():
            ax.text(0.5, 0.5, f"MISSING\n{img_path}", ha="center", va="center")
            ax.set_axis_off()
            continue
        ax.imshow(mpimg.imread(img_path))
        ax.set_axis_off()

        metrics = panel.get("metrics")
        if metrics is None and "metrics_csv" in panel:
            metrics = _load_metrics(panel["metrics_csv"])

        m = metrics
        title = (
            f"{panel['title']}\n"
            f"{panel['subtitle']}\n"
            f"mean={m['mean']:.2f}  CoV={m['CoV']:.4f}  "
            f"grad={m['grad']:.2f}%  C/P={m['CP']:.3f}"
        )
        ax.set_title(title, fontsize=10, loc="left")

    fig.suptitle(
        "Luminance Map Shape Tracking across Calibration Steps",
        fontsize=14,
        fontweight="bold",
    )
    plt.tight_layout(rect=(0, 0, 1, 0.97))

    out_dir = ROOT / "docs" / "06_TEST" / "figures"
    out_dir.mkdir(parents=True, exist_ok=True)
    out_path = out_dir / "luminance_map_evolution.png"
    plt.savefig(out_path, dpi=120, bbox_inches="tight")
    print(f"Saved: {out_path}")


if __name__ == "__main__":
    main()
