diff --git a/src/rendering/vulkan/renderer/vk_postprocess.cpp b/src/rendering/vulkan/renderer/vk_postprocess.cpp index 37ed16bc64..5fe545ac83 100644 --- a/src/rendering/vulkan/renderer/vk_postprocess.cpp +++ b/src/rendering/vulkan/renderer/vk_postprocess.cpp @@ -35,7 +35,7 @@ void VkPostprocess::SetActiveRenderTarget() imageTransition.addImage(buffers->PipelineImage[mCurrentPipelineImage].get(), &buffers->PipelineLayout[mCurrentPipelineImage], VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, false); imageTransition.execute(fb->GetDrawCommands()); - fb->GetRenderPassManager()->SetRenderTarget(buffers->PipelineView[mCurrentPipelineImage].get(), buffers->GetWidth(), buffers->GetHeight(), VK_SAMPLE_COUNT_1_BIT); + fb->GetRenderState()->SetRenderTarget(buffers->PipelineView[mCurrentPipelineImage].get(), buffers->GetWidth(), buffers->GetHeight(), VK_SAMPLE_COUNT_1_BIT); } void VkPostprocess::PostProcessScene(int fixedcm, const std::function &afterBloomDrawEndScene2D) diff --git a/src/rendering/vulkan/renderer/vk_renderpass.cpp b/src/rendering/vulkan/renderer/vk_renderpass.cpp index 916cc05323..50b40e0c4c 100644 --- a/src/rendering/vulkan/renderer/vk_renderpass.cpp +++ b/src/rendering/vulkan/renderer/vk_renderpass.cpp @@ -28,46 +28,6 @@ void VkRenderPassManager::RenderBuffersReset() RenderPassSetup.clear(); } -void VkRenderPassManager::SetRenderTarget(VulkanImageView *view, int width, int height, VkSampleCountFlagBits samples) -{ - GetVulkanFrameBuffer()->GetRenderState()->EndRenderPass(); - mRenderTargetView = view; - mRenderTargetWidth = width; - mRenderTargetHeight = height; - mSamples = samples; -} - -void VkRenderPassManager::BeginRenderPass(const VkRenderPassKey &key, VulkanCommandBuffer *cmdbuffer) -{ - auto fb = GetVulkanFrameBuffer(); - auto buffers = fb->GetBuffers(); - - VkRenderPassSetup *passSetup = GetRenderPass(key); - - auto &framebuffer = passSetup->Framebuffer[mRenderTargetView->view]; - if (!framebuffer) - { - auto buffers = fb->GetBuffers(); - FramebufferBuilder builder; - builder.setRenderPass(passSetup->RenderPass.get()); - builder.setSize(mRenderTargetWidth, mRenderTargetHeight); - builder.addAttachment(mRenderTargetView->view); - if (key.UsesDepthStencil()) - builder.addAttachment(buffers->SceneDepthStencilView.get()); - framebuffer = builder.create(GetVulkanFrameBuffer()->device); - framebuffer->SetDebugName("VkRenderPassSetup.Framebuffer"); - } - - RenderPassBegin beginInfo; - beginInfo.setRenderPass(passSetup->RenderPass.get()); - beginInfo.setRenderArea(0, 0, buffers->GetWidth(), buffers->GetHeight()); - beginInfo.setFramebuffer(framebuffer.get()); - beginInfo.addClearColor(screen->mSceneClearColor[0], screen->mSceneClearColor[1], screen->mSceneClearColor[2], screen->mSceneClearColor[3]); - beginInfo.addClearDepthStencil(1.0f, 0); - cmdbuffer->beginRenderPass(beginInfo); - cmdbuffer->bindPipeline(VK_PIPELINE_BIND_POINT_GRAPHICS, passSetup->Pipeline.get()); -} - VkRenderPassSetup *VkRenderPassManager::GetRenderPass(const VkRenderPassKey &key) { auto &item = RenderPassSetup[key]; @@ -274,8 +234,9 @@ void VkRenderPassSetup::CreatePipeline(const VkRenderPassKey &key) // builder.addDynamicState(VK_DYNAMIC_STATE_STENCIL_WRITE_MASK); builder.addDynamicState(VK_DYNAMIC_STATE_STENCIL_REFERENCE); - builder.setViewport(0.0f, 0.0f, (float)SCREENWIDTH, (float)SCREENHEIGHT); - builder.setScissor(0, 0, SCREENWIDTH, SCREENHEIGHT); + // Note: the actual values are ignored since we use dynamic viewport+scissor states + builder.setViewport(0.0f, 0.0f, 320.0f, 200.0f); + builder.setScissor(0, 0, 320.0f, 200.0f); static const VkPrimitiveTopology vktopology[] = { VK_PRIMITIVE_TOPOLOGY_POINT_LIST, diff --git a/src/rendering/vulkan/renderer/vk_renderpass.h b/src/rendering/vulkan/renderer/vk_renderpass.h index c521d220d9..9d94761c2f 100644 --- a/src/rendering/vulkan/renderer/vk_renderpass.h +++ b/src/rendering/vulkan/renderer/vk_renderpass.h @@ -69,13 +69,9 @@ public: void Init(); void RenderBuffersReset(); - void SetRenderTarget(VulkanImageView *view, int width, int height, VkSampleCountFlagBits samples); - void BeginRenderPass(const VkRenderPassKey &key, VulkanCommandBuffer *cmdbuffer); - + VkRenderPassSetup *GetRenderPass(const VkRenderPassKey &key); int GetVertexFormat(int numBindingPoints, int numAttributes, size_t stride, const FVertexBufferAttribute *attrs); - VkSampleCountFlagBits GetSamples() const { return mSamples; } - std::unique_ptr DynamicSetLayout; std::unique_ptr TextureSetLayout; std::unique_ptr PipelineLayout; @@ -93,10 +89,4 @@ private: void CreateDescriptorPool(); void CreateDynamicSet(); - VkRenderPassSetup *GetRenderPass(const VkRenderPassKey &key); - - VulkanImageView *mRenderTargetView = nullptr; - int mRenderTargetWidth = 0; - int mRenderTargetHeight = 0; - VkSampleCountFlagBits mSamples = VK_SAMPLE_COUNT_1_BIT; }; diff --git a/src/rendering/vulkan/renderer/vk_renderstate.cpp b/src/rendering/vulkan/renderer/vk_renderstate.cpp index b17cba5561..12149e89c0 100644 --- a/src/rendering/vulkan/renderer/vk_renderstate.cpp +++ b/src/rendering/vulkan/renderer/vk_renderstate.cpp @@ -189,8 +189,6 @@ void VkRenderState::ApplyDepthBias() void VkRenderState::ApplyRenderPass(int dt) { - auto passManager = GetVulkanFrameBuffer()->GetRenderPassManager(); - // Find a render pass that matches our state VkRenderPassKey passKey; passKey.ClearTargets = mRenderPassKey.ClearTargets | mClearTargets; @@ -206,7 +204,7 @@ void VkRenderState::ApplyRenderPass(int dt) passKey.StencilPassOp = mStencilOp; passKey.ColorMask = mColorMask; passKey.CullMode = mCullMode; - passKey.Samples = passManager->GetSamples(); + passKey.Samples = mRenderTarget.Samples; if (mSpecialEffect > EFF_NONE) { passKey.SpecialEffect = mSpecialEffect; @@ -241,7 +239,7 @@ void VkRenderState::ApplyRenderPass(int dt) if (changingRenderPass) { passKey.ClearTargets = mClearTargets; - passManager->BeginRenderPass(passKey, mCommandBuffer); + BeginRenderPass(passKey, mCommandBuffer); mRenderPassKey = passKey; mClearTargets = 0; } @@ -261,15 +259,12 @@ void VkRenderState::ApplyScissor() if (mScissorChanged) { VkRect2D scissor; - auto buffers = GetVulkanFrameBuffer()->GetBuffers(); - int targetWidth = buffers->GetWidth(); - int targetHeight = buffers->GetHeight(); if (mScissorWidth >= 0) { - int x0 = clamp(mScissorX, 0, targetWidth); - int y0 = clamp(mScissorY, 0, targetHeight); - int x1 = clamp(mScissorX + mScissorWidth, 0, targetWidth); - int y1 = clamp(mScissorY + mScissorHeight, 0, targetHeight); + int x0 = clamp(mScissorX, 0, mRenderTarget.Width); + int y0 = clamp(mScissorY, 0, mRenderTarget.Height); + int x1 = clamp(mScissorX + mScissorWidth, 0, mRenderTarget.Width); + int y1 = clamp(mScissorY + mScissorHeight, 0, mRenderTarget.Height); scissor.offset.x = x0; scissor.offset.y = y0; @@ -280,8 +275,8 @@ void VkRenderState::ApplyScissor() { scissor.offset.x = 0; scissor.offset.y = 0; - scissor.extent.width = targetWidth; - scissor.extent.height = targetHeight; + scissor.extent.width = mRenderTarget.Width; + scissor.extent.height = mRenderTarget.Height; } mCommandBuffer->setScissor(0, 1, &scissor); mScissorChanged = false; @@ -293,7 +288,6 @@ void VkRenderState::ApplyViewport() if (mViewportChanged) { VkViewport viewport; - auto buffers = GetVulkanFrameBuffer()->GetBuffers(); if (mViewportWidth >= 0) { viewport.x = (float)mViewportX; @@ -305,8 +299,8 @@ void VkRenderState::ApplyViewport() { viewport.x = 0.0f; viewport.y = 0.0f; - viewport.width = (float)buffers->GetWidth(); - viewport.height = (float)buffers->GetHeight(); + viewport.width = (float)mRenderTarget.Width; + viewport.height = (float)mRenderTarget.Height; } viewport.minDepth = mViewportDepthMin; viewport.maxDepth = mViewportDepthMax; @@ -573,6 +567,45 @@ void VkRenderState::EndFrame() mDataIndex = -1; } +void VkRenderState::SetRenderTarget(VulkanImageView *view, int width, int height, VkSampleCountFlagBits samples) +{ + EndRenderPass(); + + mRenderTarget.View = view; + mRenderTarget.Width = width; + mRenderTarget.Height = height; + mRenderTarget.Samples = samples; +} + +void VkRenderState::BeginRenderPass(const VkRenderPassKey &key, VulkanCommandBuffer *cmdbuffer) +{ + auto fb = GetVulkanFrameBuffer(); + + VkRenderPassSetup *passSetup = fb->GetRenderPassManager()->GetRenderPass(key); + + auto &framebuffer = passSetup->Framebuffer[mRenderTarget.View->view]; + if (!framebuffer) + { + FramebufferBuilder builder; + builder.setRenderPass(passSetup->RenderPass.get()); + builder.setSize(mRenderTarget.Width, mRenderTarget.Height); + builder.addAttachment(mRenderTarget.View->view); + if (key.UsesDepthStencil()) + builder.addAttachment(fb->GetBuffers()->SceneDepthStencilView.get()); + framebuffer = builder.create(GetVulkanFrameBuffer()->device); + framebuffer->SetDebugName("VkRenderPassSetup.Framebuffer"); + } + + RenderPassBegin beginInfo; + beginInfo.setRenderPass(passSetup->RenderPass.get()); + beginInfo.setRenderArea(0, 0, mRenderTarget.Width, mRenderTarget.Height); + beginInfo.setFramebuffer(framebuffer.get()); + beginInfo.addClearColor(screen->mSceneClearColor[0], screen->mSceneClearColor[1], screen->mSceneClearColor[2], screen->mSceneClearColor[3]); + beginInfo.addClearDepthStencil(1.0f, 0); + cmdbuffer->beginRenderPass(beginInfo); + cmdbuffer->bindPipeline(VK_PIPELINE_BIND_POINT_GRAPHICS, passSetup->Pipeline.get()); +} + ///////////////////////////////////////////////////////////////////////////// void VkRenderStateMolten::Draw(int dt, int index, int count, bool apply) diff --git a/src/rendering/vulkan/renderer/vk_renderstate.h b/src/rendering/vulkan/renderer/vk_renderstate.h index 064106389d..0a9be61cf9 100644 --- a/src/rendering/vulkan/renderer/vk_renderstate.h +++ b/src/rendering/vulkan/renderer/vk_renderstate.h @@ -42,6 +42,7 @@ public: void EnableMultisampling(bool on) override; void EnableLineSmooth(bool on) override; + void SetRenderTarget(VulkanImageView *view, int width, int height, VkSampleCountFlagBits samples); void Bind(int bindingpoint, uint32_t offset); void EndRenderPass(); void EndFrame(); @@ -60,6 +61,8 @@ protected: void ApplyVertexBuffers(); void ApplyMaterial(); + void BeginRenderPass(const VkRenderPassKey &key, VulkanCommandBuffer *cmdbuffer); + bool mDepthClamp = true; VulkanCommandBuffer *mCommandBuffer = nullptr; VkRenderPassKey mRenderPassKey = {}; @@ -107,6 +110,14 @@ protected: bool mLastSplitEnabled = true; bool mLastModelMatrixEnabled = true; bool mLastTextureMatrixEnabled = true; + + struct RenderTarget + { + VulkanImageView *View = nullptr; + int Width = 0; + int Height = 0; + VkSampleCountFlagBits Samples = VK_SAMPLE_COUNT_1_BIT; + } mRenderTarget; }; class VkRenderStateMolten : public VkRenderState diff --git a/src/rendering/vulkan/system/vk_framebuffer.cpp b/src/rendering/vulkan/system/vk_framebuffer.cpp index 0e2ba04219..698cf21c89 100644 --- a/src/rendering/vulkan/system/vk_framebuffer.cpp +++ b/src/rendering/vulkan/system/vk_framebuffer.cpp @@ -331,7 +331,7 @@ sector_t *VulkanFrameBuffer::RenderViewpoint(FRenderViewpoint &mainvp, AActor * if (mainview) // Bind the scene frame buffer and turn on draw buffers used by ssao { - mRenderPassManager->SetRenderTarget(GetBuffers()->SceneColorView.get(), GetBuffers()->GetWidth(), GetBuffers()->GetHeight(), GetBuffers()->GetSceneSamples()); + mRenderState->SetRenderTarget(GetBuffers()->SceneColorView.get(), GetBuffers()->GetWidth(), GetBuffers()->GetHeight(), GetBuffers()->GetSceneSamples()); #if 0 bool useSSAO = (gl_ssao != 0); GetRenderState()->SetPassType(useSSAO ? GBUFFER_PASS : NORMAL_PASS);