Skip to content

Commit 4044e7a

Browse files
committed
[update] render commands to support binding vertex buffers.
1 parent c015425 commit 4044e7a

6 files changed

Lines changed: 88 additions & 23 deletions

File tree

crates/lambda-platform/src/gfx/buffer.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,20 @@ impl<RenderBackend: super::internal::Backend> Buffer<RenderBackend> {
4040
gpu.internal_logical_device().destroy_buffer(self.buffer);
4141
}
4242
}
43+
44+
/// Size of each buffer element in bytes.
4345
pub fn stride(&self) -> usize {
4446
return self.stride;
4547
}
4648
}
4749

50+
impl<RenderBackend: super::internal::Backend> Buffer<RenderBackend> {
51+
/// Retrieve a reference to the internal buffer.
52+
pub(super) fn internal_buffer(&self) -> &RenderBackend::Buffer {
53+
return &self.buffer;
54+
}
55+
}
56+
4857
pub struct BufferBuilder {
4958
buffer_length: usize,
5059
usage: Usage,

crates/lambda-platform/src/gfx/command.rs

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,9 @@ pub enum Command<RenderBackend: gfx_hal::Backend> {
9696
offset: u32,
9797
bytes: Vec<u32>,
9898
},
99+
BindVertexBuffer {
100+
buffer: Rc<super::buffer::Buffer<RenderBackend>>,
101+
},
99102
EndRecording,
100103
}
101104

@@ -187,6 +190,13 @@ impl<'command_pool, RenderBackend: gfx_hal::Backend>
187190
Command::Draw { vertices } => {
188191
self.command_buffer.draw(vertices.clone(), 0..1)
189192
}
193+
Command::BindVertexBuffer { buffer } => {
194+
self.command_buffer.bind_vertex_buffers(
195+
0,
196+
vec![(buffer.internal_buffer(), gfx_hal::buffer::SubRange::WHOLE)]
197+
.into_iter(),
198+
)
199+
}
190200
Command::EndRecording => self.command_buffer.finish(),
191201
}
192202
}
@@ -386,7 +396,8 @@ impl<RenderBackend: gfx_hal::Backend> CommandPool<RenderBackend> {
386396
pub fn destroy(mut self, gpu: &super::gpu::Gpu<RenderBackend>) {
387397
unsafe {
388398
self.command_pool.reset(true);
389-
super::gpu::internal::logical_device_for(gpu)
399+
gpu
400+
.internal_logical_device()
390401
.destroy_command_pool(self.command_pool);
391402
}
392403
}

lambda/examples/push_constants.rs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -238,6 +238,10 @@ impl Component for PushConstantsExample {
238238
.clone(),
239239
viewport: viewport.clone(),
240240
},
241+
RenderCommand::BindVertexBuffer {
242+
pipeline: render_pipeline.clone(),
243+
buffer: 0,
244+
},
241245
RenderCommand::PushConstants {
242246
pipeline: render_pipeline.clone(),
243247
stage: PipelineStage::VERTEX,
@@ -247,8 +251,11 @@ impl Component for PushConstantsExample {
247251
render_matrix: mesh_matrix,
248252
})),
249253
},
250-
RenderCommand::Draw { vertices: 0..3 },
254+
RenderCommand::Draw {
255+
vertices: 0..self.mesh.as_ref().unwrap().vertices().len() as u32,
256+
},
251257
];
258+
252259
commands.push(RenderCommand::EndRenderPass);
253260

254261
return commands;

lambda/src/core/render/buffer.rs

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ mod internal {
77
};
88
}
99

10+
use std::rc::Rc;
11+
1012
// publicly use Properties and Usage from buffer.rs
1113
pub use lambda_platform::gfx::buffer::{
1214
BufferType,
@@ -21,7 +23,7 @@ use super::{
2123

2224
#[derive(Debug)]
2325
pub struct Buffer {
24-
buffer: internal::Buffer<super::internal::RenderBackend>,
26+
buffer: Rc<internal::Buffer<super::internal::RenderBackend>>,
2527
buffer_type: BufferType,
2628
}
2729

@@ -30,13 +32,21 @@ impl Buffer {
3032
/// Destroy the buffer and all it's resources with the render context that
3133
/// created it.
3234
pub fn destroy(self, render_context: &RenderContext) {
33-
self.buffer.destroy(render_context.internal_gpu());
35+
Rc::try_unwrap(self.buffer)
36+
.expect("Failed to get inside buffer")
37+
.destroy(render_context.internal_gpu());
3438
}
3539
}
3640

3741
/// Internal interface for working with buffers.
3842
impl Buffer {
3943
/// Retrieve a reference to the internal buffer.
44+
pub(super) fn internal_buffer_rc(
45+
&self,
46+
) -> Rc<internal::Buffer<super::internal::RenderBackend>> {
47+
return self.buffer.clone();
48+
}
49+
4050
pub(super) fn internal_buffer(
4151
&self,
4252
) -> &internal::Buffer<super::internal::RenderBackend> {
@@ -78,7 +88,7 @@ impl BufferBuilder {
7888
match internal_buffer {
7989
Ok(internal_buffer) => {
8090
return Ok(Buffer {
81-
buffer: internal_buffer,
91+
buffer: Rc::new(internal_buffer),
8292
buffer_type: BufferType::Vertex,
8393
});
8494
}
@@ -126,7 +136,7 @@ impl BufferBuilder {
126136
match buffer_allocation {
127137
Ok(buffer) => {
128138
return Ok(Buffer {
129-
buffer,
139+
buffer: Rc::new(buffer),
130140
buffer_type: self.buffer_type,
131141
});
132142
}

lambda/src/core/render/command.rs

Lines changed: 25 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,10 @@ pub enum RenderCommand {
3737
offset: u32,
3838
bytes: Vec<u32>,
3939
},
40+
BindVertexBuffer {
41+
pipeline: super::ResourceId,
42+
buffer: u32,
43+
},
4044
/// Draws a graphical primitive.
4145
Draw {
4246
vertices: Range<u32>,
@@ -47,15 +51,15 @@ impl RenderCommand {
4751
/// Converts the RenderCommand into a platform compatible render command.
4852
// TODO(vmarcella): implement this using Into<PlatformRenderCommand>
4953
pub fn into_platform_command(
50-
self,
54+
&self,
5155
render_context: &mut RenderContext,
5256
) -> PlatformRenderCommand {
5357
return match self {
5458
RenderCommand::SetViewports {
5559
start_at,
5660
viewports,
5761
} => PlatformRenderCommand::SetViewports {
58-
start_at,
62+
start_at: *start_at,
5963
viewports: viewports
6064
.into_iter()
6165
.map(|viewport| viewport.clone_gfx_viewport())
@@ -65,7 +69,7 @@ impl RenderCommand {
6569
start_at,
6670
viewports,
6771
} => PlatformRenderCommand::SetScissors {
68-
start_at,
72+
start_at: *start_at,
6973
viewports: viewports
7074
.into_iter()
7175
.map(|viewport| viewport.clone_gfx_viewport())
@@ -78,14 +82,14 @@ impl RenderCommand {
7882
let surface = surface_from_context(render_context);
7983
let frame_buffer = render_context.allocate_and_get_frame_buffer(
8084
render_context
81-
.get_render_pass(render_pass)
85+
.get_render_pass(*render_pass)
8286
.into_gfx_render_pass()
8387
.as_ref(),
8488
);
8589

8690
PlatformRenderCommand::BeginRenderPass {
8791
render_pass: render_context
88-
.get_render_pass(render_pass)
92+
.get_render_pass(*render_pass)
8993
.into_gfx_render_pass(),
9094
surface: surface.clone(),
9195
frame_buffer: frame_buffer.clone(),
@@ -97,7 +101,7 @@ impl RenderCommand {
97101
PlatformRenderCommand::AttachGraphicsPipeline {
98102
pipeline: render_context
99103
.render_pipelines
100-
.get(pipeline)
104+
.get(*pipeline)
101105
.unwrap()
102106
.into_platform_render_pipeline(),
103107
}
@@ -110,13 +114,25 @@ impl RenderCommand {
110114
} => PlatformRenderCommand::PushConstants {
111115
pipeline: render_context
112116
.render_pipelines
113-
.get(pipeline)
117+
.get(*pipeline)
114118
.unwrap()
115119
.into_platform_render_pipeline(),
116-
stage,
117-
offset,
120+
stage: *stage,
121+
offset: *offset,
118122
bytes: bytes.clone(),
119123
},
124+
RenderCommand::BindVertexBuffer { pipeline, buffer } => {
125+
PlatformRenderCommand::BindVertexBuffer {
126+
buffer: render_context
127+
.render_pipelines
128+
.get(*pipeline)
129+
.unwrap()
130+
.buffers()
131+
.get(*buffer as usize)
132+
.unwrap()
133+
.internal_buffer_rc(),
134+
}
135+
}
120136
RenderCommand::Draw { vertices } => PlatformRenderCommand::Draw {
121137
vertices: vertices.clone(),
122138
},

lambda/src/core/render/pipeline.rs

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
use std::rc::Rc;
1+
use std::{
2+
borrow::Borrow,
3+
ops::Deref,
4+
rc::Rc,
5+
};
26

37
use lambda_platform::gfx::{
48
buffer::Buffer as InternalBuffer,
@@ -25,22 +29,30 @@ pub struct RenderPipeline {
2529
super::internal::RenderBackend,
2630
>,
2731
>,
28-
buffers: Vec<Buffer>,
32+
buffers: Vec<Rc<Buffer>>,
2933
}
3034

3135
impl RenderPipeline {
3236
/// Destroy the render pipeline with the render context that created it.
3337
pub fn destroy(self, render_context: &RenderContext) {
3438
Rc::try_unwrap(self.pipeline)
3539
.expect("Failed to destroy render pipeline")
36-
.destroy(gpu_from_context(render_context));
40+
.destroy(render_context.internal_gpu());
3741

3842
for buffer in self.buffers {
39-
buffer.destroy(render_context);
43+
Rc::try_unwrap(buffer)
44+
.expect("Failed to get high level buffer.")
45+
.destroy(render_context);
4046
}
4147
}
48+
}
49+
50+
impl RenderPipeline {
51+
pub(super) fn buffers(&self) -> &Vec<Rc<Buffer>> {
52+
return &self.buffers;
53+
}
4254

43-
pub fn into_platform_render_pipeline(
55+
pub(super) fn into_platform_render_pipeline(
4456
&self,
4557
) -> Rc<lambda_platform::gfx::pipeline::RenderPipeline<RenderBackend>> {
4658
return self.pipeline.clone();
@@ -55,7 +67,7 @@ pub use lambda_platform::gfx::{
5567

5668
pub struct RenderPipelineBuilder {
5769
push_constants: Vec<PushConstantUpload>,
58-
buffers: Vec<Buffer>,
70+
buffers: Vec<Rc<Buffer>>,
5971
attributes: Vec<VertexAttribute>,
6072
}
6173

@@ -74,7 +86,7 @@ impl RenderPipelineBuilder {
7486
buffer: Buffer,
7587
attributes: Vec<VertexAttribute>,
7688
) -> Self {
77-
self.buffers.push(buffer);
89+
self.buffers.push(Rc::new(buffer));
7890
self.attributes.extend(attributes);
7991
return self;
8092
}
@@ -117,7 +129,7 @@ impl RenderPipelineBuilder {
117129
let internal_buffers = buffers
118130
.iter()
119131
.map(|b| b.internal_buffer())
120-
.collect::<Vec<&InternalBuffer<RenderBackend>>>();
132+
.collect::<Vec<_>>();
121133

122134
let render_pipeline = builder
123135
.with_push_constants(self.push_constants.clone())

0 commit comments

Comments
 (0)