import t, c
from stdint import *
import stdio
import memhub
import w32.win32console as w32cmd
import w32.win32file as w32file
import w32.win32base as w32base


# ============================================================
# VLogger - 原生日志系统（Windows 控制台彩色输出）
# ============================================================

# 日志级别
class LogLevel(t.CEnum):
    DEBUG = 0
    INFO = 1
    WARNING = 2
    ERROR = 3
    SUCCESS = 4


# Win32 控制台前景色属性
FOREGROUND_BLUE: t.CDefine = 0x0001
FOREGROUND_GREEN: t.CDefine = 0x0002
FOREGROUND_RED: t.CDefine = 0x0004
FOREGROUND_INTENSITY: t.CDefine = 0x0008
FOREGROUND_WHITE: t.CDefine = FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE
FOREGROUND_CYAN: t.CDefine = FOREGROUND_BLUE | FOREGROUND_GREEN
FOREGROUND_YELLOW: t.CDefine = FOREGROUND_RED | FOREGROUND_GREEN
FOREGROUND_MAGENTA: t.CDefine = FOREGROUND_RED | FOREGROUND_BLUE

# Win32 控制台背景色属性
BACKGROUND_RED: t.CDefine = 0x0040
BACKGROUND_GREEN: t.CDefine = 0x0020
BACKGROUND_BLUE: t.CDefine = 0x0010
BACKGROUND_INTENSITY: t.CDefine = 0x0080
BACKGROUND_WHITE: t.CDefine = BACKGROUND_RED | BACKGROUND_GREEN | BACKGROUND_BLUE


class Logger:
    _level: int
    _console_handle: w32base.HANDLE
    _use_color: int
    __mbuddy__: memhub.MemManager | t.CPtr

    def __init__(self, level: int = 1):
        self._level = level
        self._console_handle = w32file.GetStdHandle(w32file.STD_OUTPUT_HANDLE)
        self._use_color = 1
        self.__mbuddy__ = _mbuddy

    def _set_color(self, attr: WORD) -> int:
        if self._use_color:
            return w32cmd.SetConsoleTextAttribute(self._console_handle, attr)
        return 0

    def _reset_color(self) -> int:
        if self._use_color:
            return w32cmd.SetConsoleTextAttribute(self._console_handle, FOREGROUND_WHITE)
        return 0

    def _log(self, level: int, prefix: str, msg: str, color: WORD,
             category: str = "") -> int:
        if level < self._level:
            return 0
        self._set_color(color)
        if category is not None:
            if category[0] != 0:
                stdio.printf("%s[%s] %s\n", prefix, category, msg)
            else:
                stdio.printf("%s %s\n", prefix, msg)
        else:
            stdio.printf("%s %s\n", prefix, msg)
        self._reset_color()
        return 0

    def debug(self, msg: str, category: str = "") -> int:
        return self._log(LogLevel.DEBUG, "[DEBUG]", msg,
                         FOREGROUND_INTENSITY, category)

    def info(self, msg: str, category: str = "") -> int:
        return self._log(LogLevel.INFO, "[INFO]", msg,
                         FOREGROUND_GREEN | FOREGROUND_INTENSITY, category)

    def warning(self, msg: str, category: str = "") -> int:
        return self._log(LogLevel.WARNING, "[WARN]", msg,
                         FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_INTENSITY,
                         category)

    def error(self, msg: str, category: str = "") -> int:
        return self._log(LogLevel.ERROR, "[ERROR]", msg,
                         FOREGROUND_RED | FOREGROUND_INTENSITY, category)

    def success(self, msg: str, category: str = "") -> int:
        return self._log(LogLevel.SUCCESS, "[SUCCESS]", msg,
                         FOREGROUND_GREEN | FOREGROUND_INTENSITY, category)

    def set_level(self, level: int) -> int:
        self._level = level
        return 0

    # ============================================================
    # 高级日志方法
    # ============================================================

    def banner(self, msg: str) -> int:
        """输出分节标题（青色高亮）。"""
        self._set_color(FOREGROUND_CYAN | FOREGROUND_INTENSITY)
        stdio.printf("\n=== %s ===\n\n", msg)
        self._reset_color()
        return 0

    def compile_error(self, msg: str, file: str = "", line: int = 0) -> int:
        """格式化编译错误输出（红底白字标题 + 位置 + 错误信息）。"""
        self._set_color(BACKGROUND_RED | FOREGROUND_WHITE | FOREGROUND_INTENSITY)
        stdio.printf(" 编译错误 ")
        self._set_color(FOREGROUND_RED | FOREGROUND_INTENSITY)
        stdio.printf("\n")
        if file is not None:
            if file[0] != 0 and line > 0:
                stdio.printf("  位置: %s:%d\n", file, line)
            elif file[0] != 0:
                stdio.printf("  文件: %s\n", file)
        stdio.printf("  错误: %s\n", msg)
        self._reset_color()
        return 0

    def compile_warning(self, msg: str, file: str = "", line: int = 0) -> int:
        """格式化编译警告输出（黄底黑字标题 + 位置 + 警告信息）。"""
        self._set_color(BACKGROUND_RED | BACKGROUND_GREEN | FOREGROUND_INTENSITY)
        stdio.printf(" 编译警告 ")
        self._set_color(FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_INTENSITY)
        stdio.printf("\n")
        if file is not None:
            if file[0] != 0 and line > 0:
                stdio.printf("  位置: %s:%d\n", file, line)
            elif file[0] != 0:
                stdio.printf("  文件: %s\n", file)
        stdio.printf("  警告: %s\n", msg)
        self._reset_color()
        return 0


# 全局 mbuddy 指针（由 lib.InitLib 注入）
_mbuddy: memhub.MemManager | t.CPtr

# 全局 logger 指针
_g_logger: Logger | t.CPtr


def get_logger() -> Logger | t.CPtr:
    """获取全局 logger 实例。若不存在则通过 _mbuddy 分配并初始化。"""
    if _g_logger is None:
        if _mbuddy is None:
            return None
        raw: t.CVoid | t.CPtr = _mbuddy.alloc(Logger.__sizeof__())
        if raw is None:
            return None
        _g_logger = raw
        _g_logger._level = LogLevel.INFO
        _g_logger._console_handle = w32file.GetStdHandle(w32file.STD_OUTPUT_HANDLE)
        _g_logger._use_color = 1
        _g_logger.__mbuddy__ = _mbuddy
    return _g_logger


def set_logger(logger: Logger | t.CPtr) -> int:
    """设置全局 logger 实例。"""
    _g_logger = logger
    return 0
