summary refs log tree commit diff
path: root/src/graphics_scene.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/graphics_scene.rs')
-rw-r--r--src/graphics_scene.rs121
1 files changed, 121 insertions, 0 deletions
diff --git a/src/graphics_scene.rs b/src/graphics_scene.rs
new file mode 100644
index 0000000..771255a
--- /dev/null
+++ b/src/graphics_scene.rs
@@ -0,0 +1,121 @@
+#![deny(unsafe_code)]
+use crate::error::*;
+use crate::linear_algebra::{ Vec3, Vec4, Transformation };
+use crate::shader_data::VertexPushBlock;
+
+use std::f32::consts::{ TAU };
+use std::mem::size_of;
+
+use vulkanalia::Device;
+use vulkanalia::vk::{ self, HasBuilder, DeviceV1_0 };
+
+
+#[allow(unsafe_code)]
+pub fn generate_scene_commands(command_buffer: &vk::CommandBuffer,
+                               time: f32, device: &Device,
+                               extent: &vk::Extent2D,
+                               framebuffer: &vk::Framebuffer,
+                               render_pass: &vk::RenderPass,
+                               pipeline_layout: &vk::PipelineLayout,
+                               pipeline: &vk::Pipeline,
+                               vertex_buffer: &vk::Buffer,
+                               index_buffer: &vk::Buffer,
+                               index_count: usize,
+                               descriptor_set: &vk::DescriptorSet)
+    -> Result<()>
+{
+  let inheritance_info = vk::CommandBufferInheritanceInfo::builder();
+
+  let command_buffer_begin_info = vk::CommandBufferBeginInfo::builder()
+          .flags(vk::CommandBufferUsageFlags::empty())
+          .inheritance_info(&inheritance_info);
+
+  unsafe {
+    device.begin_command_buffer(*command_buffer, &command_buffer_begin_info)
+  }?;
+
+  let render_area = vk::Rect2D::builder()
+          .offset(vk::Offset2D::default())
+          .extent(*extent);
+
+  let color_clear_value = vk::ClearValue {
+    color: vk::ClearColorValue {
+      float32: [0.0, 0.0, 0.0, 1.0]
+    }
+  };
+  let depth_clear_value = vk::ClearValue {
+    depth_stencil: vk::ClearDepthStencilValue {
+      depth: 1.0,
+      stencil: 0,
+    }
+  };
+  let clear_values = [color_clear_value, depth_clear_value];
+
+  let begin_pass_info = vk::RenderPassBeginInfo::builder()
+          .render_pass(*render_pass)
+          .framebuffer(*framebuffer)
+          .render_area(render_area)
+          .clear_values(&clear_values);
+
+  unsafe {
+    device.cmd_begin_render_pass(*command_buffer, &begin_pass_info,
+                                 vk::SubpassContents::INLINE)
+  };
+
+  unsafe {
+    device.cmd_bind_pipeline(*command_buffer,
+                             vk::PipelineBindPoint::GRAPHICS,
+                             *pipeline)
+  };
+
+  unsafe {
+    device.cmd_bind_vertex_buffers(*command_buffer, 0,
+                                   &[*vertex_buffer], &[0])
+  };
+
+  unsafe {
+    device.cmd_bind_index_buffer(*command_buffer, *index_buffer, 0,
+                                 vk::IndexType::UINT32)
+  };
+
+  unsafe {
+    device.cmd_bind_descriptor_sets(*command_buffer,
+                                    vk::PipelineBindPoint::GRAPHICS,
+                                    *pipeline_layout,
+                                    0,
+                                    &[*descriptor_set],
+                                    &[])
+  };
+
+  let scale = Vec3::new(1.0, 1.0, 1.0);
+  let model = Transformation {
+    rotation: Vec4::rotation_quaternion(&Vec3::new(0.0, 1.0, 0.0), time % TAU),
+    translation: Vec3::new(0.0, 0.0, 0.0),
+  };
+  let push_block = VertexPushBlock::<f32> { scale, model };
+  let size = size_of::<VertexPushBlock::<f32>>();
+  let push_block_bytes = unsafe {
+    std::slice::from_raw_parts(&push_block as *const VertexPushBlock<f32>
+                                           as *const u8,
+                               size)
+  };
+
+  unsafe {
+    device.cmd_push_constants(*command_buffer, *pipeline_layout,
+                              vk::ShaderStageFlags::VERTEX,
+                              0,
+                              push_block_bytes)
+  };
+
+  unsafe {
+    device.cmd_draw_indexed(*command_buffer, index_count as u32,
+                            1, 0, 0, 0)
+  };
+
+  unsafe { device.cmd_end_render_pass(*command_buffer) };
+
+  unsafe { device.end_command_buffer(*command_buffer) }?;
+
+  Ok(())
+}
+