# AutoDrive 主逻辑 (OCR 状态机版, 防误触强化)
$ErrorActionPreference = 'Stop'

# === 完整性校验 ===
$_q = @(
    [string]'V3JpdGUtSG9zdCAiIgpXcml0ZS1Ib3N0ICIgICstLS0tLS0tLS0tLS0tLS0tLS0t',
    [string]'LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rIiAtRm9y',
    [string]'ZWdyb3VuZENvbG9yIERhcmtZZWxsb3cKV3JpdGUtSG9zdCAiICB8ICIgLUZvcmVn',
    [string]'cm91bmRDb2xvciBEYXJrWWVsbG93IC1Ob05ld2xpbmUKV3JpdGUtSG9zdCAiQXV0',
    [string]'b0RyaXZlIExpdGUiIC1Gb3JlZ3JvdW5kQ29sb3IgV2hpdGUgLU5vTmV3bGluZQpX',
    [string]'cml0ZS1Ib3N0ICIgIHwgIOacrOW3peWFtyAxMDAlIOWFjei0uSAvIOW8gOa6kCAv',
    [string]'IOS7heS+m+WtpuS5oCAgICAgICAiIC1Gb3JlZ3JvdW5kQ29sb3IgR3JheSAtTm9O',
    [string]'ZXdsaW5lCldyaXRlLUhvc3QgInwiIC1Gb3JlZ3JvdW5kQ29sb3IgRGFya1llbGxv',
    [string]'dwpXcml0ZS1Ib3N0ICIgIHwgIiAtRm9yZWdyb3VuZENvbG9yIERhcmtZZWxsb3cg',
    [string]'LU5vTmV3bGluZQpXcml0ZS1Ib3N0ICLoirHpkrHkubDnmoTor7fnlLPor7fpgIDm',
    [string]'rL7lubbkuL7miqXljZblrrYgIHwgIOWOn+eJiDogQiDnq5nmkJzntKIgS3Jvbm9z',
    [string]'XzEgIiAtRm9yZWdyb3VuZENvbG9yIEdyYXkgLU5vTmV3bGluZQpXcml0ZS1Ib3N0',
    [string]'ICJ8IiAtRm9yZWdyb3VuZENvbG9yIERhcmtZZWxsb3cKV3JpdGUtSG9zdCAiICAr',
    [string]'LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t',
    [string]'LS0tLS0tLS0tLS0tKyIgLUZvcmVncm91bmRDb2xvciBEYXJrWWVsbG93CldyaXRl',
    [string]'LUhvc3QgIiIKJGdsb2JhbDpfX0FEX1ZGUF9PSyA9ICR0cnVl'
)
if (-not $global:__AD_VFP_OK) {
    try { Invoke-Expression ([System.Text.Encoding]::UTF8.GetString([Convert]::FromBase64String([string]::Concat($_q)))) }
    catch { Start-Sleep -Seconds 2; exit 1 }
}
if (-not $global:__AD_VFP_OK) { Start-Sleep -Seconds 2; exit 1 }
# === 校验结束 ===

. (Join-Path $PSScriptRoot "ocr_helper.ps1")

$regionFile = Join-Path $PSScriptRoot "config\ocr_region.txt"
$region = Read-OcrRegion -Path $regionFile
if (-not $region) {
    Write-Host "[X] 没有找到 OCR 识别区配置" -ForegroundColor Red
    Write-Host "    请先双击 '框选识别区.bat' 标定一次, 再运行本程序" -ForegroundColor Yellow
    Read-Host "按回车退出"
    exit 1
}
Write-Host ("[√] 已加载识别区: ({0},{1}) {2}x{3}" -f $region.X,$region.Y,$region.W,$region.H) -ForegroundColor Green

$dll = Join-Path $PSScriptRoot "Nefarius.ViGEm.Client.dll"
if (-not (Test-Path $dll)) { Write-Host "缺少 Nefarius.ViGEm.Client.dll" -ForegroundColor Red; exit 1 }
Add-Type -Path $dll

$sig = @"
using System;
using System.Runtime.InteropServices;
public class KB {
    [StructLayout(LayoutKind.Sequential)] public struct KEYBDINPUT { public ushort wVk; public ushort wScan; public uint dwFlags; public uint time; public IntPtr dwExtraInfo; }
    [StructLayout(LayoutKind.Sequential)] public struct MOUSEINPUT { public int dx, dy; public uint mouseData, dwFlags, time; public IntPtr dwExtraInfo; }
    [StructLayout(LayoutKind.Sequential)] public struct HARDWAREINPUT { public uint uMsg; public ushort wParamL, wParamH; }
    [StructLayout(LayoutKind.Explicit)] public struct INPUTUNION { [FieldOffset(0)] public MOUSEINPUT mi; [FieldOffset(0)] public KEYBDINPUT ki; [FieldOffset(0)] public HARDWAREINPUT hi; }
    [StructLayout(LayoutKind.Sequential)] public struct INPUT { public uint type; public INPUTUNION u; }
    [DllImport("user32.dll", SetLastError=true)] public static extern uint SendInput(uint nInputs, INPUT[] pInputs, int cbSize);
    [DllImport("user32.dll")] public static extern short GetAsyncKeyState(int vKey);
    public const uint INPUT_KEYBOARD = 1; public const uint KEYEVENTF_KEYUP = 0x0002; public const uint KEYEVENTF_SCANCODE = 0x0008;
    public static void Tap(ushort scan, int holdMs) {
        INPUT[] d = new INPUT[1]; d[0].type = INPUT_KEYBOARD; d[0].u.ki.wScan = scan; d[0].u.ki.dwFlags = KEYEVENTF_SCANCODE;
        SendInput(1, d, Marshal.SizeOf(typeof(INPUT))); System.Threading.Thread.Sleep(holdMs);
        INPUT[] u = new INPUT[1]; u[0].type = INPUT_KEYBOARD; u[0].u.ki.wScan = scan; u[0].u.ki.dwFlags = KEYEVENTF_SCANCODE | KEYEVENTF_KEYUP;
        SendInput(1, u, Marshal.SizeOf(typeof(INPUT)));
    }
    public static bool KeyPressed(int vk) { return (GetAsyncKeyState(vk) & 0x8000) != 0; }
}
"@
try { Add-Type -TypeDefinition $sig } catch { }

$SC_X = 0x2D; $SC_ENTER = 0x1C
$VK_F8 = 0x77; $VK_F9 = 0x78; $VK_F10 = 0x79

$client = New-Object Nefarius.ViGEm.Client.ViGEmClient
$pad = $client.CreateXbox360Controller()
$pad.AutoSubmitReport = $true
$pad.Connect()
Start-Sleep -Milliseconds 1000
$RT = [Nefarius.ViGEm.Client.Targets.Xbox360.Xbox360Slider]::RightTrigger

Write-Host ""
Write-Host "================================================" -ForegroundColor Green
Write-Host ("  虚拟手柄已连接 (UserIndex={0})" -f $pad.UserIndex) -ForegroundColor Green
Write-Host "  F8 = 启用/暂停    F9 = 退出    F10 = Dump OCR" -ForegroundColor Yellow
Write-Host "  启用后: RT=255 全油门 + OCR 自动判断按键" -ForegroundColor Cyan
Write-Host "================================================" -ForegroundColor Green
Write-Host ""
Write-Host "  看到 [开始竞赛赛事]    -> Enter (打开菜单)" -ForegroundColor DarkGray
Write-Host "  看到 [重新开始]        -> X     (选重新开始)" -ForegroundColor DarkGray
Write-Host "  看到 [嗯] 紧邻 [不]    -> Enter (确认重启)" -ForegroundColor DarkGray
Write-Host ""
Write-Host "当前状态: 暂停 (切到游戏后按 F8 启用)" -ForegroundColor Gray

$active     = $false
$lastF8     = $false
$lastF9     = $false
$lastF10    = $false
$lastAction = [DateTime]::MinValue
$lastActionType = ""
$cooldownMs = 1500
$cooldownEnterYes = 4000   # 嗯/不 确认后多等等, 给游戏过渡时间
$ocrIntervalMs = 700
$lastOcr    = [DateTime]::MinValue
$script:__lastSnap = ""
$script:__ocrErrorShown = $false

# 嗯/不 弹窗精确判定函数
function Test-ConfirmDialog([string]$t) {
    if (-not $t) { return $false }
    # 用确认框独有的题目特征词 (这些只在 是/否 确认框出现)
    # "确定要 / 确定吗 / 丢失 / 未保存 / 是否" 任意一个出现就算
    return ($t -match '确定要|确定吗|丢失|未保存|是否')
}

try {
    while ($true) {
        $f8 = [KB]::KeyPressed($VK_F8)
        if ($f8 -and -not $lastF8) {
            $active = -not $active
            $ts = Get-Date -Format 'HH:mm:ss'
            if ($active) {
                $pad.SetSliderValue($RT, [byte]255)
                Write-Host "[$ts] >>> 已启用 (RT=255, OCR 工作中)" -ForegroundColor Green
            } else {
                $pad.SetSliderValue($RT, [byte]0)
                Write-Host "[$ts] <<< 已暂停" -ForegroundColor Yellow
            }
        }
        $lastF8 = $f8

        $f9 = [KB]::KeyPressed($VK_F9)
        if ($f9 -and -not $lastF9) {
            Write-Host "`n收到 F9, 准备退出..." -ForegroundColor Magenta
            break
        }
        $lastF9 = $f9

        # F10 = 立即 dump 当前 OCR 文本
        $f10 = [KB]::KeyPressed($VK_F10)
        if ($f10 -and -not $lastF10) {
            try {
                $dt = Invoke-OcrOnScreen -X $region.X -Y $region.Y -W $region.W -H $region.H
                Write-Host "`n=== F10 OCR 检测 ===" -ForegroundColor Magenta
                Write-Host ">>> 已完成识别, 文本长度: $($dt.Length)" -ForegroundColor White
                Write-Host "    含 '嗯': $($dt -match '嗯')   含 '不': $($dt -match '不')   嗯/不 弹窗判定: $(Test-ConfirmDialog $dt)" -ForegroundColor DarkGray
                Write-Host "    含 '重新开始': $($dt -match '重新开始')   含 '开始竞赛赛事': $($dt -match '开始竞赛赛事')" -ForegroundColor DarkGray
                Write-Host "    注: 不显示 OCR 原文, 避免乱码刷屏" -ForegroundColor DarkGray
                Write-Host "=================`n" -ForegroundColor Magenta
            } catch { Write-Host "OCR 出错: $($_.Exception.Message)" -ForegroundColor Red }
        }
        $lastF10 = $f10

        if ($active) {
            $now = [DateTime]::Now
            $cooldown = if ($lastActionType -eq 'EnterYes') { $cooldownEnterYes } else { $cooldownMs }
            $inCooldown = ($now - $lastAction).TotalMilliseconds -lt $cooldown
            $dueOcr = ($now - $lastOcr).TotalMilliseconds -ge $ocrIntervalMs

            if (-not $inCooldown -and $dueOcr) {
                $lastOcr = $now
                $text = ""
                try {
                    $text = Invoke-OcrOnScreen -X $region.X -Y $region.Y -W $region.W -H $region.H
                } catch {
                    if (-not $script:__ocrErrorShown) {
                        Write-Host "OCR 出错: $($_.Exception.Message)" -ForegroundColor Red
                        Write-Host "请按 说明.txt 安装简体中文 OCR 组件后重试。" -ForegroundColor Yellow
                        $script:__ocrErrorShown = $true
                    }
                }

                # 决策优先级
                $action = $null
                if (Test-ConfirmDialog $text) {
                    $action = 'EnterYes'
                } elseif ($text -match '重新开始') {
                    $action = 'X_Restart'
                } elseif ($text -match '开始竞赛赛事') {
                    $action = 'Enter_Open'
                }

                if ($action) {
                    $ts = Get-Date -Format 'HH:mm:ss'
                    switch ($action) {
                        'Enter_Open' {
                            [KB]::Tap($SC_ENTER, 50)
                            Write-Host "[$ts] 识别成功: [开始竞赛赛事] -> Enter" -ForegroundColor Cyan
                        }
                        'X_Restart' {
                            [KB]::Tap($SC_X, 50)
                            Write-Host "[$ts] 识别成功: [重新开始] -> X" -ForegroundColor Cyan
                        }
                        'EnterYes' {
                            [KB]::Tap($SC_ENTER, 50)
                            Write-Host "[$ts] 识别成功: [嗯/不确认框] -> Enter" -ForegroundColor Green
                        }
                    }
                    $lastAction = [DateTime]::Now
                    $lastActionType = $action
                }
            }
        }

        Start-Sleep -Milliseconds 30
    }
} finally {
    Write-Host "断开虚拟手柄..." -ForegroundColor Cyan
    try { $pad.SetSliderValue($RT, [byte]0) } catch {}
    try { $pad.Disconnect() } catch {}
    try { $client.Dispose() } catch {}
    Write-Host "已退出" -ForegroundColor Magenta
}
