# flake8: noqa T001, E501
# -*- coding: utf-8 -*-
"""
Ragone Plot Example

Energy density vs power density plot using simulated battery data.
"""

import BTAnalysisPyInterface as bta
import numpy as np
import pandas as pd


def simulate_battery_data(chemistry, mass_g, nominal_capacity_mAh, avg_voltage, c_rate):
    """Simulate battery discharge data with realistic internal resistance"""

    # Internal resistance (mΩ) - varies by chemistry
    resistance_mohm = {
        "NMC": 50,  # Low resistance
        "LFP": 80,  # Moderate
        "LTO": 30,  # Very low (high power)
        "NCA": 45,  # Low
    }.get(chemistry, 60)

    r_internal = resistance_mohm / 1000.0  # Convert to Ohms

    # Calculate current based on C-rate
    current = (nominal_capacity_mAh / 1000.0) * c_rate  # A

    # Discharge duration (lower at higher C-rate due to losses)
    # Peukert effect: capacity decreases at high discharge rates
    capacity_factor = 1.0 / (1.0 + 0.1 * (c_rate - 1.0))  # Capacity loss
    effective_capacity = nominal_capacity_mAh * capacity_factor
    duration = (effective_capacity / 1000.0) / current * 3600  # seconds

    time = np.linspace(0, duration, 100)

    # Voltage drops due to:
    # 1. State of charge (SOC) depletion
    # 2. Internal resistance (V = V_oc - I*R)
    soc = 1.0 - time / duration  # State of charge
    v_opencircuit = avg_voltage * (0.95 + 0.05 * soc)  # Slight voltage sag with SOC
    v_drop = current * r_internal  # Ohmic drop
    voltage = v_opencircuit - v_drop

    # Power and energy
    power = voltage * current
    energy_wh = np.trapezoid(power, time) / 3600

    return {
        "chemistry": chemistry,
        "mass_g": mass_g,
        "capacity_mAh": nominal_capacity_mAh,
        "c_rate": c_rate,
        "energy_wh": energy_wh,
        "avg_power_w": np.mean(power),
        "time": time,
        "voltage": voltage,
        "current": current,
    }


def main():
    bta.print("Generating Ragone plot with simulated data...")

    # Simulate different battery chemistries
    batteries = [
        # (chemistry, mass_g, capacity_mAh, avg_voltage, avg_current)
        ("NMC", 45.0, 3000, 3.7, 3.0),  # High energy
        ("NMC", 48.0, 3200, 3.7, 3.2),  # High energy variant
        ("LFP", 50.0, 2800, 3.3, 2.8),  # Moderate energy
        ("LFP", 52.0, 2900, 3.3, 2.9),  # Moderate energy variant
        ("LTO", 55.0, 2000, 2.4, 2.0),  # Lower energy, high power
        ("NCA", 43.0, 3100, 3.6, 3.1),  # High energy, high power
    ]

    # Create graph
    graph = bta.add_graph(
        title="Ragone Plot - Energy vs Power Density",
        xAxis="Power Density",
        y1Axis="Energy Density",
        x_unit="W/kg",
        y1_unit="W.h/kg",
    )

    # Storage for results
    results = []

    # Process each simulated battery at different C-rates
    for chemistry, mass_g, capacity, base_voltage, _ in batteries:
        # Simulate at different C-rates (0.5C to 5C)
        c_rates = [0.5, 1.0, 2.0, 3.0, 5.0]

        # Storage for this battery's curve
        power_points = []
        energy_points = []

        for c_rate in c_rates:
            # Calculate current based on C-rate
            current = (capacity / 1000.0) * c_rate

            # Simulate battery data
            data = simulate_battery_data(
                chemistry, mass_g, capacity, base_voltage, c_rate
            )

            # Calculate densities
            mass_kg = mass_g / 1000.0
            energy_density = data["energy_wh"] / mass_kg
            power_density = data["avg_power_w"] / mass_kg

            # Collect points for this battery's curve
            power_points.append(power_density)
            energy_points.append(energy_density)

            # Store result for table
            results.append(
                {
                    "Mass (g)": float(mass_g),
                    "Energy Density (Wh/kg)": float(round(energy_density, 2)),
                    "Power Density (W/kg)": float(round(power_density, 2)),
                }
            )

        # Create Series for this battery
        power_series = bta.Series("Power Density")
        power_series.add_values(power_points)

        energy_series = bta.Series("Energy Density")
        energy_series.add_values(energy_points)

        # Add as a single curve with label
        label = f"{chemistry} ({mass_g:.0f}g)"
        graph.add_series(label, power_series, energy_series)

        bta.print(f"✓ {chemistry}: {len(c_rates)} C-rates simulated")

    # Create results table
    table = bta.add_table(
        columns=["Mass (g)", "Energy Density (Wh/kg)", "Power Density (W/kg)"],
        title="Ragone Plot Data",
    )

    for result in results:
        table.add_row(result)

    bta.print(f"✓ Ragone plot created with {len(results)} simulated batteries")

    # Export
    table.export_to_csv("ragone_data.csv")
    graph.export_to_csv("ragone_plot.csv")

    bta.print("=== Battery Chemistry Comparison ===")
    bta.print("NMC: High energy density (200-250 Wh/kg)")
    bta.print("LFP: Moderate energy, good safety (150-180 Wh/kg)")
    bta.print("LTO: Lower energy, very high power (70-90 Wh/kg)")
    bta.print("NCA: High energy and power (220-260 Wh/kg)")


if __name__ == "__main__":
    main()
