Skip to main content

astrelis_render/
blend.rs

1//! Blend mode presets for common rendering scenarios.
2
3/// Predefined blend modes for common use cases.
4///
5/// Use these to configure how source and destination colors are combined
6/// during rendering.
7#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
8#[derive(Default)]
9pub enum BlendMode {
10    /// No blending - source completely replaces destination.
11    Replace,
12
13    /// Standard alpha blending for transparent content.
14    ///
15    /// Formula: `src.rgb * src.a + dst.rgb * (1 - src.a)`
16    ///
17    /// Use for: Transparent UI over game content, sprites with transparency.
18    #[default]
19    Alpha,
20
21    /// Premultiplied alpha blending.
22    ///
23    /// Formula: `src.rgb + dst.rgb * (1 - src.a)`
24    ///
25    /// Use for: Blitting framebuffers with premultiplied alpha, compositing.
26    PremultipliedAlpha,
27
28    /// Additive blending - colors are added together.
29    ///
30    /// Formula: `src.rgb + dst.rgb`
31    ///
32    /// Use for: Glow effects, particles, light sources.
33    Additive,
34
35    /// Multiplicative blending.
36    ///
37    /// Formula: `src.rgb * dst.rgb`
38    ///
39    /// Use for: Shadows, color tinting.
40    Multiply,
41
42    /// Custom blend state for advanced use cases.
43    Custom(wgpu::BlendState),
44}
45
46impl BlendMode {
47    /// Convert to wgpu BlendState.
48    pub fn to_blend_state(self) -> Option<wgpu::BlendState> {
49        match self {
50            BlendMode::Replace => Some(wgpu::BlendState::REPLACE),
51            BlendMode::Alpha => Some(wgpu::BlendState::ALPHA_BLENDING),
52            BlendMode::PremultipliedAlpha => Some(wgpu::BlendState::PREMULTIPLIED_ALPHA_BLENDING),
53            BlendMode::Additive => Some(wgpu::BlendState {
54                color: wgpu::BlendComponent {
55                    src_factor: wgpu::BlendFactor::SrcAlpha,
56                    dst_factor: wgpu::BlendFactor::One,
57                    operation: wgpu::BlendOperation::Add,
58                },
59                alpha: wgpu::BlendComponent {
60                    src_factor: wgpu::BlendFactor::One,
61                    dst_factor: wgpu::BlendFactor::One,
62                    operation: wgpu::BlendOperation::Add,
63                },
64            }),
65            BlendMode::Multiply => Some(wgpu::BlendState {
66                color: wgpu::BlendComponent {
67                    src_factor: wgpu::BlendFactor::Dst,
68                    dst_factor: wgpu::BlendFactor::Zero,
69                    operation: wgpu::BlendOperation::Add,
70                },
71                alpha: wgpu::BlendComponent {
72                    src_factor: wgpu::BlendFactor::DstAlpha,
73                    dst_factor: wgpu::BlendFactor::Zero,
74                    operation: wgpu::BlendOperation::Add,
75                },
76            }),
77            BlendMode::Custom(state) => Some(state),
78        }
79    }
80
81    /// Create a color target state with this blend mode.
82    pub fn to_color_target_state(self, format: wgpu::TextureFormat) -> wgpu::ColorTargetState {
83        wgpu::ColorTargetState {
84            format,
85            blend: self.to_blend_state(),
86            write_mask: wgpu::ColorWrites::ALL,
87        }
88    }
89}
90
91
92impl From<BlendMode> for Option<wgpu::BlendState> {
93    fn from(mode: BlendMode) -> Self {
94        mode.to_blend_state()
95    }
96}
97
98impl From<wgpu::BlendState> for BlendMode {
99    fn from(state: wgpu::BlendState) -> Self {
100        BlendMode::Custom(state)
101    }
102}