
import os
import subprocess
import webbrowser
import time
from typing import Optional
from livekit.agents import function_tool, RunContext
import psutil
import pyautogui
# Some tools may require win32 libraries which should be available
try:
    import win32gui
    import win32process
    import win32con
except ImportError:
    pass

@function_tool()
async def open_website_or_app(context: RunContext, query: str) -> str:
    try:
        q = query.lower().replace("open", "").replace("launch", "").replace("start", "").strip()
        sites = {
            "youtube": "https://www.youtube.com", "gmail": "https://mail.google.com",
            "google": "https://www.google.com", "chatgpt": "https://chat.openai.com",
            "facebook": "https://www.facebook.com", "whatsapp": "https://web.whatsapp.com"
        }
        chrome_path = r"C:\Program Files\Google\Chrome\Application\chrome.exe"
        
        for name, url in sites.items():
            if name in q:
                if os.path.exists(chrome_path):
                    subprocess.Popen([chrome_path, url])
                    return f"✅ Opened {name.capitalize()} in Chrome."
                webbrowser.open(url)
                return f"✅ Opened {name.capitalize()}."
        
        if "." in q or q.startswith("http") or q.startswith("www"):
            url = q if q.startswith("http") else "https://" + q
            webbrowser.open(url)
            return f"✅ Opened {q}"
            
        try:
            os.startfile(q)
            return f"✅ Launched: {q}"
        except:
            subprocess.Popen(q, shell=True)
            return f"✅ Launched: {q}"
            
    except Exception as e:
        return f"❌ Unable to open '{q}': {e}"

@function_tool()
async def open_file_or_folder(context: RunContext, path: str) -> str:
    os.startfile(path)
    return "Opened"

@function_tool()
async def run_command(context: RunContext, command: str) -> str:
    subprocess.Popen(command, shell=True)
    return "Command executed"

@function_tool()
async def get_active_window(context: RunContext) -> str:
    try:
        hwnd = win32gui.GetForegroundWindow()
        return win32gui.GetWindowText(hwnd)
    except: return "Unknown"

@function_tool()
async def minimize_window(context: RunContext) -> str:
    pyautogui.hotkey('win', 'down')
    return "Window minimized"

@function_tool()
async def maximize_window(context: RunContext) -> str:
    pyautogui.hotkey('win', 'up')
    return "Window maximized"

@function_tool()
async def close_active_window(context: RunContext) -> str:
    pyautogui.hotkey('alt', 'f4')
    return "Window closed"

@function_tool()
async def switch_window(context: RunContext) -> str:
    pyautogui.hotkey('alt', 'tab')
    return "Switched window"

@function_tool()
async def keyboard_mouse_control(context: RunContext, action: str, value: Optional[str] = None) -> str:
    try:
        if action == "move":
            x, y = map(int, value.split(","))
            pyautogui.moveTo(x, y, duration=0.5)
        elif action == "click": pyautogui.click()
        elif action == "double_click": pyautogui.doubleClick()
        elif action == "right_click": pyautogui.rightClick()
        elif action == "type": pyautogui.write(value, interval=0.05)
        elif action == "press": pyautogui.press(value)
        elif action == "scroll": pyautogui.scroll(int(value))
        return f"Action executed: {action}"
    except Exception as e: return f"Error: {e}"

@function_tool()
async def volume_control(context: RunContext, level: int) -> str:
    # Requires specialized libraries or keys. Simulating with keys for now if not implemented fully
    # But tools.py had just "return Volume set". I'll keep it simple or try keys
    for _ in range(50): pyautogui.press('volumedown') # Reset
    for _ in range(level // 2): pyautogui.press('volumeup')
    return f"Volume set to approx {level}%"

@function_tool()
async def take_screenshot(context: RunContext) -> str:
    pyautogui.screenshot("screenshot.png")
    return "Screenshot saved"

@function_tool()
async def read_clipboard(context: RunContext) -> str:
    import pyperclip
    return pyperclip.paste()

@function_tool()
async def copy_to_clipboard(context: RunContext, text: str) -> str:
    import pyperclip
    pyperclip.copy(text)
    return "Copied"

@function_tool()
async def open_clipboard_history(context: RunContext) -> str:
    pyautogui.hotkey('win', 'v')
    return "History opened"

@function_tool()
async def running_processes(context: RunContext) -> str:
    return ", ".join(p.name() for p in psutil.process_iter())

@function_tool()
async def terminate_process(context: RunContext, name: str) -> str:
    for p in psutil.process_iter():
        if p.name().lower() == name.lower():
            p.kill()
            return "Terminated"
    return "Not found"

@function_tool()
async def control_bluetooth(context: RunContext, action: str, device_name: Optional[str] = None) -> str:
    webbrowser.open("ms-settings:bluetooth")
    return f"Opened Bluetooth settings to action found: {action}"

@function_tool()
async def control_windows_settings(context: RunContext, page: str, toggle: Optional[str] = None) -> str:
    pages = {
        "display": "ms-settings:display", "sound": "ms-settings:sounds", 
        "notifications": "ms-settings:notifications", "power": "ms-settings:powersleep",
        "storage": "ms-settings:storagesense", "bluetooth": "ms-settings:bluetooth",
        "network": "ms-settings:network", "update": "ms-settings:windowsupdate"
    }
    webbrowser.open(pages.get(page.lower(), "ms-settings:"))
    return f"Opened {page} settings"

@function_tool()
async def restart_system(context: RunContext) -> str:
    os.system("shutdown /r /t 5")
    return "Restarting in 5s"

@function_tool()
async def shutdown_system(context: RunContext) -> str:
    os.system("shutdown /s /t 5")
    return "Shutting down in 5s"

@function_tool()
async def sleep_system(context: RunContext) -> str:
    os.system("rundll32.exe powrprof.dll,SetSuspendState 0,1,0")
    return "Sleeping"

@function_tool()
async def hibernate_system(context: RunContext) -> str:
    os.system("shutdown /h")
    return "Hibernating"

@function_tool()
async def lock_system(context: RunContext) -> str:
    os.system("rundll32.exe user32.dll,LockWorkStation")
    return "Locked"

@function_tool()
async def set_brightness(context: RunContext, level: int) -> str:
    try:
        import screen_brightness_control as sbc
        sbc.set_brightness(level)
        return f"Brightness: {level}%"
    except: return "Failed to set brightness"

@function_tool()
async def show_notification(context: RunContext, title: str, message: str) -> str:
    try:
        from win10toast import ToastNotifier
        ToastNotifier().show_toast(title, message, duration=5, threaded=True)
        return "Notification sent"
    except: return "Failed"

@function_tool()
async def login_with_gmail(context: RunContext, website: str) -> str:
    webbrowser.open(f"https://{website}.com")
    return f"Opening {website}"

@function_tool()
async def execute_powershell(context: RunContext, command: str) -> str:
    try:
        res = subprocess.run(["powershell", "-Command", command], capture_output=True, text=True, timeout=30)
        return (res.stdout.strip() + res.stderr.strip())[:1000]
    except Exception as e: return f"Error: {e}"

@function_tool()
async def execute_cmd(context: RunContext, command: str) -> str:
    try:
        res = subprocess.run(command, shell=True, capture_output=True, text=True, timeout=30)
        return (res.stdout.strip() + res.stderr.strip())[:1000]
    except Exception as e: return f"Error: {e}"

@function_tool()
async def schedule_task(context: RunContext, task_name: str, command: str, time: str) -> str:
    try:
        subprocess.run(f'schtasks /create /sc once /tn "{task_name}" /tr "{command}" /st {time} /f', shell=True)
        return "Task Scheduled"
    except Exception as e: return f"Error: {e}"
