import sys
from pathlib import Path

from PIL import ImageFont

_cache: dict[tuple[bool, int], ImageFont.FreeTypeFont | ImageFont.ImageFont] = {}
_regular_path: str | None = None
_bold_path: str | None = None
_initialized: bool = False

# 项目内置字体目录：src/render/pillow/fonts/
# 支持 .ttf / .ttc / .otf，文件名含 "bold" 的优先用作粗体
_LOCAL_FONTS_DIR = Path(__file__).parent / "fonts"

_CANDIDATES: dict[str, dict[bool, list[str]]] = {
    "win32": {
        False: [
            "C:/Windows/Fonts/msyh.ttc",
            "C:/Windows/Fonts/simsun.ttc",
            "C:/Windows/Fonts/simhei.ttf",
        ],
        True: [
            "C:/Windows/Fonts/msyhbd.ttc",
            "C:/Windows/Fonts/simhei.ttf",
            "C:/Windows/Fonts/msyh.ttc",
        ],
    },
    "darwin": {
        False: [
            "/System/Library/Fonts/PingFang.ttc",
            "/System/Library/Fonts/Supplemental/Arial Unicode MS.ttf",
        ],
        True: [
            "/System/Library/Fonts/PingFang.ttc",
        ],
    },
    "linux": {
        False: [
            "/usr/share/fonts/opentype/noto/NotoSansCJK-Regular.ttc",
            "/usr/share/fonts/noto-cjk/NotoSansCJK-Regular.ttc",
            "/usr/share/fonts/truetype/noto/NotoSansSC-Regular.otf",
            "/usr/share/fonts/google-noto-cjk/NotoSansCJK-Regular.ttc",
            "/usr/share/fonts/noto/NotoSansCJK-Regular.ttc",
            "/usr/share/fonts/truetype/dejavu/DejaVuSans.ttf",
        ],
        True: [
            "/usr/share/fonts/opentype/noto/NotoSansCJK-Bold.ttc",
            "/usr/share/fonts/noto-cjk/NotoSansCJK-Bold.ttc",
            "/usr/share/fonts/truetype/noto/NotoSansSC-Bold.otf",
            "/usr/share/fonts/truetype/dejavu/DejaVuSans-Bold.ttf",
        ],
    },
}


def _scan_local_fonts() -> tuple[str | None, str | None]:
    """
    扫描 src/render/pillow/fonts/ 目录，返回 (regular_path, bold_path)。
    规则：
      - 文件名包含 "bold"（不区分大小写）→ 优先作为粗体
      - 其余文件 → 作为常规字体
      - 若只找到一个文件，常规和粗体均使用它
    """
    if not _LOCAL_FONTS_DIR.is_dir():
        return None, None

    exts = {".ttf", ".ttc", ".otf"}
    all_fonts = [p for p in _LOCAL_FONTS_DIR.iterdir() if p.suffix.lower() in exts]
    if not all_fonts:
        return None, None

    bold_fonts = [p for p in all_fonts if "bold" in p.stem.lower()]
    regular_fonts = [p for p in all_fonts if p not in bold_fonts]

    regular = str(regular_fonts[0]) if regular_fonts else str(all_fonts[0])
    bold = str(bold_fonts[0]) if bold_fonts else regular
    return regular, bold


def _init() -> None:
    global _regular_path, _bold_path, _initialized
    if _initialized:
        return

    # 1. 优先使用项目内 fonts/ 目录
    local_regular, local_bold = _scan_local_fonts()
    if local_regular:
        _regular_path = local_regular
        _bold_path = local_bold
        _initialized = True
        return

    # 2. 回退到系统字体
    platform = sys.platform if sys.platform in _CANDIDATES else "linux"

    def _find(bold: bool) -> str | None:
        for p in _CANDIDATES[platform][bold]:
            if Path(p).exists():
                return p
        for plat_cands in _CANDIDATES.values():
            for p in plat_cands[False]:
                if Path(p).exists():
                    return p
        return None

    _regular_path = _find(False)
    _bold_path = _find(True) or _regular_path
    _initialized = True


def get_font(
    size: int, bold: bool = False
) -> ImageFont.FreeTypeFont | ImageFont.ImageFont:
    """Return a CJK-compatible font at the requested size."""
    _init()
    key = (bold, size)
    if key in _cache:
        return _cache[key]

    path = _bold_path if bold else _regular_path
    if path:
        try:
            font = ImageFont.truetype(path, size)
            _cache[key] = font
            return font
        except Exception:
            pass

    # Ultimate fallback: PIL built-in bitmap font
    try:
        fb: ImageFont.FreeTypeFont | ImageFont.ImageFont = ImageFont.load_default(
            size=size
        )
    except TypeError:
        fb = ImageFont.load_default()
    _cache[key] = fb
    return fb
