wgpu: Use vertex buffer and staging belt for glow filter
This commit is contained in:
parent
2722a6588e
commit
7e0bd48061
|
@ -67,67 +67,59 @@ impl<'a> FilterSource<'a> {
|
|||
]
|
||||
}
|
||||
|
||||
pub fn vertices_with_blur_offset(
|
||||
&self,
|
||||
device: &wgpu::Device,
|
||||
blur_offset: (f32, f32),
|
||||
) -> wgpu::Buffer {
|
||||
pub fn vertices_with_blur_offset(&self, blur_offset: (f32, f32)) -> [FilterVertexWithBlur; 4] {
|
||||
let source_width = self.texture.width() as f32;
|
||||
let source_height = self.texture.height() as f32;
|
||||
let source_left = self.point.0;
|
||||
let source_top = self.point.1;
|
||||
let source_right = source_left + self.size.0;
|
||||
let source_bottom = source_top + self.size.1;
|
||||
device.create_buffer_init(&wgpu::util::BufferInitDescriptor {
|
||||
label: create_debug_label!("Filter vertices").as_deref(),
|
||||
contents: bytemuck::cast_slice(&[
|
||||
FilterVertexWithBlur {
|
||||
position: [0.0, 0.0],
|
||||
source_uv: [
|
||||
source_left as f32 / source_width,
|
||||
source_top as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_left as f32 + blur_offset.0) / source_width,
|
||||
(source_top as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [1.0, 0.0],
|
||||
source_uv: [
|
||||
source_right as f32 / source_width,
|
||||
source_top as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_right as f32 + blur_offset.0) / source_width,
|
||||
(source_top as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [1.0, 1.0],
|
||||
source_uv: [
|
||||
source_right as f32 / source_width,
|
||||
source_bottom as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_right as f32 + blur_offset.0) / source_width,
|
||||
(source_bottom as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [0.0, 1.0],
|
||||
source_uv: [
|
||||
source_left as f32 / source_width,
|
||||
source_bottom as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_left as f32 + blur_offset.0) / source_width,
|
||||
(source_bottom as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
]),
|
||||
usage: wgpu::BufferUsages::VERTEX,
|
||||
})
|
||||
[
|
||||
FilterVertexWithBlur {
|
||||
position: [0.0, 0.0],
|
||||
source_uv: [
|
||||
source_left as f32 / source_width,
|
||||
source_top as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_left as f32 + blur_offset.0) / source_width,
|
||||
(source_top as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [1.0, 0.0],
|
||||
source_uv: [
|
||||
source_right as f32 / source_width,
|
||||
source_top as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_right as f32 + blur_offset.0) / source_width,
|
||||
(source_top as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [1.0, 1.0],
|
||||
source_uv: [
|
||||
source_right as f32 / source_width,
|
||||
source_bottom as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_right as f32 + blur_offset.0) / source_width,
|
||||
(source_bottom as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
FilterVertexWithBlur {
|
||||
position: [0.0, 1.0],
|
||||
source_uv: [
|
||||
source_left as f32 / source_width,
|
||||
source_bottom as f32 / source_height,
|
||||
],
|
||||
blur_uv: [
|
||||
(source_left as f32 + blur_offset.0) / source_width,
|
||||
(source_bottom as f32 + blur_offset.1) / source_height,
|
||||
],
|
||||
},
|
||||
]
|
||||
}
|
||||
|
||||
pub fn vertices_with_highlight_and_shadow(
|
||||
|
|
|
@ -2,7 +2,9 @@ use crate::backend::RenderTargetMode;
|
|||
use crate::buffer_pool::TexturePool;
|
||||
use crate::descriptors::Descriptors;
|
||||
use crate::filters::blur::BlurFilter;
|
||||
use crate::filters::{FilterSource, VERTEX_BUFFERS_DESCRIPTION_FILTERS_WITH_BLUR};
|
||||
use crate::filters::{
|
||||
FilterSource, FilterVertexWithBlur, VERTEX_BUFFERS_DESCRIPTION_FILTERS_WITH_BLUR,
|
||||
};
|
||||
use crate::surface::target::CommandTarget;
|
||||
use crate::utils::SampleCountMap;
|
||||
use bytemuck::{Pod, Zeroable};
|
||||
|
@ -23,14 +25,16 @@ struct GlowUniform {
|
|||
pub struct GlowFilter {
|
||||
bind_group_layout: wgpu::BindGroupLayout,
|
||||
pipeline_layout: wgpu::PipelineLayout,
|
||||
buffer: wgpu::Buffer,
|
||||
buffer_size: wgpu::BufferSize,
|
||||
vertex_buffer: wgpu::Buffer,
|
||||
uniform_buffer: wgpu::Buffer,
|
||||
vertices_size: wgpu::BufferSize,
|
||||
uniform_size: wgpu::BufferSize,
|
||||
pipeline: SampleCountMap<OnceLock<wgpu::RenderPipeline>>,
|
||||
}
|
||||
|
||||
impl GlowFilter {
|
||||
pub fn new(device: &wgpu::Device) -> Self {
|
||||
let buffer_size = std::mem::size_of::<GlowUniform>() as u64;
|
||||
let uniform_size = std::mem::size_of::<GlowUniform>() as u64;
|
||||
let bind_group_layout = device.create_bind_group_layout(&wgpu::BindGroupLayoutDescriptor {
|
||||
entries: &[
|
||||
wgpu::BindGroupLayoutEntry {
|
||||
|
@ -55,7 +59,7 @@ impl GlowFilter {
|
|||
ty: wgpu::BindingType::Buffer {
|
||||
ty: wgpu::BufferBindingType::Uniform,
|
||||
has_dynamic_offset: false,
|
||||
min_binding_size: wgpu::BufferSize::new(buffer_size),
|
||||
min_binding_size: wgpu::BufferSize::new(uniform_size),
|
||||
},
|
||||
count: None,
|
||||
},
|
||||
|
@ -73,9 +77,17 @@ impl GlowFilter {
|
|||
label: create_debug_label!("Blur filter binds").as_deref(),
|
||||
});
|
||||
|
||||
let buffer = device.create_buffer(&wgpu::BufferDescriptor {
|
||||
let vertices_size = std::mem::size_of::<[FilterVertexWithBlur; 4]>() as u64;
|
||||
let vertex_buffer = device.create_buffer(&wgpu::BufferDescriptor {
|
||||
label: None,
|
||||
size: buffer_size,
|
||||
size: vertices_size,
|
||||
usage: wgpu::BufferUsages::VERTEX | wgpu::BufferUsages::COPY_DST,
|
||||
mapped_at_creation: false,
|
||||
});
|
||||
|
||||
let uniform_buffer = device.create_buffer(&wgpu::BufferDescriptor {
|
||||
label: None,
|
||||
size: uniform_size,
|
||||
usage: wgpu::BufferUsages::UNIFORM | wgpu::BufferUsages::COPY_DST,
|
||||
mapped_at_creation: false,
|
||||
});
|
||||
|
@ -89,9 +101,11 @@ impl GlowFilter {
|
|||
Self {
|
||||
pipeline: Default::default(),
|
||||
pipeline_layout,
|
||||
buffer,
|
||||
vertex_buffer,
|
||||
uniform_buffer,
|
||||
bind_group_layout,
|
||||
buffer_size: wgpu::BufferSize::new(buffer_size).expect("Definitely not zero."),
|
||||
uniform_size: wgpu::BufferSize::new(uniform_size).expect("Definitely not zero."),
|
||||
vertices_size: wgpu::BufferSize::new(vertices_size).expect("Definitely not zero."),
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -181,9 +195,9 @@ impl GlowFilter {
|
|||
staging_belt
|
||||
.write_buffer(
|
||||
draw_encoder,
|
||||
&self.buffer,
|
||||
&self.uniform_buffer,
|
||||
0,
|
||||
self.buffer_size,
|
||||
self.uniform_size,
|
||||
&descriptors.device,
|
||||
)
|
||||
.copy_from_slice(bytemuck::cast_slice(&[GlowUniform {
|
||||
|
@ -198,7 +212,17 @@ impl GlowFilter {
|
|||
knockout: if filter.is_knockout() { 1 } else { 0 },
|
||||
composite_source: if filter.composite_source() { 1 } else { 0 },
|
||||
}]));
|
||||
let vertices = source.vertices_with_blur_offset(&descriptors.device, blur_offset);
|
||||
staging_belt
|
||||
.write_buffer(
|
||||
draw_encoder,
|
||||
&self.vertex_buffer,
|
||||
0,
|
||||
self.vertices_size,
|
||||
&descriptors.device,
|
||||
)
|
||||
.copy_from_slice(bytemuck::cast_slice(&[
|
||||
source.vertices_with_blur_offset(blur_offset)
|
||||
]));
|
||||
let filter_group = descriptors
|
||||
.device
|
||||
.create_bind_group(&wgpu::BindGroupDescriptor {
|
||||
|
@ -217,7 +241,7 @@ impl GlowFilter {
|
|||
},
|
||||
wgpu::BindGroupEntry {
|
||||
binding: 2,
|
||||
resource: self.buffer.as_entire_binding(),
|
||||
resource: self.uniform_buffer.as_entire_binding(),
|
||||
},
|
||||
wgpu::BindGroupEntry {
|
||||
binding: 3,
|
||||
|
@ -234,7 +258,7 @@ impl GlowFilter {
|
|||
|
||||
render_pass.set_bind_group(0, &filter_group, &[]);
|
||||
|
||||
render_pass.set_vertex_buffer(0, vertices.slice(..));
|
||||
render_pass.set_vertex_buffer(0, self.vertex_buffer.slice(..));
|
||||
render_pass.set_index_buffer(
|
||||
descriptors.quad.indices.slice(..),
|
||||
wgpu::IndexFormat::Uint32,
|
||||
|
|
Loading…
Reference in New Issue