Enabled text overlay for samples with differing render pass setup

This commit is contained in:
saschawillems 2017-11-03 11:23:02 +01:00
parent 4e5d95c098
commit a8cb646a7c
2 changed files with 78 additions and 51 deletions

View file

@ -43,7 +43,7 @@ class VulkanExample : public VulkanExampleBase
{ {
public: public:
bool useSampleShading = false; bool useSampleShading = false;
VkSampleCountFlagBits sampleCount = VK_SAMPLE_COUNT_1_BIT; VkSampleCountFlagBits sampleCount = VK_SAMPLE_COUNT_1_BIT;
struct { struct {
vks::Texture2D colorMap; vks::Texture2D colorMap;
@ -83,6 +83,7 @@ public:
VkPipelineLayout pipelineLayout; VkPipelineLayout pipelineLayout;
VkDescriptorSet descriptorSet; VkDescriptorSet descriptorSet;
VkDescriptorSetLayout descriptorSetLayout; VkDescriptorSetLayout descriptorSetLayout;
VkRenderPass uiRenderPass;
VulkanExample() : VulkanExampleBase(ENABLE_VALIDATION) VulkanExample() : VulkanExampleBase(ENABLE_VALIDATION)
{ {
@ -90,7 +91,8 @@ public:
zoomSpeed = 2.5f; zoomSpeed = 2.5f;
rotation = { 0.0f, -90.0f, 0.0f }; rotation = { 0.0f, -90.0f, 0.0f };
cameraPos = glm::vec3(2.5f, 2.5f, 0.0f); cameraPos = glm::vec3(2.5f, 2.5f, 0.0f);
title = "Vulkan Example - Multisampling"; title = "Multisampling";
settings.overlay = true;
} }
~VulkanExample() ~VulkanExample()
@ -99,6 +101,7 @@ public:
// Note : Inherited destructor cleans up resources stored in base class // Note : Inherited destructor cleans up resources stored in base class
vkDestroyPipeline(device, pipelines.MSAA, nullptr); vkDestroyPipeline(device, pipelines.MSAA, nullptr);
vkDestroyPipeline(device, pipelines.MSAASampleShading, nullptr); vkDestroyPipeline(device, pipelines.MSAASampleShading, nullptr);
vkDestroyRenderPass(device, uiRenderPass, nullptr);
vkDestroyPipelineLayout(device, pipelineLayout, nullptr); vkDestroyPipelineLayout(device, pipelineLayout, nullptr);
vkDestroyDescriptorSetLayout(device, descriptorSetLayout, nullptr); vkDestroyDescriptorSetLayout(device, descriptorSetLayout, nullptr);
@ -232,8 +235,7 @@ public:
attachments[0].format = swapChain.colorFormat; attachments[0].format = swapChain.colorFormat;
attachments[0].samples = sampleCount; attachments[0].samples = sampleCount;
attachments[0].loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR; attachments[0].loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
// No longer required after resolve, this may save some bandwidth on certain GPUs attachments[0].storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachments[0].storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachments[0].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE; attachments[0].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachments[0].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE; attachments[0].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachments[0].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED; attachments[0].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
@ -318,6 +320,11 @@ public:
renderPassInfo.pDependencies = dependencies.data(); renderPassInfo.pDependencies = dependencies.data();
VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &renderPass)); VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &renderPass));
// Create custom overlay render pass
attachments[0].loadOp = VK_ATTACHMENT_LOAD_OP_LOAD;
attachments[1].loadOp = VK_ATTACHMENT_LOAD_OP_LOAD;
VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &uiRenderPass));
} }
// Frame buffer attachments must match with render pass setup, // Frame buffer attachments must match with render pass setup,
@ -355,16 +362,6 @@ public:
} }
} }
void reBuildCommandBuffers()
{
if (!checkCommandBuffers())
{
destroyCommandBuffers();
createCommandBuffers();
}
buildCommandBuffers();
}
void buildCommandBuffers() void buildCommandBuffers()
{ {
VkCommandBufferBeginInfo cmdBufInfo = vks::initializers::commandBufferBeginInfo(); VkCommandBufferBeginInfo cmdBufInfo = vks::initializers::commandBufferBeginInfo();
@ -693,7 +690,7 @@ public:
void prepare() void prepare()
{ {
sampleCount = getMaxUsableSampleCount(); sampleCount = getMaxUsableSampleCount();
VulkanExampleBase::prepare(); VulkanExampleBase::prepare();
loadAssets(); loadAssets();
setupVertexDescriptions(); setupVertexDescriptions();
@ -718,38 +715,41 @@ public:
updateUniformBuffers(); updateUniformBuffers();
} }
void toggleSampleShading() // Returns the maximum sample count usable by the platform
VkSampleCountFlagBits getMaxUsableSampleCount()
{ {
useSampleShading = !useSampleShading; VkSampleCountFlags counts = std::min(deviceProperties.limits.framebufferColorSampleCounts, deviceProperties.limits.framebufferDepthSampleCounts);
reBuildCommandBuffers(); if (counts & VK_SAMPLE_COUNT_64_BIT) { return VK_SAMPLE_COUNT_64_BIT; }
if (counts & VK_SAMPLE_COUNT_32_BIT) { return VK_SAMPLE_COUNT_32_BIT; }
if (counts & VK_SAMPLE_COUNT_16_BIT) { return VK_SAMPLE_COUNT_16_BIT; }
if (counts & VK_SAMPLE_COUNT_8_BIT) { return VK_SAMPLE_COUNT_8_BIT; }
if (counts & VK_SAMPLE_COUNT_4_BIT) { return VK_SAMPLE_COUNT_4_BIT; }
if (counts & VK_SAMPLE_COUNT_2_BIT) { return VK_SAMPLE_COUNT_2_BIT; }
return VK_SAMPLE_COUNT_1_BIT;
} }
virtual void keyPressed(uint32_t keyCode) // UI overlay configuration needs to be adjusted for this example (renderpass setup, attachment count, etc.)
virtual void OnSetupUIOverlay(vks::UIOverlayCreateInfo &createInfo)
{ {
switch (keyCode) createInfo.renderPass = uiRenderPass;
{ createInfo.framebuffers = frameBuffers;
case KEY_S: createInfo.rasterizationSamples = sampleCount;
case GAMEPAD_BUTTON_A: createInfo.attachmentCount = 1;
toggleSampleShading(); createInfo.clearValues = {
break; { { 1.0f, 1.0f, 1.0f, 1.0f } },
{ { 1.0f, 1.0f, 1.0f, 1.0f } },
{ { 1.0f, 0 } },
};
}
virtual void OnUpdateUIOverlay(vks::UIOverlay *overlay)
{
if (overlay->header("Settings")) {
if (overlay->checkBox("Sample rate shading", &useSampleShading)) {
buildCommandBuffers();
}
} }
} }
// Returns the maximum sample count usable by the platform
VkSampleCountFlagBits getMaxUsableSampleCount()
{
VkSampleCountFlags counts = std::min(deviceProperties.limits.framebufferColorSampleCounts,
deviceProperties.limits.framebufferDepthSampleCounts);
if (counts & VK_SAMPLE_COUNT_64_BIT) { return VK_SAMPLE_COUNT_64_BIT; }
if (counts & VK_SAMPLE_COUNT_32_BIT) { return VK_SAMPLE_COUNT_32_BIT; }
if (counts & VK_SAMPLE_COUNT_16_BIT) { return VK_SAMPLE_COUNT_16_BIT; }
if (counts & VK_SAMPLE_COUNT_8_BIT) { return VK_SAMPLE_COUNT_8_BIT; }
if (counts & VK_SAMPLE_COUNT_4_BIT) { return VK_SAMPLE_COUNT_4_BIT; }
if (counts & VK_SAMPLE_COUNT_2_BIT) { return VK_SAMPLE_COUNT_2_BIT; }
return VK_SAMPLE_COUNT_1_BIT;
}
}; };
VULKAN_EXAMPLE_MAIN() VULKAN_EXAMPLE_MAIN()

View file

@ -111,9 +111,11 @@ public:
FrameBufferAttachment position, normal, albedo; FrameBufferAttachment position, normal, albedo;
} attachments; } attachments;
VkRenderPass uiRenderPass;
VulkanExample() : VulkanExampleBase(ENABLE_VALIDATION) VulkanExample() : VulkanExampleBase(ENABLE_VALIDATION)
{ {
title = "Vulkan Example - Subpasses"; title = "Subpasses";
camera.type = Camera::CameraType::firstperson; camera.type = Camera::CameraType::firstperson;
camera.movementSpeed = 5.0f; camera.movementSpeed = 5.0f;
#ifndef __ANDROID__ #ifndef __ANDROID__
@ -122,7 +124,7 @@ public:
camera.setPosition(glm::vec3(-3.2f, 1.0f, 5.9f)); camera.setPosition(glm::vec3(-3.2f, 1.0f, 5.9f));
camera.setRotation(glm::vec3(0.5f, 210.05f, 0.0f)); camera.setRotation(glm::vec3(0.5f, 210.05f, 0.0f));
camera.setPerspective(60.0f, (float)width / (float)height, 0.1f, 256.0f); camera.setPerspective(60.0f, (float)width / (float)height, 0.1f, 256.0f);
settings.overlay = false; settings.overlay = true;
} }
~VulkanExample() ~VulkanExample()
@ -154,6 +156,8 @@ public:
vkDestroyDescriptorSetLayout(device, descriptorSetLayouts.composition, nullptr); vkDestroyDescriptorSetLayout(device, descriptorSetLayouts.composition, nullptr);
vkDestroyDescriptorSetLayout(device, descriptorSetLayouts.transparent, nullptr); vkDestroyDescriptorSetLayout(device, descriptorSetLayouts.transparent, nullptr);
vkDestroyRenderPass(device, uiRenderPass, nullptr);
textures.glass.destroy(); textures.glass.destroy();
models.scene.destroy(); models.scene.destroy();
models.transparent.destroy(); models.transparent.destroy();
@ -426,6 +430,10 @@ public:
renderPassInfo.pDependencies = dependencies.data(); renderPassInfo.pDependencies = dependencies.data();
VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &renderPass)); VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &renderPass));
// Create custom overlay render pass
attachments[0].loadOp = VK_ATTACHMENT_LOAD_OP_LOAD;
VK_CHECK_RESULT(vkCreateRenderPass(device, &renderPassInfo, nullptr, &uiRenderPass));
} }
void buildCommandBuffers() void buildCommandBuffers()
@ -1042,15 +1050,34 @@ public:
updateUniformBufferDeferredLights(); updateUniformBufferDeferredLights();
} }
virtual void keyPressed(uint32_t keyCode) // UI overlay configuration needs to be adjusted for this example (renderpass setup, attachment count, etc.)
virtual void OnSetupUIOverlay(vks::UIOverlayCreateInfo &createInfo)
{ {
switch (keyCode) createInfo.renderPass = uiRenderPass;
{ createInfo.framebuffers = frameBuffers;
case KEY_F1: createInfo.subpassCount = 3;
case GAMEPAD_BUTTON_A: createInfo.attachmentCount = 4;
initLights(); createInfo.clearValues = {
updateUniformBufferDeferredLights(); { { 0.0f, 0.0f, 0.0f, 0.0f } },
break; { { 0.0f, 0.0f, 0.0f, 0.0f } },
{ { 0.0f, 0.0f, 0.0f, 0.0f } },
{ { 0.0f, 0.0f, 0.0f, 0.0f } },
{ { 1.0f, 0 } },
};
}
virtual void OnUpdateUIOverlay(vks::UIOverlay *overlay)
{
if (overlay->header("Subpasses")) {
overlay->text("0: Deferred G-Buffer creation");
overlay->text("1: Deferred composition");
overlay->text("2: Forward transparency");
}
if (overlay->header("Settings")) {
if (overlay->button("Randomize lights")) {
initLights();
updateUniformBufferDeferredLights();
}
} }
} }
}; };