From 3c9aca3fcba83c68e94b12fca61771e54a6bd1a9 Mon Sep 17 00:00:00 2001 From: Sascha Willems Date: Tue, 9 May 2023 18:03:51 +0200 Subject: [PATCH] Add stencil format require toggle Fixes #1031 --- base/VulkanTools.cpp | 28 +++++++++++++++++++++--- base/VulkanTools.h | 14 +++++++----- base/vulkanexamplebase.cpp | 14 ++++++++---- base/vulkanexamplebase.h | 3 ++- examples/stencilbuffer/stencilbuffer.cpp | 4 +++- 5 files changed, 48 insertions(+), 15 deletions(-) diff --git a/base/VulkanTools.cpp b/base/VulkanTools.cpp index a760f6e3..25b1ce07 100644 --- a/base/VulkanTools.cpp +++ b/base/VulkanTools.cpp @@ -82,7 +82,7 @@ namespace vks { // Since all depth formats may be optional, we need to find a suitable depth format to use // Start with the highest precision packed format - std::vector depthFormats = { + std::vector formatList = { VK_FORMAT_D32_SFLOAT_S8_UINT, VK_FORMAT_D32_SFLOAT, VK_FORMAT_D24_UNORM_S8_UINT, @@ -90,11 +90,10 @@ namespace vks VK_FORMAT_D16_UNORM }; - for (auto& format : depthFormats) + for (auto& format : formatList) { VkFormatProperties formatProps; vkGetPhysicalDeviceFormatProperties(physicalDevice, format, &formatProps); - // Format must support depth stencil attachment for optimal tiling if (formatProps.optimalTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) { *depthFormat = format; @@ -105,6 +104,29 @@ namespace vks return false; } + VkBool32 getSupportedDepthStencilFormat(VkPhysicalDevice physicalDevice, VkFormat* depthStencilFormat) + { + std::vector formatList = { + VK_FORMAT_D32_SFLOAT_S8_UINT, + VK_FORMAT_D24_UNORM_S8_UINT, + VK_FORMAT_D16_UNORM_S8_UINT, + }; + + for (auto& format : formatList) + { + VkFormatProperties formatProps; + vkGetPhysicalDeviceFormatProperties(physicalDevice, format, &formatProps); + if (formatProps.optimalTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) + { + *depthStencilFormat = format; + return true; + } + } + + return false; + } + + VkBool32 formatHasStencil(VkFormat format) { std::vector stencilFormats = { diff --git a/base/VulkanTools.h b/base/VulkanTools.h index e1fce43e..c597b696 100644 --- a/base/VulkanTools.h +++ b/base/VulkanTools.h @@ -1,10 +1,10 @@ /* -* Assorted Vulkan helper functions -* -* Copyright (C) 2016 by Sascha Willems - www.saschawillems.de -* -* This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) -*/ + * Assorted Vulkan helper functions + * + * Copyright (C) 2016-2023 by Sascha Willems - www.saschawillems.de + * + * This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) + */ #pragma once @@ -78,6 +78,8 @@ namespace vks // Selected a suitable supported depth format starting with 32 bit down to 16 bit // Returns false if none of the depth formats in the list is supported by the device VkBool32 getSupportedDepthFormat(VkPhysicalDevice physicalDevice, VkFormat *depthFormat); + // Same as getSupportedDepthFormat but will only select formats that also have stencil + VkBool32 getSupportedDepthStencilFormat(VkPhysicalDevice physicalDevice, VkFormat* depthStencilFormat); // Returns tru a given format support LINEAR filtering VkBool32 formatIsFilterable(VkPhysicalDevice physicalDevice, VkFormat format, VkImageTiling tiling); diff --git a/base/vulkanexamplebase.cpp b/base/vulkanexamplebase.cpp index c73a4656..3bad890b 100644 --- a/base/vulkanexamplebase.cpp +++ b/base/vulkanexamplebase.cpp @@ -1,7 +1,7 @@ /* * Vulkan Example base class * -* Copyright (C) by Sascha Willems - www.saschawillems.de +* Copyright (C) 2016-2023 by Sascha Willems - www.saschawillems.de * * This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) */ @@ -1043,9 +1043,15 @@ bool VulkanExampleBase::initVulkan() // Get a graphics queue from the device vkGetDeviceQueue(device, vulkanDevice->queueFamilyIndices.graphics, 0, &queue); - // Find a suitable depth format - VkBool32 validDepthFormat = vks::tools::getSupportedDepthFormat(physicalDevice, &depthFormat); - assert(validDepthFormat); + // Find a suitable depth and/or stencil format + VkBool32 validFormat{ false }; + // Sample that make use of stencil will require a depth + stencil format, so we select from a different list + if (requiresStencil) { + validFormat = vks::tools::getSupportedDepthStencilFormat(physicalDevice, &depthFormat); + } else { + validFormat = vks::tools::getSupportedDepthFormat(physicalDevice, &depthFormat); + } + assert(validFormat); swapChain.connect(instance, physicalDevice, device); diff --git a/base/vulkanexamplebase.h b/base/vulkanexamplebase.h index abdd61f5..91100f73 100644 --- a/base/vulkanexamplebase.h +++ b/base/vulkanexamplebase.h @@ -1,7 +1,7 @@ /* * Vulkan Example base class * -* Copyright (C) by Sascha Willems - www.saschawillems.de +* Copyright (C) 2016-2023 by Sascha Willems - www.saschawillems.de * * This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) */ @@ -154,6 +154,7 @@ protected: VkSemaphore renderComplete; } semaphores; std::vector waitFences; + bool requiresStencil{ false }; public: bool prepared = false; bool resized = false; diff --git a/examples/stencilbuffer/stencilbuffer.cpp b/examples/stencilbuffer/stencilbuffer.cpp index 1deb28b4..6ce72bb7 100644 --- a/examples/stencilbuffer/stencilbuffer.cpp +++ b/examples/stencilbuffer/stencilbuffer.cpp @@ -1,7 +1,7 @@ /* * Vulkan Example - Rendering outlines using the stencil buffer * -* Copyright (C) 2016-2017 by Sascha Willems - www.saschawillems.de +* Copyright (C) 2016-2023 by Sascha Willems - www.saschawillems.de * * This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) */ @@ -43,6 +43,8 @@ public: camera.setPerspective(60.0f, (float)width / (float)height, 0.1f, 512.0f); camera.setRotation(glm::vec3(2.5f, -35.0f, 0.0f)); camera.setTranslation(glm::vec3(0.0f, 0.0f, -2.0f)); + // This samples requires a format that supports depth AND stencil, which will be handled by the base class + requiresStencil = true; } ~VulkanExample()