shaderc-macro 0.1.0

Compile shaders with shaderc using macros at compile time
Documentation
use super::shaderc_serde;
use serde::Deserialize;

#[derive(Deserialize, Copy, Clone, Debug)]
pub struct TargetEnvArgs {
    #[serde(with = "shaderc_serde::TargetEnv")]
    pub env: shaderc::TargetEnv,
    #[serde(with = "shaderc_serde::EnvVersion")]
    pub version: shaderc::EnvVersion,
}

#[derive(Deserialize, Copy, Clone, Debug, Default)]
pub struct ForcedVersionProfileArgs {
    #[serde(default)]
    pub version: Option<u32>,
    #[serde(deserialize_with = "shaderc_serde::de_opt_glsl_profile", default)]
    pub profile: Option<shaderc::GlslProfile>,
}

#[derive(Deserialize, Copy, Clone, Debug)]
pub struct LimitArgs {
    #[serde(with = "shaderc_serde::Limit")]
    pub limit: shaderc::Limit,
    pub value: i32,
}

#[derive(Deserialize, Copy, Clone, Debug)]
pub struct BindingBaseArgs {
    #[serde(with = "shaderc_serde::ResourceKind")]
    pub resource_kind: shaderc::ResourceKind,
    pub base: u32,
}

#[derive(Deserialize, Copy, Clone, Debug)]
pub struct BindingBaseForStageArgs {
    #[serde(with = "shaderc_serde::ResourceKind")]
    pub resource_kind: shaderc::ResourceKind,
    pub base: u32,
    #[serde(with = "shaderc_serde::ShaderKind")]
    pub shader_kind: shaderc::ShaderKind,
}

#[derive(Deserialize, Clone, Debug)]
pub struct HlslRegisterSetAndBindingArgs {
    pub register: String,
    pub set: String,
    pub binding: String,
}

#[derive(Deserialize, Clone, Debug)]
pub struct HlslRegisterSetAndBindingForStageArgs {
    #[serde(with = "shaderc_serde::ShaderKind")]
    pub kind: shaderc::ShaderKind,
    pub register: String,
    pub set: String,
    pub binding: String,
}

#[derive(Deserialize, Clone, Debug)]
pub struct MacroDefinitionArgs {
    pub name: String,
    #[serde(default)]
    pub value: Option<String>,
}

#[derive(Deserialize, Clone, Debug, Default)]
#[serde(deny_unknown_fields)]
pub struct Args {
    #[serde(default, deserialize_with = "shaderc_serde::de_opt_shader_kind")]
    pub kind: Option<shaderc::ShaderKind>,
    #[serde(default)]
    pub name: Option<String>,
    #[serde(default)]
    pub entry: Option<String>,
    #[serde(default, alias = "env")]
    pub target_env: Option<TargetEnvArgs>,
    #[serde(
    default,
    alias = "spirv",
    deserialize_with = "shaderc_serde::de_opt_spirv_version"
    )]
    pub target_spirv: Option<shaderc::SpirvVersion>,
    #[serde(
    default,
    alias = "lang",
    deserialize_with = "shaderc_serde::de_opt_source_language"
    )]
    pub source_language: Option<shaderc::SourceLanguage>,
    #[serde(flatten)]
    pub forced_version_profile: ForcedVersionProfileArgs,
    #[serde(default)]
    pub limit: Vec<LimitArgs>,
    #[serde(default)]
    pub auto_bind_uniforms: Option<bool>,
    #[serde(default)]
    pub hlsl_io_mapping: Option<bool>,
    #[serde(default)]
    pub hlsl_offsets: Option<bool>,
    #[serde(default)]
    pub binding_base: Vec<BindingBaseArgs>,
    #[serde(default)]
    pub binding_base_for_stage: Vec<BindingBaseForStageArgs>,
    #[serde(default)]
    pub hlsl_register_set_and_binding: Vec<HlslRegisterSetAndBindingArgs>,
    #[serde(default)]
    pub hlsl_register_set_and_binding_for_stage: Vec<HlslRegisterSetAndBindingForStageArgs>,
    #[serde(default)]
    pub hlsl_functionality: Option<bool>,
    #[serde(default)]
    pub invert_y: Option<bool>,
    #[serde(default)]
    pub nan_clamp: Option<bool>,
    #[serde(default, alias = "define")]
    pub macro_definition: Vec<MacroDefinitionArgs>,
    #[serde(default, deserialize_with = "shaderc_serde::de_opt_optimization_level")]
    pub optimization_level: Option<shaderc::OptimizationLevel>,
    #[serde(default, alias = "debug")]
    pub generate_debug_info: bool,
    #[serde(default)]
    pub suppress_warnings: bool,
    #[serde(default)]
    pub warnings_as_errors: bool,
}

impl Args {
    pub fn to_options(&self) -> Option<shaderc::CompileOptions> {
        #[cfg(feature = "debug")]
        {
            emit_call_site_warning!("debugging compiler options");
        }
        let mut options = shaderc::CompileOptions::new()?;
        if let Some(TargetEnvArgs { env, version }) = self.target_env {
            options.set_target_env(env, version as u32);
            #[cfg(feature = "debug")]
            {
                     emit_call_site_warning!(format!(
                    "options.set_target_env({:?}, {:?});",
                    env, version
                ));
            }
        }
        if let Some(target_spirv) = self.target_spirv {
            options.set_target_spirv(target_spirv);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_target_spirv({:?});", target_spirv));
            }
        }
        if let Some(source_language) = self.source_language {
            options.set_source_language(source_language);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!(
                    "options.set_source_language({:?});",
                    source_language
                ));
            }
        }
        if let ForcedVersionProfileArgs {
            version: Some(version),
            profile,
        } = self.forced_version_profile
        {
            let profile = profile.unwrap_or(shaderc::GlslProfile::None);
            options.set_forced_version_profile(version, profile);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!(
                    "options.set_forced_version_profile({:?}, {:?});",
                    version, profile
                ));
            }
        }
        for LimitArgs { limit, value } in &self.limit {
            options.set_limit(*limit, *value);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_limit({:?}, {:?});", limit, value));
            }
        }
        if let Some(auto_bind_uniforms) = self.auto_bind_uniforms {
            options.set_auto_bind_uniforms(auto_bind_uniforms);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!(
                    "options.set_auto_bind_uniforms({:?});",
                    auto_bind_uniforms
                ));
            }
        }
        if let Some(hlsl_io_mapping) = self.hlsl_io_mapping {
            options.set_hlsl_io_mapping(hlsl_io_mapping);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_hlsl_io_mapping({:?});", hlsl_io_mapping));
            }
        }
        if let Some(hlsl_offsets) = self.hlsl_offsets {
            options.set_hlsl_offsets(hlsl_offsets);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_hlsl_offsets({:?});", hlsl_offsets));
            }
        }
        for BindingBaseArgs {
            resource_kind,
            base,
        } in &self.binding_base
        {
            options.set_binding_base(*resource_kind, *base);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_binding_base({:?}, {:?});", resource_kind, base));
            }
        }
        for BindingBaseForStageArgs {
            shader_kind,
            resource_kind,
            base,
        } in &self.binding_base_for_stage
        {
            options.set_binding_base_for_stage(*shader_kind, *resource_kind, *base);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_binding_base_for_stage({:?}, {:?}, {:?});", shader_kind, resource_kind, base));
            }
        }
        for HlslRegisterSetAndBindingArgs {
            register,
            set,
            binding,
        } in &self.hlsl_register_set_and_binding
        {
            options.set_hlsl_register_set_and_binding(register, set, binding);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_hlsl_register_set_and_binding({:?}, {:?}, {:?});", register, set, binding));
            }
        }
        for HlslRegisterSetAndBindingForStageArgs {
            kind,
            register,
            set,
            binding,
        } in &self.hlsl_register_set_and_binding_for_stage
        {
            options.set_hlsl_register_set_and_binding_for_stage(*kind, register, set, binding);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_hlsl_register_set_and_binding_for_stage({:?}, {:?}, {:?}, {:?});", kind, register, set, binding));
            }
        }
        if let Some(hlsl_functionality) = self.hlsl_functionality {
            options.set_hlsl_functionality1(hlsl_functionality);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_hlsl_functionality1({:?});", hlsl_functionality));
            }
        }
        if let Some(invert_y) = self.invert_y {
            options.set_invert_y(invert_y);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_invert_y({:?});", invert_y));
            }
        }
        if let Some(nan_clamp) = self.nan_clamp {
            options.set_nan_clamp(nan_clamp);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_nan_clamp({:?});", nan_clamp));
            }
        }
        for MacroDefinitionArgs { name, value } in &self.macro_definition {
            options.add_macro_definition(name, value.as_ref().map(|s| s.as_str()));
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.add_macro_definition({:?}, {:?});", name, value));
            }
        }
        if let Some(optimization_level) = self.optimization_level {
            options.set_optimization_level(optimization_level);
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!(format!("options.set_optimization_level({:?});", optimization_level));
            }
        }
        if self.generate_debug_info {
            options.set_generate_debug_info();
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!("options.set_generate_debug_info();");
            }
        }
        if self.suppress_warnings {
            options.set_suppress_warnings();
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!("options.set_suppress_warnings();");
            }
        }
        if self.warnings_as_errors {
            options.set_warnings_as_errors();
            #[cfg(feature = "debug")]
            {
                emit_call_site_warning!("options.set_warnings_as_errors();");
            }
        }
        Some(options)
    }
}