# docs/examples/example_basic_capacity.py

"""
Example: Basic Capacity Calculation and Validation

This script demonstrates a fundamental workflow in BatteryProc:
1.  Loading a simple CSV data file.
2.  Normalizing the inputs to the canonical format required by the formula engine.
3.  Computing the per-cycle charge/discharge capacity and Coulombic efficiency.
4.  Comparing the recomputed values to the 'capacity_mAh' column from the source file.
5.  Plotting the results for visual inspection.

This example uses the `sample_3cycles.csv` dataset, which contains clean,
well-formed data.
"""

import matplotlib.pyplot as plt
import pandas as pd

from batteryproc.formulas import normalize_inputs, per_cycle_capacity_summary


def run_basic_capacity_example():
    """
    Loads sample data, computes per-cycle capacity, and prints a summary.
    """
    print("--- Running Basic Capacity Example ---")

    # 1. Load data from a CSV file
    try:
        df = pd.read_csv("docs/examples/sample_3cycles.csv")
        print("Loaded sample_3cycles.csv successfully.")
    except FileNotFoundError:
        print("Error: sample_3cycles.csv not found. Make sure you are running from the repo root.")
        return

    # 2. Normalize inputs for the formula engine
    # This step ensures column names and units are standardized.
    inputs = normalize_inputs(df)
    print("Inputs normalized for the formula engine.")

    # 3. Compute per-cycle capacity summary
    # The `per_cycle_capacity_summary` function is a high-level helper that
    # runs the core integration and aggregation logic.
    # We can optionally provide an active mass to get specific capacity.
    mass_g = 0.523  # Example active mass in grams
    summary = per_cycle_capacity_summary(inputs, mass_g=mass_g)
    print("\nComputed Per-Cycle Capacity Summary:")
    print(summary)

    # The summary DataFrame contains both the recomputed capacity and efficiency,
    # as well as specific capacity since we provided a mass.

    # 4. Plotting the results
    fig, ax1 = plt.subplots(figsize=(10, 6))

    ax1.plot(
        summary["cycle_index"],
        summary["charge_mAh"],
        "o-",
        color="blue",
        label="Charge Capacity (mAh)",
    )
    ax1.plot(
        summary["cycle_index"],
        summary["discharge_mAh"],
        "o-",
        color="green",
        label="Discharge Capacity (mAh)",
    )
    ax1.set_xlabel("Cycle Index")
    ax1.set_ylabel("Capacity (mAh)", color="blue")
    ax1.tick_params(axis="y", labelcolor="blue")
    ax1.grid(True)

    # Create a second y-axis for Coulombic Efficiency
    ax2 = ax1.twinx()
    ax2.plot(
        summary["cycle_index"],
        summary["coulombic_efficiency_percent"],
        "s--",
        color="red",
        label="Coulombic Efficiency (%)",
    )
    ax2.set_ylabel("Coulombic Efficiency (%)", color="red")
    ax2.tick_params(axis="y", labelcolor="red")
    ax2.set_ylim(80, 105)  # Typical range for CE

    # Collect legend handles and labels from both axes and combine them
    h1, l1 = ax1.get_legend_handles_labels()
    h2, l2 = ax2.get_legend_handles_labels()
    handles = h1 + h2
    labels = l1 + l2

    # Use a figure-level suptitle for multi-axis figures and make layout room
    fig.suptitle("Per-Cycle Capacity and Coulombic Efficiency")
    fig.tight_layout(rect=[0, 0, 1, 0.95])
    fig.legend(handles, labels, loc="upper right", bbox_to_anchor=(0.9, 0.9))

    # Save the plot
    output_path = "docs/examples/basic_capacity_plot.png"
    plt.savefig(output_path)
    print(f"\nPlot saved to {output_path}")
    # plt.show()


if __name__ == "__main__":
    run_basic_capacity_example()
