"""Interactive Procedural Generation Demo Launcher

Run with: ./mcrogueface ../tests/procgen_interactive/main.py
"""

import mcrfpy
import sys

# Demo classes
from .demos.cave_demo import CaveDemo
from .demos.dungeon_demo import DungeonDemo
from .demos.terrain_demo import TerrainDemo
from .demos.town_demo import TownDemo


class DemoLauncher:
    """Main menu for selecting demos."""

    DEMOS = [
        ("Cave (Cellular Automata)", CaveDemo,
         "Cellular automata cave generation with noise, smoothing, and region detection"),
        ("Dungeon (BSP)", DungeonDemo,
         "Binary Space Partitioning with room extraction and corridor connections"),
        ("Terrain (Multi-layer)", TerrainDemo,
         "FBM noise elevation with water level, mountains, erosion, and biomes"),
        ("Town (Voronoi)", TownDemo,
         "Voronoi districts with Bezier roads and building placement"),
    ]

    def __init__(self):
        """Build the menu scene."""
        self.scene = mcrfpy.Scene("procgen_menu")
        self.current_demo = None
        self._build_menu()

    def _build_menu(self):
        """Create the menu UI."""
        ui = self.scene.children

        # Background
        bg = mcrfpy.Frame(
            pos=(0, 0),
            size=(1024, 768),
            fill_color=mcrfpy.Color(25, 28, 35)
        )
        ui.append(bg)

        # Title
        title = mcrfpy.Caption(
            text="Interactive Procedural Generation",
            pos=(512, 60),
            font_size=32,
            fill_color=mcrfpy.Color(220, 220, 230)
        )
        ui.append(title)

        subtitle = mcrfpy.Caption(
            text="Educational demos for exploring generation techniques",
            pos=(512, 100),
            font_size=16,
            fill_color=mcrfpy.Color(150, 150, 160)
        )
        ui.append(subtitle)

        # Demo buttons
        button_y = 180
        button_width = 400
        button_height = 80

        for i, (name, demo_class, description) in enumerate(self.DEMOS):
            # Button frame
            btn = mcrfpy.Frame(
                pos=(312, button_y),
                size=(button_width, button_height),
                fill_color=mcrfpy.Color(45, 48, 55),
                outline=2,
                outline_color=mcrfpy.Color(80, 85, 100)
            )

            # Demo name
            name_caption = mcrfpy.Caption(
                text=name,
                pos=(20, 15),
                font_size=20,
                fill_color=mcrfpy.Color(200, 200, 210)
            )
            btn.children.append(name_caption)

            # Description (wrap manually for now)
            desc_text = description[:55] + "..." if len(description) > 55 else description
            desc_caption = mcrfpy.Caption(
                text=desc_text,
                pos=(20, 45),
                font_size=12,
                fill_color=mcrfpy.Color(120, 120, 130)
            )
            btn.children.append(desc_caption)

            # Click handler
            demo_idx = i
            btn.on_click = lambda p, b, a, idx=demo_idx: self._on_demo_click(idx, b, a)
            btn.on_enter = lambda p, btn=btn: self._on_btn_enter(btn)
            btn.on_exit = lambda p, btn=btn: self._on_btn_exit(btn)

            ui.append(btn)
            button_y += button_height + 20

        # Instructions
        instructions = [
            "Click a demo to start exploring procedural generation",
            "Each demo shows step-by-step visualization of the algorithm",
            "",
            "Controls (in demos):",
            "  Left/Right arrows: Navigate steps",
            "  Middle-drag: Pan viewport",
            "  Scroll wheel: Zoom in/out",
            "  Number keys: Toggle layer visibility",
            "  R: Reset view",
            "  Escape: Return to this menu",
        ]

        instr_y = 580
        for line in instructions:
            cap = mcrfpy.Caption(
                text=line,
                pos=(312, instr_y),
                font_size=12,
                fill_color=mcrfpy.Color(100, 100, 110)
            )
            ui.append(cap)
            instr_y += 18

        # Keyboard handler
        self.scene.on_key = self._on_key

    def _on_btn_enter(self, btn):
        """Handle button hover enter."""
        btn.fill_color = mcrfpy.Color(55, 60, 70)
        btn.outline_color = mcrfpy.Color(100, 120, 180)

    def _on_btn_exit(self, btn):
        """Handle button hover exit."""
        btn.fill_color = mcrfpy.Color(45, 48, 55)
        btn.outline_color = mcrfpy.Color(80, 85, 100)

    def _on_demo_click(self, idx, button, action):
        """Handle demo button click."""
        if button == mcrfpy.MouseButton.LEFT and action == mcrfpy.InputState.RELEASED:
            self._launch_demo(idx)

    def _launch_demo(self, idx):
        """Launch a demo by index."""
        _, demo_class, _ = self.DEMOS[idx]
        self.current_demo = demo_class()
        self.current_demo.activate()

    def _on_key(self, key, action):
        """Handle keyboard input."""
        # Only process on key press
        if action != mcrfpy.InputState.PRESSED:
            return

        # Number keys to launch demos directly
        _num_key_map = {mcrfpy.Key.NUM_1: 1, mcrfpy.Key.NUM_2: 2, mcrfpy.Key.NUM_3: 3,
                        mcrfpy.Key.NUM_4: 4, mcrfpy.Key.NUM_5: 5, mcrfpy.Key.NUM_6: 6,
                        mcrfpy.Key.NUM_7: 7, mcrfpy.Key.NUM_8: 8, mcrfpy.Key.NUM_9: 9}
        if key in _num_key_map:
            num = _num_key_map[key]
            if 1 <= num <= len(self.DEMOS):
                self._launch_demo(num - 1)
        elif key == mcrfpy.Key.ESCAPE:
            sys.exit(0)

    def show(self):
        """Show the menu."""
        mcrfpy.current_scene = self.scene


# Global launcher instance
_launcher = None


def show_menu():
    """Show the demo menu (called from demos to return)."""
    global _launcher
    if _launcher is None:
        _launcher = DemoLauncher()
    _launcher.show()


def main():
    """Entry point for the demo system."""
    show_menu()


if __name__ == "__main__":
    main()
