From 0c236856f4126b0d4dc09c07d87c61dfd7205d02 Mon Sep 17 00:00:00 2001 From: Wunkolo Date: Wed, 9 Oct 2024 17:26:58 -0700 Subject: [PATCH] vk: Additional `VK_EXT_provoking_vertex` pipeline fixes --- core/rend/vulkan/oit/oit_drawer.cpp | 10 +++++++++- core/rend/vulkan/oit/oit_pipeline.cpp | 22 ++++++++++++++++++++++ core/rend/vulkan/pipeline.cpp | 11 +++++++++++ 3 files changed, 42 insertions(+), 1 deletion(-) diff --git a/core/rend/vulkan/oit/oit_drawer.cpp b/core/rend/vulkan/oit/oit_drawer.cpp index f4ed5b3c8..2695ad3eb 100644 --- a/core/rend/vulkan/oit/oit_drawer.cpp +++ b/core/rend/vulkan/oit/oit_drawer.cpp @@ -341,7 +341,15 @@ bool OITDrawer::Draw(const Texture *fogTexture, const Texture *paletteTexture) bool firstFrameAfterInit = oitBuffers->isFirstFrameAfterInit(); oitBuffers->OnNewFrame(cmdBuffer); - setFirstProvokingVertex(pvrrc); + if (VulkanContext::Instance()->hasProvokingVertex()) + { + // Pipelines are using VK_EXT_provoking_vertex, no need to + // re-order vertices + } + else + { + setFirstProvokingVertex(pvrrc); + } // Upload vertex and index buffers UploadMainBuffer(vtxUniforms, fragUniforms); diff --git a/core/rend/vulkan/oit/oit_pipeline.cpp b/core/rend/vulkan/oit/oit_pipeline.cpp index 890ac0313..b6d3d31db 100644 --- a/core/rend/vulkan/oit/oit_pipeline.cpp +++ b/core/rend/vulkan/oit/oit_pipeline.cpp @@ -317,6 +317,17 @@ void OITPipelineManager::CreateClearPipeline() 0.0f, // depthBiasSlopeFactor 1.0f // lineWidth ); + + // Dreamcast uses the last vertex as the provoking vertex, but Vulkan uses the first. + // Utilize VK_EXT_provoking_vertex when available to set the provoking vertex to be the + // last vertex + vk::PipelineRasterizationProvokingVertexStateCreateInfoEXT provokingVertexInfo{}; + if (GetContext()->hasProvokingVertex()) + { + provokingVertexInfo.provokingVertexMode = vk::ProvokingVertexModeEXT::eLastVertex; + pipelineRasterizationStateCreateInfo.pNext = &provokingVertexInfo; + } + vk::PipelineMultisampleStateCreateInfo pipelineMultisampleStateCreateInfo; // Depth and stencil @@ -522,6 +533,17 @@ void OITPipelineManager::CreateTrModVolPipeline(ModVolMode mode, int cullMode, b 0.0f, // depthBiasSlopeFactor 1.0f // lineWidth ); + + // Dreamcast uses the last vertex as the provoking vertex, but Vulkan uses the first. + // Utilize VK_EXT_provoking_vertex when available to set the provoking vertex to be the + // last vertex + vk::PipelineRasterizationProvokingVertexStateCreateInfoEXT provokingVertexInfo{}; + if (GetContext()->hasProvokingVertex()) + { + provokingVertexInfo.provokingVertexMode = vk::ProvokingVertexModeEXT::eLastVertex; + pipelineRasterizationStateCreateInfo.pNext = &provokingVertexInfo; + } + vk::PipelineMultisampleStateCreateInfo pipelineMultisampleStateCreateInfo; // Depth and stencil diff --git a/core/rend/vulkan/pipeline.cpp b/core/rend/vulkan/pipeline.cpp index c0de95156..fa2e45a8b 100644 --- a/core/rend/vulkan/pipeline.cpp +++ b/core/rend/vulkan/pipeline.cpp @@ -200,6 +200,17 @@ void PipelineManager::CreateDepthPassPipeline(int cullMode, bool naomi2) 0.0f, // depthBiasSlopeFactor 1.0f // lineWidth ); + + // Dreamcast uses the last vertex as the provoking vertex, but Vulkan uses the first. + // Utilize VK_EXT_provoking_vertex when available to set the provoking vertex to be the + // last vertex + vk::PipelineRasterizationProvokingVertexStateCreateInfoEXT provokingVertexInfo{}; + if (GetContext()->hasProvokingVertex()) + { + provokingVertexInfo.provokingVertexMode = vk::ProvokingVertexModeEXT::eLastVertex; + pipelineRasterizationStateCreateInfo.pNext = &provokingVertexInfo; + } + vk::PipelineMultisampleStateCreateInfo pipelineMultisampleStateCreateInfo; // Depth and stencil