diff --git a/src/BehPipelines.cpp b/src/BehPipelines.cpp index b6eca15..6faea8e 100644 --- a/src/BehPipelines.cpp +++ b/src/BehPipelines.cpp @@ -37,28 +37,6 @@ BehPipeline::BehPipeline(std::shared_ptr& device, PipelineConfigurati .primitiveRestartEnable = VK_FALSE }; - vk::Viewport viewport { - .x = 0.0f, - .y = 0.0f, - .width = static_cast(config.extent.width), - .height = static_cast(config.extent.height), - .minDepth = 0.0f, - .maxDepth = 1.0f - }; - - vk::Rect2D scissor { - .offset = {0, 0}, - .extent = config.extent - }; - - vk::PipelineViewportStateCreateInfo viewportState { - .viewportCount = 1, - .pViewports = &viewport, - .scissorCount = 1, - .pScissors = &scissor, - }; - - vk::PipelineRasterizationStateCreateInfo rasterizer { .depthClampEnable = VK_FALSE, .rasterizerDiscardEnable = VK_FALSE, @@ -109,6 +87,21 @@ BehPipeline::BehPipeline(std::shared_ptr& device, PipelineConfigurati .stencilTestEnable = VK_FALSE }; + std::vector dynamicStates { + vk::DynamicState::eScissor, + vk::DynamicState::eViewport + }; + + vk::PipelineDynamicStateCreateInfo dynamicStateCreateInfo { + .dynamicStateCount = static_cast(dynamicStates.size()), + .pDynamicStates = dynamicStates.data() + }; + + vk::PipelineViewportStateCreateInfo viewportState { + .viewportCount = 1, + .scissorCount = 1, + }; + vk::GraphicsPipelineCreateInfo pipelineInfo { // Reference programmable stages .stageCount = static_cast(shaderStageCreateInfos.size()), @@ -122,6 +115,7 @@ BehPipeline::BehPipeline(std::shared_ptr& device, PipelineConfigurati .pMultisampleState = &multisampling, .pDepthStencilState = &depthStencil, .pColorBlendState = &colorBlending, + .pDynamicState = &dynamicStateCreateInfo, // A vulkan handle, not a struct pointer .layout = config.pipelineLayout, diff --git a/src/Renderer.cpp b/src/Renderer.cpp index 9beacb3..cc9b1fd 100644 --- a/src/Renderer.cpp +++ b/src/Renderer.cpp @@ -172,7 +172,6 @@ void Renderer::recreateSwapchain() { createSwapChain(); createImageViews(); createRenderPass(); - createPipelines(); createColorResources(); createDepthResources(); createFramebuffers(); @@ -826,70 +825,89 @@ void Renderer::createCommandBuffers() { void Renderer::recordCommandBuffer(uint32_t index, FrameInfo& frameInfo) { vk::CommandBufferBeginInfo beginInfo {}; - try { - commandBuffers[index].begin(beginInfo); - } - catch (vk::SystemError& err) { - throw std::runtime_error(std::string("failed to begin recording command buffer!") + err.what()); - } + try { + commandBuffers[index].begin(beginInfo); + } + catch (vk::SystemError& err) { + throw std::runtime_error(std::string("failed to begin recording command buffer!") + err.what()); + } - std::array clearValues{}; - clearValues[0].color = {std::array{ 0.0f, 0.0f, 0.0f, 1.0f }}; - clearValues[1].depthStencil = vk::ClearDepthStencilValue {1.0f, 0}; + std::array clearValues{}; + clearValues[0].color = {std::array{ 0.0f, 0.0f, 0.0f, 1.0f }}; + clearValues[1].depthStencil = vk::ClearDepthStencilValue {1.0f, 0}; + + vk::RenderPassBeginInfo renderPassInfo { + .renderPass = renderPass, + .framebuffer = swapChainFramebuffers[index], + .renderArea = { + .offset = {0, 0}, + .extent = swapChainExtent, + }, + .clearValueCount = static_cast(clearValues.size()), + .pClearValues = clearValues.data() + }; - vk::RenderPassBeginInfo renderPassInfo { - .renderPass = renderPass, - .framebuffer = swapChainFramebuffers[index], - .renderArea = { - .offset = {0, 0}, - .extent = swapChainExtent, - }, - .clearValueCount = static_cast(clearValues.size()), - .pClearValues = clearValues.data() - }; + vk::Rect2D scissor { + .offset = {0, 0}, + .extent = swapChainExtent + }; - commandBuffers[index].beginRenderPass(renderPassInfo, vk::SubpassContents::eInline); - { - //Add commands to buffer - if(rendererMode == NORMAL) { - graphicsPipeline->bind(commandBuffers[index]); - } - else if(rendererMode == WIREFRAME) { - wireframePipeline->bind(commandBuffers[index]); - } - commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout, 0, 1, &descriptorSets[index], 0, nullptr); + commandBuffers[index].setScissor(0, 1, &scissor); - for (const auto& model : frameInfo.objects) { - vk::Buffer vertexBuffers[] = { model->mesh->_vertexBuffer._buffer }; - vk::DeviceSize offsets[] = { 0 }; - commandBuffers[index].bindVertexBuffers(0, 1, vertexBuffers, offsets); + vk::Viewport viewport { + .x = 0.0f, + .y = 0.0f, + .width = static_cast(swapChainExtent.width), + .height = static_cast(swapChainExtent.height), + .minDepth = 0.0f, + .maxDepth = 1.0f + }; - commandBuffers[index].bindIndexBuffer(model->mesh->_indexBuffer._buffer, 0, vk::IndexType::eUint32); + commandBuffers[index].setViewport(0, 1, &viewport); - commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout, 1, 1, &model->material.textureSet, 0, nullptr); - MeshPushConstants constants = model->transformMatrix; - commandBuffers[index].pushConstants(pipelineLayout, vk::ShaderStageFlagBits::eVertex, 0, sizeof(MeshPushConstants), &constants); - - commandBuffers[index].drawIndexed(static_cast(model->mesh->_indices.size()), 1, 0, 0, 0); - } + commandBuffers[index].beginRenderPass(renderPassInfo, vk::SubpassContents::eInline); + { + //Add commands to buffer + if(rendererMode == NORMAL) { + graphicsPipeline->bind(commandBuffers[index]); + } + else if(rendererMode == WIREFRAME) { + wireframePipeline->bind(commandBuffers[index]); + } + commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout, 0, 1, &descriptorSets[index], 0, nullptr); - // Point lights - billboardPipeline->bind(commandBuffers[index]); - commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, billboardPipelineLayout, 0, 1, &descriptorSets[index], 0, nullptr); - commandBuffers[index].draw(6, 1, 0, 0); - } + for (const auto& model : frameInfo.objects) { + vk::Buffer vertexBuffers[] = { model->mesh->_vertexBuffer._buffer }; + vk::DeviceSize offsets[] = { 0 }; + commandBuffers[index].bindVertexBuffers(0, 1, vertexBuffers, offsets); - ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), commandBuffers[index]); - - commandBuffers[index].endRenderPass(); + commandBuffers[index].bindIndexBuffer(model->mesh->_indexBuffer._buffer, 0, vk::IndexType::eUint32); - try { - commandBuffers[index].end(); - } - catch (vk::SystemError& err) { - throw std::runtime_error(std::string("failed to record command buffer!") + err.what()); - } + commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout, 1, 1, &model->material.textureSet, 0, nullptr); + + MeshPushConstants constants = model->transformMatrix; + commandBuffers[index].pushConstants(pipelineLayout, vk::ShaderStageFlagBits::eVertex, 0, sizeof(MeshPushConstants), &constants); + + commandBuffers[index].drawIndexed(static_cast(model->mesh->_indices.size()), 1, 0, 0, 0); + } + + // Point lights + billboardPipeline->bind(commandBuffers[index]); + commandBuffers[index].bindDescriptorSets(vk::PipelineBindPoint::eGraphics, billboardPipelineLayout, 0, 1, &descriptorSets[index], 0, nullptr); + commandBuffers[index].draw(6, 1, 0, 0); + } + + ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), commandBuffers[index]); + + commandBuffers[index].endRenderPass(); + + try { + commandBuffers[index].end(); + } + catch (vk::SystemError& err) { + throw std::runtime_error(std::string("failed to record command buffer!") + err.what()); + } } void Renderer::createSyncObjects() {