From 3d6ca447a7104c499e92fc954affdaf4bf011388 Mon Sep 17 00:00:00 2001 From: Frederico Linhares Date: Fri, 16 Sep 2022 12:03:04 -0300 Subject: feat Create View --- src/vk/renderer.cpp | 169 ++++++++++++++++++++++++++++------------------------ 1 file changed, 92 insertions(+), 77 deletions(-) (limited to 'src/vk/renderer.cpp') diff --git a/src/vk/renderer.cpp b/src/vk/renderer.cpp index 33a4bf7..e806716 100644 --- a/src/vk/renderer.cpp +++ b/src/vk/renderer.cpp @@ -16,63 +16,13 @@ #include "renderer.hpp" +#include + #include "../core.hpp" namespace { -void -load_frame_sync(void *obj) -{ - auto self = static_cast(obj); - - self->image_available_semaphores.resize(self->max_frames_in_flight); - self->render_finished_semaphores.resize(self->max_frames_in_flight); - self->in_flight_fences.resize(self->max_frames_in_flight); - - VkSemaphoreCreateInfo semaphore_info = {}; - semaphore_info.sType = VK_STRUCTURE_TYPE_SEMAPHORE_CREATE_INFO; - semaphore_info.pNext = nullptr; - semaphore_info.flags = 0; - - VkFenceCreateInfo fence_info = {}; - fence_info.sType = VK_STRUCTURE_TYPE_FENCE_CREATE_INFO; - fence_info.pNext = nullptr; - fence_info.flags = VK_FENCE_CREATE_SIGNALED_BIT; - - // FIXME: if this loop fails, it will not destroy the semaphores. - for(auto i{0}; i < self->max_frames_in_flight; i++) - { - if(vkCreateSemaphore( - cg_core.vk_device_with_swapchain->device, &semaphore_info, - nullptr, &self->image_available_semaphores[i]) != VK_SUCCESS || - vkCreateSemaphore( - cg_core.vk_device_with_swapchain->device, &semaphore_info, - nullptr, &self->render_finished_semaphores[i]) != VK_SUCCESS || - vkCreateFence(cg_core.vk_device_with_swapchain->device, &fence_info, - nullptr, &self->in_flight_fences[i]) != VK_SUCCESS) - throw CommandError{"Failed to create semaphores."}; - } -} - -void -unload_frame_sync(void *obj) -{ - auto self = static_cast(obj); - - vkDeviceWaitIdle(cg_core.vk_device_with_swapchain->device); - - for(auto i{0}; i < self->max_frames_in_flight; i++) - { - vkDestroySemaphore(cg_core.vk_device_with_swapchain->device, - self->render_finished_semaphores[i], nullptr); - vkDestroySemaphore(cg_core.vk_device_with_swapchain->device, - self->image_available_semaphores[i], nullptr); - vkDestroyFence(cg_core.vk_device_with_swapchain->device, - self->in_flight_fences[i], nullptr); - } -} - void load_queue_family(void *obj) { @@ -103,9 +53,10 @@ unload_command_pool(void *obj) { auto self = static_cast(obj); - vkWaitForFences(cg_core.vk_device_with_swapchain->device, 2, - self->in_flight_fences.data(), VK_TRUE, - std::numeric_limits::max()); + vkWaitForFences(cg_core.vk_device_with_swapchain->device, + VK::Swapchain::max_frames_in_flight, + cg_core.vk_swapchain->in_flight_fences.data(), VK_TRUE, + std::numeric_limits::max()); vkDestroyCommandPool( self->queue_family->device->device, self->command_pool, nullptr); } @@ -132,7 +83,6 @@ load_draw_command_buffer(void *obj) } const CommandChain loader{ - {&load_frame_sync, &unload_frame_sync}, {&load_queue_family, nullptr}, {&load_command_pool, &unload_command_pool}, {&load_draw_command_buffer, nullptr} @@ -143,12 +93,18 @@ const CommandChain loader{ namespace VK { -Renderer::Renderer(): - current_frame{0} +Renderer::Renderer(std::vector> views): + models_to_draw{cg_core.vk_swapchain->images_count}, + views{views} { loader.execute(this); } +Renderer::Renderer(std::initializer_list> views): + Renderer{std::vector>(views)} +{ +} + Renderer::~Renderer() { loader.revert(this); @@ -158,24 +114,26 @@ void Renderer::draw() { vkWaitForFences(cg_core.vk_device_with_swapchain->device, 1, - &this->in_flight_fences[this->current_frame], VK_TRUE, - std::numeric_limits::max()); + &cg_core.vk_swapchain->in_flight_fences[ + cg_core.vk_swapchain->current_frame], VK_TRUE, + std::numeric_limits::max()); vkResetFences(cg_core.vk_device_with_swapchain->device, 1, - &this->in_flight_fences[this->current_frame]); + &cg_core.vk_swapchain->in_flight_fences[ + cg_core.vk_swapchain->current_frame]); uint32_t image_index; vkAcquireNextImageKHR( - cg_core.vk_device_with_swapchain->device, cg_core.vk_swapchain->swapchain, - std::numeric_limits::max(), - this->image_available_semaphores[this->current_frame], - VK_NULL_HANDLE, &image_index); + cg_core.vk_device_with_swapchain->device, + cg_core.vk_swapchain->swapchain, std::numeric_limits::max(), + cg_core.vk_swapchain->image_available_semaphores[ + cg_core.vk_swapchain->current_frame], VK_NULL_HANDLE, &image_index); VkCommandBuffer draw_command_buffer = - this->draw_command_buffers[this->current_frame]; + this->draw_command_buffers[cg_core.vk_swapchain->current_frame]; vkResetCommandBuffer(draw_command_buffer, 0); - auto next_frame = this->current_frame + 1; - if(next_frame == this->max_frames_in_flight) next_frame = 0; + auto next_frame = cg_core.vk_swapchain->current_frame + 1; + if(next_frame == Swapchain::max_frames_in_flight) next_frame = 0; // Begin command buffer. { @@ -187,10 +145,64 @@ Renderer::draw() throw std::runtime_error{"Failed to beggin draw command buffer."}; } - cg_core.vk_graphics_pipeline_3d->draw( - draw_command_buffer, current_frame, next_frame, image_index); - cg_core.vk_graphics_pipeline_2d->draw( - draw_command_buffer, current_frame, next_frame, image_index); + // 3D drawing. + { + // Dark gray blue. + std::array clear_values{}; + clear_values[0].color = {0.12f, 0.12f, 0.18f, 1.0f}; + clear_values[1].depthStencil = {1.0f, 0}; + + VkRenderPassBeginInfo render_pass_begin{}; + render_pass_begin.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; + render_pass_begin.pNext = nullptr; + render_pass_begin.renderPass = + cg_core.vk_graphics_pipeline_3d_layout->render_pass; + render_pass_begin.framebuffer = + cg_core.vk_graphics_pipeline_3d->swapchain_framebuffers[image_index]; + render_pass_begin.renderArea.offset = {0, 0}; + render_pass_begin.renderArea.extent = { + static_cast(cg_core.screen_width), + static_cast(cg_core.screen_height)}; + render_pass_begin.clearValueCount = clear_values.size(); + render_pass_begin.pClearValues = clear_values.data(); + + vkCmdBeginRenderPass( + draw_command_buffer, &render_pass_begin, VK_SUBPASS_CONTENTS_INLINE); + + for(auto &view: this->views) + cg_core.vk_graphics_pipeline_3d->draw( + view, draw_command_buffer, cg_core.vk_swapchain->current_frame, + image_index); + + vkCmdEndRenderPass(draw_command_buffer); + } + + // 2D drawing + { + VkRenderPassBeginInfo render_pass_begin{}; + render_pass_begin.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; + render_pass_begin.pNext = nullptr; + render_pass_begin.renderPass = + cg_core.vk_graphics_pipeline_2d_layout->render_pass; + render_pass_begin.framebuffer = + cg_core.vk_graphics_pipeline_2d->swapchain_framebuffers[image_index]; + render_pass_begin.renderArea.offset = {0, 0}; + render_pass_begin.renderArea.extent = { + static_cast(cg_core.screen_width), + static_cast(cg_core.screen_height)}; + render_pass_begin.clearValueCount = 0; + render_pass_begin.pClearValues = nullptr; + + vkCmdBeginRenderPass( + draw_command_buffer, &render_pass_begin, VK_SUBPASS_CONTENTS_INLINE); + + for(auto &view: this->views) + cg_core.vk_graphics_pipeline_2d->draw( + view, draw_command_buffer, cg_core.vk_swapchain->current_frame, + next_frame, image_index); + + vkCmdEndRenderPass(draw_command_buffer); + } // End command buffer. if(vkEndCommandBuffer(draw_command_buffer) != VK_SUCCESS) @@ -201,11 +213,13 @@ Renderer::draw() auto queue{this->queue_family->get_queue()}; VkSemaphore wait_semaphores[]{ - this->image_available_semaphores[this->current_frame]}; + cg_core.vk_swapchain->image_available_semaphores[ + cg_core.vk_swapchain->current_frame]}; VkPipelineStageFlags wait_stages[] = {VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT}; VkSemaphore signal_semaphores[]{ - this->render_finished_semaphores[this->current_frame]}; + cg_core.vk_swapchain->render_finished_semaphores[ + cg_core.vk_swapchain->current_frame]}; VkSubmitInfo submit_info{}; submit_info.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO; @@ -219,8 +233,8 @@ Renderer::draw() submit_info.pSignalSemaphores = signal_semaphores; if(vkQueueSubmit( - queue.queue, 1, &submit_info, - this->in_flight_fences[this->current_frame]) != VK_SUCCESS) + queue.queue, 1, &submit_info, cg_core.vk_swapchain->in_flight_fences[ + cg_core.vk_swapchain->current_frame]) != VK_SUCCESS) throw std::runtime_error{"Failed to submit draw command buffer."}; VkSwapchainKHR swap_chains[]{cg_core.vk_swapchain->swapchain}; @@ -239,7 +253,8 @@ Renderer::draw() } // Prepare for the next frame. - this->current_frame = next_frame; + this->models_to_draw[next_frame].clear(); + cg_core.vk_swapchain->current_frame = next_frame; } } -- cgit v1.2.3