#[derive(Default)]
pub(crate) struct OverlayTextResources {
pub(crate) pipeline: Option<wgpu::RenderPipeline>,
pub(crate) bgl: Option<wgpu::BindGroupLayout>,
pub(crate) sampler: Option<wgpu::Sampler>,
}
impl crate::resources::DeviceResources {
pub(crate) fn ensure_overlay_text_pipeline(&mut self, device: &wgpu::Device) {
if self.overlay_text.pipeline.is_some() {
return;
}
let bgl = crate::resources::builders::texture_sampler_bgl(
device,
"overlay_text_bgl",
wgpu::ShaderStages::FRAGMENT,
);
let sampler =
crate::resources::builders::clamp_linear_sampler(device, "overlay_text_sampler");
let layout = device.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
label: Some("overlay_text_layout"),
bind_group_layouts: &[&bgl],
push_constant_ranges: &[],
});
let shader = crate::resources::builders::wgsl_module(
device,
"overlay_text.wgsl",
crate::resources::builders::wgsl_source!("overlay_text"),
);
let pipeline = device.create_render_pipeline(&wgpu::RenderPipelineDescriptor {
label: Some("overlay_text_pipeline"),
layout: Some(&layout),
vertex: wgpu::VertexState {
module: &shader,
entry_point: Some("vs_main"),
buffers: &[OverlayTextVertex::buffer_layout()],
compilation_options: wgpu::PipelineCompilationOptions::default(),
},
primitive: wgpu::PrimitiveState {
topology: wgpu::PrimitiveTopology::TriangleList,
..Default::default()
},
depth_stencil: Some(wgpu::DepthStencilState {
format: wgpu::TextureFormat::Depth24PlusStencil8,
depth_write_enabled: false,
depth_compare: wgpu::CompareFunction::Always,
stencil: wgpu::StencilState::default(),
bias: wgpu::DepthBiasState::default(),
}),
multisample: wgpu::MultisampleState::default(),
fragment: Some(wgpu::FragmentState {
module: &shader,
entry_point: Some("fs_main"),
targets: &[Some(wgpu::ColorTargetState {
format: self.target_format,
blend: Some(wgpu::BlendState {
color: wgpu::BlendComponent {
src_factor: wgpu::BlendFactor::SrcAlpha,
dst_factor: wgpu::BlendFactor::OneMinusSrcAlpha,
operation: wgpu::BlendOperation::Add,
},
alpha: wgpu::BlendComponent {
src_factor: wgpu::BlendFactor::One,
dst_factor: wgpu::BlendFactor::OneMinusSrcAlpha,
operation: wgpu::BlendOperation::Add,
},
}),
write_mask: wgpu::ColorWrites::ALL,
})],
compilation_options: wgpu::PipelineCompilationOptions::default(),
}),
multiview: None,
cache: None,
});
self.overlay_text.bgl = Some(bgl);
self.overlay_text.sampler = Some(sampler);
self.overlay_text.pipeline = Some(pipeline);
}
}
#[repr(C)]
#[derive(Copy, Clone, bytemuck::Pod, bytemuck::Zeroable)]
pub(crate) struct OverlayTextVertex {
pub position: [f32; 2],
pub uv: [f32; 2],
pub colour: [f32; 4],
pub use_texture: f32,
pub _pad: f32,
}
impl OverlayTextVertex {
pub fn buffer_layout() -> wgpu::VertexBufferLayout<'static> {
wgpu::VertexBufferLayout {
array_stride: std::mem::size_of::<OverlayTextVertex>() as wgpu::BufferAddress,
step_mode: wgpu::VertexStepMode::Vertex,
attributes: &[
wgpu::VertexAttribute {
offset: 0,
shader_location: 0,
format: wgpu::VertexFormat::Float32x2,
},
wgpu::VertexAttribute {
offset: 8,
shader_location: 1,
format: wgpu::VertexFormat::Float32x2,
},
wgpu::VertexAttribute {
offset: 16,
shader_location: 2,
format: wgpu::VertexFormat::Float32x4,
},
wgpu::VertexAttribute {
offset: 32,
shader_location: 3,
format: wgpu::VertexFormat::Float32,
},
],
}
}
}
pub(crate) struct LabelGpuData {
pub vertex_buf: wgpu::Buffer,
pub vertex_count: u32,
pub bind_group: wgpu::BindGroup,
}