# scripts/plot_sun_elevation_relationships.py
from __future__ import annotations

from pathlib import Path

import numpy as np

from meteo.dataset import load_raw_csv
from meteo.variables import VARIABLES_BY_KEY
from meteo.analysis import compute_binned_statistics
from meteo.plots import plot_binned_profiles, plot_hexbin_with_third_variable
from meteo.config import StationLocation
from meteo.solar import add_solar_elevation_column


CSV_PATH = Path("data/weather_minutely.csv")
OUTPUT_DIR = Path("figures/sun")


def ensure_sun_elevation(df):
    if "sun_elevation" in df.columns:
        return df

    print("ℹ La colonne 'sun_elevation' est absente, tentative de calcul à la volée.")
    location = StationLocation.from_env(optional=True)
    if location is None:
        print(
            "⚠ Impossible de calculer l'élévation solaire : définissez STATION_LATITUDE et STATION_LONGITUDE "
            "puis regénérez le dataset (scripts/make_minutely_dataset)."
        )
        return None

    print(
        f"→ Calcul d'élévation solaire avec lat={location.latitude}, lon={location.longitude}, "
        f"alt={location.elevation_m} m."
    )
    add_solar_elevation_column(
        df,
        latitude=location.latitude,
        longitude=location.longitude,
        elevation_m=location.elevation_m,
    )
    return df


def main() -> None:
    if not CSV_PATH.exists():
        print(f"⚠ Fichier introuvable : {CSV_PATH}")
        return

    df = load_raw_csv(CSV_PATH)
    print(f"Dataset minuté chargé : {CSV_PATH}")
    print(f"  Lignes   : {len(df)}")
    print(f"  Colonnes : {list(df.columns)}")
    print()

    df = ensure_sun_elevation(df)
    if df is None or "sun_elevation" not in df.columns:
        return

    OUTPUT_DIR.mkdir(parents=True, exist_ok=True)

    profile_keys = ["temperature", "humidity", "illuminance"]
    profile_vars = [VARIABLES_BY_KEY[key] for key in profile_keys]
    bins = np.arange(-90, 95, 5)  # bins de 5°

    stats = compute_binned_statistics(
        df=df,
        bin_source_column="sun_elevation",
        target_columns=[v.column for v in profile_vars],
        bins=bins,
        min_count=100,
        quantiles=(0.2, 0.8),
    )

    profile_output = OUTPUT_DIR / "sun_elevation_profiles.png"
    plot_binned_profiles(
        stats=stats,
        variables=profile_vars,
        output_path=profile_output,
        xlabel="Élévation solaire (°)",
        title="Profils moyens en fonction de l'élévation solaire",
        show_counts=True,
    )
    print(f"✔ Profils sun vs variables : {profile_output}")

    hexbin_scenarios = [
        {
            "x": "sun_elevation",
            "y": "illuminance",
            "color": "temperature",
            "filename": "hexbin_sun_elevation_vs_illuminance.png",
            "description": "Illuminance en fonction de l'élévation du soleil, couleur = température.",
        },
        {
            "x": "sun_elevation",
            "y": "temperature",
            "color": "humidity",
            "filename": "hexbin_sun_elevation_vs_temperature.png",
            "description": "Température en fonction de l'élévation, couleur = humidité relative.",
        },
    ]

    for scenario in hexbin_scenarios:
        var_x = VARIABLES_BY_KEY[scenario["x"]]
        var_y = VARIABLES_BY_KEY[scenario["y"]]
        var_color = VARIABLES_BY_KEY[scenario["color"]]
        output_path = OUTPUT_DIR / scenario["filename"]

        print(f"→ {scenario['description']}")
        plot_hexbin_with_third_variable(
            df=df,
            var_x=var_x,
            var_y=var_y,
            var_color=var_color,
            output_path=output_path,
            gridsize=60,
            mincnt=10,
            reduce_func_label="moyenne",
            cmap="cividis",
        )
        print(f"   ✔ Hexbin enregistré : {output_path}")

    print("✔ Tous les graphiques liés à l'élévation solaire ont été produits.")


if __name__ == "__main__":
    main()
