import os
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import matplotlib.ticker as mticker
import seaborn as sns
from scipy import stats
from scipy.stats import gaussian_kde

# Path Configuration
# MT5 terminal sandbox default path (Windows):
# C:\Users\<user>\AppData\Roaming\MetaQuotes\Terminal\<InstanceID>\MQL5\Files\
# Adjust DATA_PATH to point to your local MT5 Files directory.

BASE_DIR   = os.path.dirname(os.path.abspath(__file__))
DATA_PATH  = os.path.join(BASE_DIR, "exports", "analytics_export.csv")
OUTPUT_DIR = os.path.join(BASE_DIR, "charts")
os.makedirs(OUTPUT_DIR, exist_ok=True)

# Load the normalized analytics export
df = pd.read_csv(DATA_PATH)

# Global Style Configuration
plt.rcParams.update({
    "figure.facecolor"  : "#0d1117",
    "axes.facecolor"    : "#161b22",
    "axes.edgecolor"    : "#30363d",
    "axes.labelcolor"   : "#c9d1d9",
    "xtick.color"       : "#8b949e",
    "ytick.color"       : "#8b949e",
    "text.color"        : "#c9d1d9",
    "grid.color"        : "#21262d",
    "grid.linestyle"    : "--",
    "grid.linewidth"    : 0.6,
    "font.family"       : "monospace",
    "font.size"         : 9,
})


def plot_intraday_heatmap(df: pd.DataFrame,
                           metric: str = "Net_Profit_USD",
                           save_path: str = None):
    """
    Intraday and Intraweek Alpha Clusters (Hour-by-Day Performance Heatmap)

    Aggregates the chosen performance metric by Entry_Hour (0–23) and
    Entry_DayOfWeek (0=Monday, 4=Friday), then renders a seaborn heatmap
    with annotated cell values and session zone overlays.

    Parameters
    ----------
    df        : Full analytics DataFrame from CSV export.
    metric    : Column to aggregate into the heatmap cells.
    save_path : File path for saving the output figure (optional).
    """

    required = ["Entry_Hour", "Entry_DayOfWeek", metric]
    plot_df  = df[required].dropna().copy()
    plot_df["Entry_Hour"]      = plot_df["Entry_Hour"].astype(int)
    plot_df["Entry_DayOfWeek"] = plot_df["Entry_DayOfWeek"].astype(int)

    pivot = plot_df.pivot_table(index="Entry_Hour", columns="Entry_DayOfWeek",
                                values=metric, aggfunc="mean")
    pivot = pivot.reindex(index=range(24), columns=range(5), fill_value=0.0)

    day_labels = {0: "Mon", 1: "Tue", 2: "Wed", 3: "Thu", 4: "Fri"}
    pivot.rename(columns=day_labels, inplace=True)

    fig, ax = plt.subplots(figsize=(8.167, 7.6))
    fig.suptitle(
        f"Intraday Alpha Cluster Heatmap  |  {metric} by Session Hour and Weekday",
        fontsize=11, fontweight="bold", color="#e6edf3"
    )

    cmap = sns.diverging_palette(10, 130, as_cmap=True)

    sns.heatmap(pivot, ax=ax, cmap=cmap, center=0,
                linewidths=0.4, linecolor="#21262d",
                annot=True, fmt=".0f",
                annot_kws={"size": 6.5, "color": "#e6edf3"},
                cbar_kws={"label": metric, "shrink": 0.75, "pad": 0.02})

    # --- Session Zone Overlays (approximate UTC ranges)
    session_zones = [
        (0,  9,  "Asian",    "#388bfd", 0.06),
        (7,  16, "London",   "#3fb950", 0.06),
        (13, 22, "New York", "#d29922", 0.06),
    ]

    for row_start, row_end, label, color, alpha in session_zones:
        ax.add_patch(
            plt.Rectangle((0, row_start), len(pivot.columns), row_end - row_start,
                           fill=True, color=color, alpha=alpha, zorder=0)
        )
        ax.text(-0.35, (row_start + row_end) / 2, label,
                va="center", ha="right", fontsize=7,
                color=color, rotation=90, style="italic")

    ax.set_xlabel("Weekday", fontsize=9, labelpad=7)
    ax.set_ylabel("Entry Hour (UTC)", fontsize=9, labelpad=7)
    ax.tick_params(axis="both", labelsize=8)
    ax.set_yticklabels([f"{h:02d}:00" for h in range(24)], fontsize=7, rotation=0)

    cbar = ax.collections[0].colorbar
    cbar.ax.yaxis.label.set_color("#c9d1d9")
    cbar.ax.tick_params(labelcolor="#8b949e")

    plt.tight_layout()

    if save_path:
        plt.savefig(save_path, dpi=120, bbox_inches="tight",
                    facecolor=fig.get_facecolor())
    plt.show()


# Execute
plot_intraday_heatmap(
    df, metric="Net_Profit_USD",
    save_path=os.path.join(OUTPUT_DIR, "Intraday_Performance_Heatmap.png")
)
