"""
Theme Composition System for Qt Styles
======================================

提供主题继承、组合和自定义功能的高级主题系统。
"""

from __future__ import annotations

from abc import ABC, abstractmethod
from dataclasses import dataclass, field


@dataclass
class ThemeConfig:
    """主题配置数据类."""

    name: str
    colors: dict[str, str] = field(default_factory=dict)
    dimensions: dict[str, int] = field(default_factory=dict)
    fonts: dict[str, str] = field(default_factory=dict)
    parent: BaseTheme | None = None


class BaseTheme(ABC):
    """主题基类 - 定义主题的通用接口."""

    def __init__(self, config: ThemeConfig):
        self.config = config
        self._cached_stylesheet: str | None = None

    @property
    @abstractmethod
    def name(self) -> str:
        """获取主题名称."""
        pass

    @abstractmethod
    def _generate_stylesheet_template(self) -> str:
        """生成样式表模板."""
        pass

    def get_stylesheet(self) -> str:
        """获取完整样式表."""
        if self._cached_stylesheet is None:
            self._cached_stylesheet = self._render_stylesheet()
        return self._cached_stylesheet

    def invalidate_cache(self) -> None:
        """使缓存失效."""
        self._cached_stylesheet = None

    def _render_stylesheet(self) -> str:
        """渲染完整的样式表."""
        template = self._generate_stylesheet_template()

        # 合并父主题和当前主题的配置
        merged_colors = self._merge_colors()
        merged_dimensions = self._merge_dimensions()
        merged_fonts = self._merge_fonts()

        # 替换模板中的占位符
        stylesheet = template
        for key, value in merged_colors.items():
            stylesheet = stylesheet.replace(f"{{{key}}}", str(value))
        for key, value in merged_dimensions.items():
            stylesheet = stylesheet.replace(f"{{{key}}}", str(value))
        for key, value in merged_fonts.items():
            stylesheet = stylesheet.replace(f"{{{key}}}", str(value))

        return stylesheet

    def _merge_colors(self) -> dict[str, str]:
        """合并颜色配置."""
        colors = {}
        if self.config.parent:
            colors.update(self.config.parent._merge_colors())
        colors.update(self.config.colors)
        return colors

    def _merge_dimensions(self) -> dict[str, int]:
        """合并尺寸配置."""
        dimensions = {}
        if self.config.parent:
            dimensions.update(self.config.parent._merge_dimensions())
        dimensions.update(self.config.dimensions)
        return dimensions

    def _merge_fonts(self) -> dict[str, str]:
        """合并字体配置."""
        fonts = {}
        if self.config.parent:
            fonts.update(self.config.parent._merge_fonts())
        fonts.update(self.config.fonts)
        return fonts


class CustomTheme(BaseTheme):
    """自定义主题类 - 允许完全自定义的主题创建."""

    def __init__(self, config: ThemeConfig):
        super().__init__(config)

    @property
    def name(self) -> str:
        return self.config.name

    def _generate_stylesheet_template(self) -> str:
        """生成自定义样式表模板."""
        # 这里可以实现更复杂的模板系统
        # 目前返回一个基础模板
        return self._get_base_template()

    def _get_base_template(self) -> str:
        """获取基础样式表模板."""
        return f"""
/* =============================================================================
   {self.name.upper()} THEME
   ============================================================================= */

QMainWindow, QDialog {{
    background-color: {{BACKGROUND_SOFT}};
    font-family: {{FONT_FAMILY}};
    font-size: {{FONT_SIZE_LARGE}};
    color: {{TEXT_DARK}};
}}

QWidget {{
    font-family: {{FONT_FAMILY}};
    font-size: {{FONT_SIZE_LARGE}};
    color: {{TEXT_DARK}};
}}

QPushButton {{
    background: {{PRIMARY_BLUE}};
    color: white;
    border: none;
    border-radius: {{BORDER_RADIUS_MEDIUM}}px;
    padding: {{PADDING_MEDIUM}}px {{PADDING_LARGE}}px;
    font-size: {{FONT_SIZE_MEDIUM}};
    min-height: {{BUTTON_HEIGHT}}px;
}}

QPushButton:hover {{
    background: {{SECONDARY_BLUE}};
}}

/* 更多样式定义... */

/* =============================================================================
   END OF {self.name.upper()} THEME
   ============================================================================= */
"""


class ThemeBuilder:
    """主题构建器 - 提供流畅的 API 来创建自定义主题."""

    def __init__(self, name: str):
        self.config = ThemeConfig(name=name)

    def inherit_from(
        self, parent_theme: type[BaseTheme] | BaseTheme
    ) -> ThemeBuilder:
        """从现有主题继承."""
        if isinstance(parent_theme, type) and issubclass(parent_theme, BaseTheme):
            # 如果传入的是类，创建实例
            parent_instance = parent_theme.__new__(parent_theme)
            parent_instance.config = ThemeConfig(name=parent_theme.__name__)
            self.config.parent = parent_instance
        elif hasattr(parent_theme, "config"):
            # 如果是已有实例
            self.config.parent = parent_theme
        else:
            # 如果是其他类型的对象（如 ModernBlueTheme 类）
            # 创建适配器包装器
            adapter = self._create_theme_adapter(parent_theme)
            self.config.parent = adapter
        return self

    def _create_theme_adapter(self, theme_obj) -> BaseTheme:
        """为现有主题对象创建适配器."""
        # 这里可以实现更复杂的适配逻辑
        # 目前简单地创建一个基本适配器
        adapter_config = ThemeConfig(
            name=theme_obj.__class__.__name__
            if hasattr(theme_obj, "__class__")
            else str(theme_obj)
        )
        return CustomTheme(adapter_config)

    def set_color(self, name: str, value: str) -> ThemeBuilder:
        """设置颜色."""
        self.config.colors[name] = value
        return self

    def set_dimension(self, name: str, value: int) -> ThemeBuilder:
        """设置尺寸."""
        self.config.dimensions[name] = value
        return self

    def set_font(self, name: str, value: str) -> ThemeBuilder:
        """设置字体."""
        self.config.fonts[name] = value
        return self

    def build(self) -> CustomTheme:
        """构建自定义主题."""
        return CustomTheme(self.config)


class ThemeManager:
    """主题管理器 - 管理多个主题的注册和应用."""

    _themes: dict[str, BaseTheme] = {}
    _current_theme: str | None = None

    @classmethod
    def register_theme(cls, name: str, theme: BaseTheme) -> None:
        """注册主题."""
        cls._themes[name] = theme

    @classmethod
    def get_theme(cls, name: str) -> BaseTheme | None:
        """获取注册的主题."""
        return cls._themes.get(name)

    @classmethod
    def list_themes(cls) -> list[str]:
        """列出所有注册的主题."""
        return list(cls._themes.keys())

    @classmethod
    def apply_theme(cls, name: str, widget) -> bool:
        """应用指定主题到控件."""
        theme = cls.get_theme(name)
        if theme:
            widget.setStyleSheet(theme.get_stylesheet())
            cls._current_theme = name
            return True
        return False

    @classmethod
    def get_current_theme(cls) -> str | None:
        """获取当前应用的主题名称."""
        return cls._current_theme


# 便利函数
def create_custom_theme(
    name: str,
    colors: dict[str, str] | None = None,
    dimensions: dict[str, int] | None = None,
    fonts: dict[str, str] | None = None,
    parent: type[BaseTheme] | BaseTheme | None = None,
) -> CustomTheme:
    """创建自定义主题的便利函数."""
    builder = ThemeBuilder(name)

    if parent:
        builder.inherit_from(parent)

    if colors:
        for key, value in colors.items():
            builder.set_color(key, value)

    if dimensions:
        for key, value in dimensions.items():
            builder.set_dimension(key, value)

    if fonts:
        for key, value in fonts.items():
            builder.set_font(key, value)

    return builder.build()


def apply_registered_theme(theme_name: str, widget) -> bool:
    """应用已注册的主题."""
    return ThemeManager.apply_theme(theme_name, widget)


def register_and_apply_theme(
    theme: BaseTheme, widget, name: str | None = None
) -> bool:
    """注册并应用主题."""
    theme_name = name or theme.name
    ThemeManager.register_theme(theme_name, theme)
    return ThemeManager.apply_theme(theme_name, widget)
