Update
Some checks failed
Build legacy Nix package on Ubuntu / build (push) Failing after 1s

This commit is contained in:
Florian RICHER 2024-11-24 19:24:28 +01:00
parent c0367144a6
commit dd8a5a97ea
Signed by: florian.richer
GPG key ID: C73D37CBED7BFC77
9 changed files with 83 additions and 13 deletions

10
res/shaders/vertex.frag Normal file
View file

@ -0,0 +1,10 @@
#version 450
#extension GL_ARB_separate_shader_objects: enable
layout (location = 0) in vec3 fragColor;
layout (location = 0) out vec4 outColor;
void main() {
outColor = vec4(fragColor, 1.0);
}

1
res/shaders/vertex.vert Normal file
View file

@ -0,0 +1 @@
#version 450 #extension GL_ARB_separate_shader_objects: enable // NOTE: names must match the `Vertex` struct in Rust layout (location = 0) in vec2 pos; layout (location = 1) in vec3 color; layout (location = 0) out vec3 fragColor; out gl_PerVertex { vec4 gl_Position; }; void main() { gl_Position = vec4(pos, 0.0, 1.0); fragColor = color; }

View file

@ -38,3 +38,4 @@ mod vk_fence;
pub(self) use vk_fence::VkFence;
mod utils;
mod vertex;

33
src/vulkan/vertex.rs Normal file
View file

@ -0,0 +1,33 @@
use ash::vk;
use std::mem::offset_of;
#[derive(Default)]
pub struct Vertex {
pub position: [f32; 2],
pub color: [f32; 3],
}
impl Vertex {
pub fn get_binding_description() -> vk::VertexInputBindingDescription {
vk::VertexInputBindingDescription::default()
.binding(0)
.stride(size_of::<Self>() as u32)
.input_rate(vk::VertexInputRate::VERTEX)
}
pub fn get_attribute_descriptions() -> [vk::VertexInputAttributeDescription; 2] {
let position_attribute = vk::VertexInputAttributeDescription::default()
.binding(0)
.location(0)
.format(vk::Format::R32G32_SFLOAT)
.offset(offset_of!(Vertex, position) as u32);
let color_attribute = vk::VertexInputAttributeDescription::default()
.binding(0)
.location(1)
.format(vk::Format::R32G32B32_SFLOAT)
.offset(offset_of!(Vertex, color) as u32);
[position_attribute, color_attribute]
}
}

View file

@ -6,7 +6,6 @@ use std::sync::Arc;
pub struct VkGraphicsPipeline {
device: Arc<VkDevice>,
swapchain: Arc<VkSwapchain>,
render_pass: Arc<VkRenderPass>,
pub(super) pipeline_layout: vk::PipelineLayout,
@ -18,7 +17,6 @@ pub struct VkGraphicsPipeline {
impl VkGraphicsPipeline {
pub fn new(
device: &Arc<VkDevice>,
swapchain: &Arc<VkSwapchain>,
render_pass: &Arc<VkRenderPass>,
) -> anyhow::Result<Self> {
let shader_entry_name = CStr::from_bytes_with_nul(b"main\0")?;
@ -99,7 +97,6 @@ impl VkGraphicsPipeline {
Ok(Self {
device: device.clone(),
swapchain: swapchain.clone(),
render_pass: render_pass.clone(),
pipeline_layout,
pipeline,

View file

@ -62,7 +62,7 @@ impl VkRenderContext {
.create_framebuffers(&render_pass)
.ok_or_else(|| anyhow::anyhow!("Failed to get framebuffers"))?;
let pipeline = Arc::new(VkGraphicsPipeline::new(&device, &swapchain, &render_pass)?);
let pipeline = Arc::new(VkGraphicsPipeline::new(&device, &render_pass)?);
let command_pool = VkCommandPool::new(&device)?;
@ -109,6 +109,10 @@ impl VkRenderContext {
.swapchain
.acquire_next_image(&self.image_available_semaphore)?;
// if self.swapchain.is_dirty() {
// self.update_swapchain()?
// }
let command_buffer = self.command_buffers[index as usize];
unsafe { self.device.handle.reset_command_buffer(command_buffer, vk::CommandBufferResetFlags::default())? };
@ -152,7 +156,7 @@ impl VkRenderContext {
unsafe { self.device.handle.cmd_set_viewport(command_buffer, 0, &[viewport]) }
let scissor = vk::Rect2D::default().extent(self.swapchain.surface_resolution);
let scissor = self.swapchain.surface_resolution.into();
unsafe { self.device.handle.cmd_set_scissor(command_buffer, 0, &[scissor]) }
@ -196,8 +200,9 @@ impl VkRenderContext {
}
pub fn update_resolution(&mut self, width: u32, height: u32) -> anyhow::Result<()> {
if let Some(swapchain) = Arc::get_mut(&mut self.swapchain) {
swapchain.update_resolution(width, height)?;
match Arc::get_mut(&mut self.swapchain) {
Some(swapchain) => swapchain.update_resolution(width, height)?,
None => log::warn!("Impossible to get mutable swapchain"),
}
Ok(())
@ -206,4 +211,19 @@ impl VkRenderContext {
pub fn exit(&self) {
unsafe { self.device.handle.device_wait_idle().unwrap() }
}
fn update_swapchain(&mut self) -> anyhow::Result<()> {
match Arc::get_mut(&mut self.swapchain) {
Some(swapchain) => {
swapchain.create_swapchain()?;
self.framebuffers = self.swapchain
.create_framebuffers(&self.render_pass)
.ok_or_else(|| anyhow::anyhow!("Failed to get framebuffers"))?;
}
None => log::warn!("Impossible to get mutable swapchain"),
}
Ok(())
}
}

View file

@ -5,7 +5,6 @@ use std::sync::Arc;
pub struct VkRenderPass {
device: Arc<VkDevice>,
swapchain: Arc<VkSwapchain>,
pub(super) handle: vk::RenderPass,
}
@ -42,7 +41,6 @@ impl VkRenderPass {
Ok(Self {
device: device.clone(),
swapchain: swapchain.clone(),
handle: render_pass,
})
}

View file

@ -12,6 +12,7 @@ pub struct SwapchainSupportDetails(
pub struct VkSurface {
instance: Arc<VkInstance>,
pub(super) surface: vk::SurfaceKHR,
}

View file

@ -17,6 +17,7 @@ pub struct VkSwapchain {
pub(super) desired_image_count: u32,
pub(super) surface_format: vk::SurfaceFormatKHR,
pub(super) surface_resolution: vk::Extent2D,
pub(super) new_requested_surface_resolution: Option<vk::Extent2D>,
pub(super) present_mode: vk::PresentModeKHR,
pub(super) pre_transform: vk::SurfaceTransformFlagsKHR,
@ -64,6 +65,7 @@ impl VkSwapchain {
device: device.clone(),
swapchain: None,
new_requested_surface_resolution: None,
swapchain_support_details,
desired_image_count,
surface_format,
@ -80,6 +82,11 @@ impl VkSwapchain {
}
pub(super) fn create_swapchain(&mut self) -> VkResult<()> {
if let Some(new_requested_surface_resolution) = self.new_requested_surface_resolution {
self.surface_resolution = new_requested_surface_resolution;
self.new_requested_surface_resolution = None;
}
let mut swapchain_create_info = self.create_swapchain_info(&self.surface);
if let Some(old_swapchain) = self.swapchain {
@ -154,14 +161,12 @@ impl VkSwapchain {
if chosen_extent.width != self.surface_resolution.width
|| chosen_extent.height != self.surface_resolution.height
{
self.surface_resolution = chosen_extent;
self.new_requested_surface_resolution = Some(chosen_extent);
log::debug!(
"New resolution applied ({}x{})",
"New resolution submitted ({}x{})",
chosen_extent.width,
chosen_extent.height
);
self.create_swapchain()?;
} else {
log::debug!("New resolution skipped ({width}x{height}) : Same resolution");
}
@ -180,6 +185,10 @@ impl VkSwapchain {
}
}
pub(super) fn is_dirty(&self) -> bool {
self.new_requested_surface_resolution.is_some()
}
fn create_swapchain_info(&self, surface: &VkSurface) -> vk::SwapchainCreateInfoKHR {
vk::SwapchainCreateInfoKHR::default()
.surface(surface.surface)