# RR3 Asset Extraction PowerShell Script
# Extracts .z (ZLIB compressed) texture files from Real Racing 3

param(
    [Parameter(Mandatory=$true)]
    [string]$InputFile,
    
    [Parameter(Mandatory=$false)]
    [string]$OutputDir
)

Write-Host "════════════════════════════════════════════════════════════" -ForegroundColor Cyan
Write-Host "   RR3 Asset Extraction Tool - Windows" -ForegroundColor Yellow
Write-Host "════════════════════════════════════════════════════════════" -ForegroundColor Cyan
Write-Host ""

# Validate input
if (-not (Test-Path $InputFile)) {
    Write-Host "ERROR: Input file not found: $InputFile" -ForegroundColor Red
    exit 1
}

# Default output dir
if (-not $OutputDir) {
    $OutputDir = Split-Path -Parent $InputFile
}

Write-Host "Input file: $InputFile" -ForegroundColor Green
Write-Host "Output directory: $OutputDir" -ForegroundColor Green
Write-Host ""

# Create output directory
New-Item -ItemType Directory -Path $OutputDir -Force | Out-Null

# Read file
Write-Host "Reading file..." -ForegroundColor Cyan
$data = [System.IO.File]::ReadAllBytes($InputFile)

$output = New-Object System.Collections.ArrayList
$i = 0
$found = 0

Write-Host "Scanning for ZLIB blocks..." -ForegroundColor Cyan

# Scan for zlib blocks (magic bytes 0x78 0x9C, 0xDA, or 0x01)
while ($i -lt ($data.Length - 2)) {
    if ($data[$i] -eq 0x78 -and ($data[$i+1] -eq 0x9C -or $data[$i+1] -eq 0xDA -or $data[$i+1] -eq 0x01)) {
        try {
            # Try to decompress from this position
            $compressed = $data[$i..($data.Length-1)]
            $decompressed = [System.IO.Compression.DeflateStream]::new(
                [System.IO.MemoryStream]::new($compressed, 2, $compressed.Length - 2),
                [System.IO.Compression.CompressionMode]::Decompress
            )
            
            $ms = New-Object System.IO.MemoryStream
            $decompressed.CopyTo($ms)
            $decompressed.Close()
            
            $block = $ms.ToArray()
            $ms.Close()
            
            if ($block.Length -gt 0) {
                $output.AddRange($block)
                Write-Host "  [+] Block $found at 0x$($i.ToString('X'))" -ForegroundColor Gray
                $found++
                $i += $block.Length
                continue
            }
        } catch {
            # Not a valid zlib block, continue
        }
    }
    $i++
}

if ($found -eq 0) {
    Write-Host "ERROR: No valid zlib blocks found!" -ForegroundColor Red
    exit 1
}

# Get output filename
$baseName = [System.IO.Path]::GetFileName($InputFile)
if ($baseName.ToLower().EndsWith(".z")) {
    $baseName = $baseName.Substring(0, $baseName.Length - 2)
}

$outputFile = Join-Path $OutputDir $baseName

# Backup if exists
if (Test-Path $outputFile) {
    $bakFile = "$outputFile.bak"
    if (-not (Test-Path $bakFile)) {
        Move-Item $outputFile $bakFile
        Write-Host "Backup created: $bakFile" -ForegroundColor Yellow
    }
}

# Write output
[System.IO.File]::WriteAllBytes($outputFile, $output.ToArray())

Write-Host ""
Write-Host "✅ Extraction complete!" -ForegroundColor Green
Write-Host "Output: $outputFile" -ForegroundColor White
Write-Host "Blocks found: $found" -ForegroundColor White
Write-Host "Size: $($output.Count) bytes" -ForegroundColor White
