"""콤보 차트 (막대 + 선) 생성"""
from io import BytesIO
import matplotlib.pyplot as plt
import matplotlib.font_manager as fm
import numpy as np

from ..data_models import ChartData
from ..pdf.styles import CHART_COLORS


def setup_japanese_font():
    """일본어 폰트 설정"""
    # 사용 가능한 일본어 폰트 찾기
    font_candidates = [
        "Noto Sans CJK JP",
        "IPAGothic",
        "IPAPGothic",
        "TakaoPGothic",
        "VL PGothic",
        "DejaVu Sans",
    ]

    for font in font_candidates:
        try:
            fm.findfont(font, fallback_to_default=False)
            plt.rcParams["font.family"] = font
            return font
        except Exception:
            continue

    # 기본 폰트 사용
    plt.rcParams["font.family"] = "sans-serif"
    return "sans-serif"


def create_combo_chart(chart_data: ChartData) -> BytesIO:
    """콤보 차트 생성 (막대 + 선)

    Args:
        chart_data: 차트 데이터

    Returns:
        PNG 이미지 바이트 버퍼
    """
    setup_japanese_font()

    fig, ax1 = plt.subplots(figsize=(10, 5))

    labels = chart_data.labels
    x = np.arange(len(labels))
    width = 0.35

    bar_datasets = [d for d in chart_data.datasets if d.get("type") == "bar"]
    line_datasets = [d for d in chart_data.datasets if d.get("type") == "line"]

    # 막대 차트
    bar_offset = -width / 2
    for i, dataset in enumerate(bar_datasets):
        data = dataset.get("data", [])
        color = dataset.get("color", CHART_COLORS[i % len(CHART_COLORS)])
        label = dataset.get("label", f"Bar {i+1}")

        ax1.bar(
            x + bar_offset + (i * width / len(bar_datasets) if len(bar_datasets) > 1 else 0),
            data,
            width / len(bar_datasets) if len(bar_datasets) > 1 else width,
            label=label,
            color=color,
            alpha=0.8,
        )

    ax1.set_xlabel("")
    ax1.set_ylabel("金額", color=CHART_COLORS[0])
    ax1.tick_params(axis="y", labelcolor=CHART_COLORS[0])
    ax1.set_xticks(x)
    ax1.set_xticklabels(labels, rotation=45, ha="right")

    # Y축 포맷 (만 단위)
    ax1.yaxis.set_major_formatter(
        plt.FuncFormatter(lambda x, p: f"{x/10000:.0f}万" if x != 0 else "0")
    )

    # 선 차트 (두 번째 Y축)
    if line_datasets:
        ax2 = ax1.twinx()
        for i, dataset in enumerate(line_datasets):
            data = dataset.get("data", [])
            color = dataset.get("color", CHART_COLORS[(len(bar_datasets) + i) % len(CHART_COLORS)])
            label = dataset.get("label", f"Line {i+1}")
            dashed = dataset.get("dashed", False)

            ax2.plot(
                x,
                data,
                color=color,
                label=label,
                marker="o",
                markersize=4,
                linestyle="--" if dashed else "-",
                linewidth=2,
            )

        ax2.set_ylabel("利益", color=CHART_COLORS[2])
        ax2.tick_params(axis="y", labelcolor=CHART_COLORS[2])
        ax2.yaxis.set_major_formatter(
            plt.FuncFormatter(lambda x, p: f"{x/10000:.0f}万" if x != 0 else "0")
        )

    # 범례
    lines1, labels1 = ax1.get_legend_handles_labels()
    if line_datasets:
        lines2, labels2 = ax2.get_legend_handles_labels()
        ax1.legend(lines1 + lines2, labels1 + labels2, loc="upper left", fontsize=8)
    else:
        ax1.legend(loc="upper left", fontsize=8)

    # 타이틀
    if chart_data.title:
        plt.title(chart_data.title, fontsize=12, fontweight="bold")

    # 그리드
    ax1.grid(axis="y", alpha=0.3)
    ax1.set_axisbelow(True)

    plt.tight_layout()

    # 이미지로 저장
    buffer = BytesIO()
    plt.savefig(buffer, format="png", dpi=150, bbox_inches="tight")
    buffer.seek(0)
    plt.close(fig)

    return buffer
