"""
TaskingBot AI Desktop App — PyWebView-based native GUI.

Launches a native window with the TaskingBot chat UI and runs
the desktop agent poller in a background thread.
"""

import sys
import os
import platform
import base64
import json
import threading

# Ensure the agent package is importable when running standalone
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))

from .config import load_config, get_os_info, save_config, CONFIG_DIR
from .webui import DESKTOP_HTML


class DesktopAPI:
    """Python API exposed to the webview JS via window.pywebview.api."""

    def __init__(self, config, poller=None):
        self.config = config
        self.poller = poller
        self._window = None

    def set_window(self, window):
        self._window = window

    def get_os_info(self):
        """Return OS info dict for the Desktop panel."""
        return get_os_info()

    def take_screenshot(self):
        """Capture a screenshot and return as base64 PNG."""
        try:
            import mss
            from PIL import Image
            import io

            with mss.mss() as sct:
                # Capture the primary monitor
                monitor = sct.monitors[1]  # Primary monitor
                img = sct.grab(monitor)

                # Convert to PIL Image and then to base64
                pil_img = Image.frombytes("RGB", img.size, img.bgra, "raw", "BGRX")

                # Resize if very large (keep under 1920px wide for performance)
                max_w = 1920
                if pil_img.width > max_w:
                    ratio = max_w / pil_img.width
                    new_h = int(pil_img.height * ratio)
                    pil_img = pil_img.resize((max_w, new_h), Image.LANCZOS)

                buf = io.BytesIO()
                pil_img.save(buf, format="PNG", optimize=True)
                b64 = base64.b64encode(buf.getvalue()).decode("ascii")

                return {"ok": True, "data": b64}
        except Exception as e:
            return {"ok": False, "error": str(e)}

    def open_external(self, url):
        """Open a URL in the system's default browser."""
        import webbrowser
        webbrowser.open(url)
        return {"ok": True}

    def get_config(self):
        """Return the current config (without sensitive keys in full)."""
        cfg = dict(self.config)
        if cfg.get("api_key"):
            cfg["api_key"] = cfg["api_key"][:8] + "..."
        return cfg

    def get_agent_status(self):
        """Check if the poller is running."""
        if self.poller:
            return {"running": self.poller.running}
        return {"running": False}


def _start_poller_background(config, api_instance, window):
    """Start the desktop agent poller in a daemon thread."""
    from .poller import DesktopAgentPoller

    poller = DesktopAgentPoller(config)
    api_instance.poller = poller

    # Forward status messages to the webview
    def on_status(msg):
        if window:
            try:
                safe_msg = json.dumps(msg)
                window.evaluate_js(f"window.desktopAgentStatus({safe_msg})")
            except Exception:
                pass

    def on_action(action_type, result):
        if window:
            try:
                safe_msg = json.dumps(f"{action_type}: {'OK' if result.get('success') else 'FAILED'}")
                window.evaluate_js(f"window.desktopAgentStatus({safe_msg})")
            except Exception:
                pass

    poller.on_status = on_status
    poller.on_action = on_action

    # Send OS info to the webview once ready
    def send_os_info():
        import time
        time.sleep(2)  # Wait for webview to be ready
        if window:
            try:
                info = json.dumps(get_os_info())
                window.evaluate_js(f"window.desktopAgentOsInfo({info})")
            except Exception:
                pass

    threading.Thread(target=send_os_info, daemon=True).start()

    # Only start poller if API key is configured
    if config.get("api_key"):
        poller.run_in_background()
    else:
        on_status("Desktop agent not started — no API key configured. Use the Desktop tab or run 'tt-desktop setup'.")


def launch_app(config=None):
    """Launch the TaskingBot AI desktop application."""
    try:
        import webview
    except ImportError:
        print("ERROR: pywebview is required. Install it with:")
        print("  pip install pywebview")
        print()
        print("On Linux, you may also need one of these backends:")
        print("  pip install pywebview[qt]    # For Qt backend")
        print("  pip install pywebview[gtk]   # For GTK backend")
        print("  pip install pywebview[cef]   # For CEF backend")
        sys.exit(1)

    if config is None:
        config = load_config()

    api = DesktopAPI(config)

    # Create the webview window
    window = webview.create_window(
        title="TaskingBot AI",
        html=DESKTOP_HTML,
        width=340,
        height=620,
        resizable=True,
        min_size=(280, 400),
        js_api=api,
        text_select=True,
    )

    api.set_window(window)

    def on_loaded():
        """Called when the webview finishes loading."""
        _start_poller_background(config, api, window)

    window.events.loaded += on_loaded

    def on_closing():
        """Clean up when window closes."""
        if api.poller:
            api.poller.running = False
            api.poller.disconnect()

    window.events.closing += on_closing

    # Start the webview (blocks until window is closed)
    webview.start(debug=False)


def main():
    """Entry point for `tt-desktop app` or direct execution."""
    launch_app()


if __name__ == "__main__":
    main()
