//! AI model definitions and parameter types

use serde::{Deserialize, Serialize};

/// Upscaling AI models available in Topaz Video AI
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum UpscaleModel {
    /// Iris v3 - Best general purpose model
    Iris3,
    /// Iris v2 - Balanced quality and speed
    Iris2,
    /// Artemis HQ v12 - High quality model
    Ahq12,
    /// Artemis LQ v13 - Optimized for low quality input
    Alq13,
    /// Artemis LQ Small v2 - Fast processing
    Alqs2,
    /// Artemis MQ v13 - Medium quality balance
    Amq13,
    /// Artemis MQ Small v2 - Fast medium quality
    Amqs2,
    /// Gaia HQ v5 - Game/CG content
    Ghq5,
    /// Nyx v3 - Portrait optimization
    Nyx3,
    /// Proteus v4 - Problem footage repair
    Prob4,
    /// Theia Fidelity v4 - Old content restoration
    Thf4,
    /// Theia Detail v3 - Detail enhancement
    Thd3,
    /// Theia Magic v2 - Magic enhancement (forces 1x scale)
    Thm2,
    /// Rhea v1 - Realism enhancement
    Rhea1,
    /// Rhea XL v1 - Extra large resolution
    Rxl1,
    /// Artemis Anti-Alias v9 - Anti-aliasing
    Aaa9,
}

impl UpscaleModel {
    /// Get the model identifier string for FFmpeg
    pub fn as_str(&self) -> &'static str {
        match self {
            Self::Iris3 => "iris-3",  // 使用版本化格式
            Self::Iris2 => "iris-2",  // 使用版本化格式
            Self::Ahq12 => "ahq-12",  // 使用版本化格式
            Self::Alq13 => "alq-13",  // 使用版本化格式
            Self::Alqs2 => "alqs-2",  // 使用版本化格式
            Self::Amq13 => "amq-13",  // 使用版本化格式
            Self::Amqs2 => "amqs-2",  // 使用版本化格式
            Self::Ghq5 => "ghq-5",    // 使用版本化格式
            Self::Nyx3 => "nyx-3",    // 使用版本化格式
            Self::Prob4 => "prob-4",  // 使用版本化格式
            Self::Thf4 => "thf-4",    // 使用版本化格式
            Self::Thd3 => "thd-3",    // 使用版本化格式
            Self::Thm2 => "thm-2",    // 使用版本化格式
            Self::Rhea1 => "rhea-1",  // 使用版本化格式
            Self::Rxl1 => "rxl-1",    // 使用版本化格式
            Self::Aaa9 => "aaa-9",    // 使用版本化格式
        }
    }
    
    /// Check if this model forces a specific scale factor
    pub fn forces_scale(&self) -> Option<f32> {
        match self {
            Self::Thm2 => Some(1.0), // Theia Magic forces 1x scale
            _ => None,
        }
    }
    
    /// Get recommended use case for this model
    pub fn description(&self) -> &'static str {
        match self {
            Self::Iris3 => "Best general purpose model for most content",
            Self::Iris2 => "Balanced quality and processing speed",
            Self::Ahq12 => "High quality upscaling for premium content",
            Self::Alq13 => "Optimized for low quality input footage",
            Self::Alqs2 => "Fast processing for low quality content",
            Self::Amq13 => "Medium quality balance for general use",
            Self::Amqs2 => "Fast medium quality processing",
            Self::Ghq5 => "Specialized for game footage and CG content",
            Self::Nyx3 => "Optimized for portrait and face content",
            Self::Prob4 => "Repair and restoration of problem footage",
            Self::Thf4 => "Restoration of old films and vintage content",
            Self::Thd3 => "Enhanced detail preservation",
            Self::Thm2 => "Magic enhancement with artifact removal",
            Self::Rhea1 => "Realism enhancement for natural content",
            Self::Rxl1 => "Extra large resolution upscaling",
            Self::Aaa9 => "Anti-aliasing and edge smoothing",
        }
    }
}

/// Frame interpolation models available in Topaz Video AI
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum InterpolationModel {
    /// Apollo v8 - High quality interpolation
    Apo8,
    /// Apollo Fast v1 - Fast interpolation
    Apf1,
    /// Apollo Fast v2 - Improved fast interpolation (most common)
    Apf2,
    /// Chronos v2 - Animation content
    Chr2,
    /// Chronos Fast v3 - Fast animation interpolation
    Chf3,
}

impl InterpolationModel {
    /// Get the model identifier string for FFmpeg
    pub fn as_str(&self) -> &'static str {
        match self {
            Self::Apo8 => "apo-8",
            Self::Apf1 => "apf-1",
            Self::Apf2 => "apf-2",
            Self::Chr2 => "chr-2",
            Self::Chf3 => "chf-3",
        }
    }
    
    /// Get recommended use case for this model
    pub fn description(&self) -> &'static str {
        match self {
            Self::Apo8 => "High quality interpolation for most content",
            Self::Apf1 => "Fast interpolation with good quality",
            Self::Apf2 => "Improved fast interpolation - most commonly used",
            Self::Chr2 => "Specialized for animation and cartoon content",
            Self::Chf3 => "Fast interpolation for animation content",
        }
    }
}

/// Quality presets for processing
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum QualityPreset {
    /// Fast processing with acceptable quality
    Fast,
    /// Balanced quality and speed
    Balanced,
    /// High quality processing
    HighQuality,
    /// Maximum quality (slowest)
    Maximum,
}

impl QualityPreset {
    /// Get encoding settings for this preset
    pub fn get_encoding_settings(&self, use_gpu: bool) -> (&'static str, &'static str) {
        match (self, use_gpu) {
            (Self::Fast, true) => ("hevc_nvenc", "fast"),
            (Self::Fast, false) => ("libx264", "ultrafast"),
            (Self::Balanced, true) => ("hevc_nvenc", "medium"),
            (Self::Balanced, false) => ("libx264", "medium"),
            (Self::HighQuality, true) => ("hevc_nvenc", "slow"),
            (Self::HighQuality, false) => ("libx264", "slow"),
            (Self::Maximum, true) => ("hevc_nvenc", "slow"),
            (Self::Maximum, false) => ("libx264", "veryslow"),
        }
    }
    
    /// Get quality value for this preset
    pub fn get_quality_value(&self, use_gpu: bool) -> &'static str {
        match (self, use_gpu) {
            (Self::Fast, true) => "25",
            (Self::Fast, false) => "23",
            (Self::Balanced, true) => "20",
            (Self::Balanced, false) => "20",
            (Self::HighQuality, true) => "17",
            (Self::HighQuality, false) => "17",
            (Self::Maximum, true) => "15",
            (Self::Maximum, false) => "15",
        }
    }
}
