Skip to main content

easy_gpu/assets/compute/
bind_group.rs

1use crate::assets::compute::pipeline::ComputePipeline;
2use crate::assets::{Texture};
3use crate::assets::buffer::Buffer;
4use crate::assets_manager::Handle;
5use crate::Renderer;
6
7pub struct ComputeBindGroup{
8    pub bind_group: wgpu::BindGroup
9}
10
11pub struct ComputeBindGroupBuilder{
12    textures: Vec<(u32, Handle<Texture>)>,
13    storages: Vec<(u32,Handle<Buffer>)>,
14    uniforms: Vec<(u32,Handle<Buffer>)>,
15    pipeline: Handle<ComputePipeline>,
16}
17
18impl ComputeBindGroupBuilder{
19    pub fn new(pipeline: Handle<ComputePipeline>) -> Self{
20        Self{
21            textures: vec![],
22            storages: vec![],
23            uniforms: vec![],
24            pipeline,
25        }
26    }
27
28    pub fn texture(
29        mut self,
30        texture_binding: u32,
31        texture: Handle<Texture>,
32    ) -> Self {
33        self.textures.push((texture_binding, texture));
34        self
35    }
36    pub fn storage(
37        mut self,
38        binding: u32,
39        buffer: Handle<Buffer>,
40    ) -> Self {
41        self.storages.push((binding, buffer));
42        self
43    }
44    pub fn uniform(
45        mut self,
46        binding: u32,
47        buffer: Handle<Buffer>,
48    ) -> Self {
49        self.storages.push((binding, buffer));
50        self
51    }
52
53    pub fn build(&self,renderer: &mut Renderer) -> Handle<ComputeBindGroup> {
54        let pipeline = renderer.asset_manager.compute_pipelines.get(self.pipeline).unwrap();
55
56        let mut entries = Vec::new();
57
58        for (binding,handle) in &self.uniforms {
59            let uniform = renderer.asset_manager.buffers.get(*handle).unwrap();
60
61            entries.push(wgpu::BindGroupEntry {
62                binding:*binding,
63                resource: uniform.buffer.as_entire_binding(),
64            });
65        }
66
67        for (binding,handle) in &self.storages {
68            let storage = renderer.asset_manager.buffers.get(*handle).unwrap();
69
70            entries.push(wgpu::BindGroupEntry {
71                binding:*binding,
72                resource: storage.buffer.as_entire_binding(),
73            });
74        }
75
76        for (tex_binding,handle) in &self.textures {
77            let texture = renderer.asset_manager.textures.get(*handle).unwrap();
78
79            entries.push(wgpu::BindGroupEntry {
80                binding: *tex_binding,
81                resource: wgpu::BindingResource::TextureView(&texture.view),
82            });
83        }
84
85        let bind_group = renderer.device.create_bind_group(
86            &wgpu::BindGroupDescriptor {
87                label: Some("material bind group"),
88                layout: &pipeline.layout,
89                entries: &entries,
90            }
91        );
92
93        renderer.asset_manager.compute_bind_groups.insert(ComputeBindGroup{
94            bind_group,
95        })
96    }
97}