Will update commit message tomorrow. Fuck Vulkan. *KW in BG: DiReCtX*

- Changed RenderGraphNodeNames to RenderGraphEntityNames
- Managed to get shadow maps into desc sets
This commit is contained in:
Brandon Mak 2023-01-07 22:40:29 +08:00
parent 77a5829fc9
commit 4928ed4bcf
14 changed files with 136 additions and 66 deletions

View File

@ -502,7 +502,7 @@ namespace SHADE
//auto const& renderers = gfxSystem->GetDefaultViewport()->GetRenderers(); //auto const& renderers = gfxSystem->GetDefaultViewport()->GetRenderers();
auto renderGraph = gfxSystem->GetRenderGraph(); auto renderGraph = gfxSystem->GetRenderGraph();
auto renderPass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::IMGUI_PASS.data())->GetRenderpass(); auto renderPass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::IMGUI_PASS.data())->GetRenderpass();
if(ImGui_ImplVulkan_Init(&initInfo, renderPass->GetVkRenderpass()) == false) if(ImGui_ImplVulkan_Init(&initInfo, renderPass->GetVkRenderpass()) == false)
{ {
@ -521,7 +521,7 @@ namespace SHADE
ImGui_ImplVulkan_DestroyFontUploadObjects(); ImGui_ImplVulkan_DestroyFontUploadObjects();
renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::IMGUI_PASS.data())->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer> cmd, Handle<SHRenderer> renderer, uint32_t frameIndex) renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::IMGUI_PASS.data())->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer> cmd, Handle<SHRenderer> renderer, uint32_t frameIndex)
{ {
cmd->BeginLabeledSegment("ImGui Draw"); cmd->BeginLabeledSegment("ImGui Draw");
ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), cmd->GetVkCommandBuffer()); ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), cmd->GetVkCommandBuffer());

View File

@ -215,6 +215,28 @@ namespace SHADE
} }
void SHVkDescriptorSetGroup::UpdateDescriptorSetImage(uint32_t set, uint32_t binding, uint32_t descArrayIndex) noexcept
{
vk::WriteDescriptorSet writeDescSet{};
// Get binding + set hash
BindingAndSetHash bsHash = SHVkUtil::GenBindingSetHash(set, binding);
// to index a write for a binding
uint32_t writeInfoIndex = updater.writeHashMap[bsHash];
// Initialize info for write
writeDescSet.descriptorType = layoutsUsed[set]->GetBindings()[binding].Type;
writeDescSet.dstArrayElement = descArrayIndex;
writeDescSet.dstSet = descSets[set];
writeDescSet.dstBinding = binding;
writeDescSet.pImageInfo = updater.writeInfos[writeInfoIndex].descImageInfos.data() + descArrayIndex;
writeDescSet.descriptorCount = 1u;
device->UpdateDescriptorSet(writeDescSet);
}
void SHVkDescriptorSetGroup::UpdateDescriptorSetImages(uint32_t set, uint32_t binding) noexcept void SHVkDescriptorSetGroup::UpdateDescriptorSetImages(uint32_t set, uint32_t binding) noexcept
{ {
vk::WriteDescriptorSet writeDescSet{}; vk::WriteDescriptorSet writeDescSet{};

View File

@ -63,6 +63,7 @@ namespace SHADE
/*-----------------------------------------------------------------------------*/ /*-----------------------------------------------------------------------------*/
/* Public member functions */ /* Public member functions */
/*-----------------------------------------------------------------------------*/ /*-----------------------------------------------------------------------------*/
void UpdateDescriptorSetImage (uint32_t set, uint32_t binding, uint32_t descArrayIndex) noexcept;
void UpdateDescriptorSetImages(uint32_t set, uint32_t binding) noexcept; void UpdateDescriptorSetImages(uint32_t set, uint32_t binding) noexcept;
void UpdateDescriptorSetBuffer(uint32_t set, uint32_t binding) noexcept; void UpdateDescriptorSetBuffer(uint32_t set, uint32_t binding) noexcept;

View File

@ -191,6 +191,7 @@ namespace SHADE
features.multiDrawIndirect = VK_TRUE; features.multiDrawIndirect = VK_TRUE;
features.independentBlend = VK_TRUE; features.independentBlend = VK_TRUE;
// for wide lines // for wide lines
features.wideLines = true; features.wideLines = true;

View File

@ -101,7 +101,7 @@ namespace SHADE
// Register function for subpass // Register function for subpass
//auto const& RENDERERS = gfxSystem->GetDefaultViewport()->GetRenderers(); //auto const& RENDERERS = gfxSystem->GetDefaultViewport()->GetRenderers();
auto renderGraph = gfxSystem->GetRenderGraph(); auto renderGraph = gfxSystem->GetRenderGraph();
auto subPass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW.data())->GetSubpass("Debug Draw"); auto subPass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW.data())->GetSubpass("Debug Draw");
subPass->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex) subPass->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex)
{ {
const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex(); const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex();
@ -125,7 +125,7 @@ namespace SHADE
} }
cmdBuffer->EndLabeledSegment(); cmdBuffer->EndLabeledSegment();
}); });
auto subPassWithDepth = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW_DEPTH_PASS.data())->GetSubpass("Debug Draw with Depth"); auto subPassWithDepth = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW_DEPTH_PASS.data())->GetSubpass("Debug Draw with Depth");
subPassWithDepth->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex) subPassWithDepth->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex)
{ {
const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex(); const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex();

View File

@ -31,7 +31,7 @@ namespace SHADE
static constexpr uint32_t EDITOR = 0; static constexpr uint32_t EDITOR = 0;
}; };
struct RenderGraphNodeNames struct RenderGraphEntityNames
{ {
/***************************************************************************/ /***************************************************************************/
/*! /*!
@ -103,6 +103,18 @@ namespace SHADE
/***************************************************************************/ /***************************************************************************/
static constexpr std::string_view IMGUI_PASS = "ImGui Pass"; static constexpr std::string_view IMGUI_PASS = "ImGui Pass";
/***************************************************************************/
/*!
\brief
Name of deferred composite compute.
*/
/***************************************************************************/
static constexpr std::string_view DEFERRED_COMPOSITE_COMPUTE = "Deferred Composite";
}; };
struct DescriptorSetBindings struct DescriptorSetBindings
@ -178,6 +190,7 @@ namespace SHADE
/***************************************************************************/ /***************************************************************************/
static constexpr uint32_t SHADOW_MAP_IMAGE_SAMPLER_DATA = 0; static constexpr uint32_t SHADOW_MAP_IMAGE_SAMPLER_DATA = 0;
}; };
struct VertexBufferBindings struct VertexBufferBindings

View File

@ -208,7 +208,7 @@ namespace SHADE
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
/* MAIN NODE */ /* MAIN NODE */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
auto gBufferNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data(), auto gBufferNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data(),
//auto gBufferNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data() //auto gBufferNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data()
{ {
"Position", "Position",
@ -276,7 +276,7 @@ namespace SHADE
/* DEFERRED COMPOSITE NODE */ /* DEFERRED COMPOSITE NODE */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
// This pass will facilitate both lighting and shadows in 1 single pass. // This pass will facilitate both lighting and shadows in 1 single pass.
auto deferredCompositeNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::DEFERRED_COMPOSITE_PASS.data(), auto deferredCompositeNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_PASS.data(),
{ {
"Position", "Position",
"Light Layer Indices", "Light Layer Indices",
@ -285,13 +285,13 @@ namespace SHADE
"Scene", "Scene",
"SSAO Blur" "SSAO Blur"
}, },
{ SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS .data()}); { SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS .data()});
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
/* DEFERRED COMPOSITE SUBPASS INIT */ /* DEFERRED COMPOSITE SUBPASS INIT */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
auto deferredCompositeCompute = deferredCompositeNode->AddNodeCompute("Deferred Composite", deferredCompositeShader, { "Position", "Normals", "Albedo", "Light Layer Indices", "SSAO Blur", "Scene" }, {}/*SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::SHADOW)[0]*/); auto deferredCompositeCompute = deferredCompositeNode->AddNodeCompute(SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_COMPUTE.data(), deferredCompositeShader, {"Position", "Normals", "Albedo", "Light Layer Indices", "SSAO Blur", "Scene"}, {}, SHLightingSubSystem::MAX_SHADOWS);
deferredCompositeCompute->AddPreComputeFunction([=](Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) deferredCompositeCompute->AddPreComputeFunction([=](Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex)
{ {
lightingSubSystem->PrepareShadowMapsForRead(cmdBuffer); lightingSubSystem->PrepareShadowMapsForRead(cmdBuffer);
@ -303,19 +303,19 @@ namespace SHADE
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
// Set up Debug Draw Passes // Set up Debug Draw Passes
// - Depth Tested // - Depth Tested
auto debugDrawNodeDepth = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW_DEPTH_PASS.data(), {"Scene", "Depth Buffer"}, {SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data(), SHGraphicsConstants::RenderGraphNodeNames::DEFERRED_COMPOSITE_PASS.data()}); auto debugDrawNodeDepth = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW_DEPTH_PASS.data(), {"Scene", "Depth Buffer"}, {SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data(), SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_PASS.data()});
auto debugDrawDepthSubpass = debugDrawNodeDepth->AddSubpass("Debug Draw with Depth", worldViewport, worldRenderer); auto debugDrawDepthSubpass = debugDrawNodeDepth->AddSubpass("Debug Draw with Depth", worldViewport, worldRenderer);
debugDrawDepthSubpass->AddColorOutput("Scene"); debugDrawDepthSubpass->AddColorOutput("Scene");
debugDrawDepthSubpass->AddDepthOutput("Depth Buffer"); debugDrawDepthSubpass->AddDepthOutput("Depth Buffer");
// - No Depth Test // - No Depth Test
auto debugDrawNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW.data(), {"Scene"}, {SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW_DEPTH_PASS.data()}); auto debugDrawNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW.data(), {"Scene"}, {SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW_DEPTH_PASS.data()});
auto debugDrawSubpass = debugDrawNode->AddSubpass("Debug Draw", worldViewport, worldRenderer); auto debugDrawSubpass = debugDrawNode->AddSubpass("Debug Draw", worldViewport, worldRenderer);
debugDrawSubpass->AddColorOutput("Scene"); debugDrawSubpass->AddColorOutput("Scene");
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
/* SCREEN SPACE PASS */ /* SCREEN SPACE PASS */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
auto screenSpaceNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::SCREEN_SPACE_PASS.data(), {"Scene", "Entity ID"}, {SHGraphicsConstants::RenderGraphNodeNames::DEFERRED_COMPOSITE_PASS.data(), SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data(), SHGraphicsConstants::RenderGraphNodeNames::DEBUG_DRAW.data()}); auto screenSpaceNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::SCREEN_SPACE_PASS.data(), {"Scene", "Entity ID"}, {SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_PASS.data(), SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data(), SHGraphicsConstants::RenderGraphEntityNames::DEBUG_DRAW.data()});
auto uiSubpass = screenSpaceNode->AddSubpass("UI", worldViewport, screenRenderer); auto uiSubpass = screenSpaceNode->AddSubpass("UI", worldViewport, screenRenderer);
uiSubpass->AddColorOutput("Scene"); uiSubpass->AddColorOutput("Scene");
uiSubpass->AddColorOutput("Entity ID"); uiSubpass->AddColorOutput("Entity ID");
@ -330,16 +330,16 @@ namespace SHADE
#ifdef SHEDITOR #ifdef SHEDITOR
{ {
// Dummy Node to transition scene render graph resource // Dummy Node to transition scene render graph resource
auto dummyNode = renderGraph->AddNode("Dummy Pass", { "Scene" }, { SHGraphicsConstants::RenderGraphNodeNames::SCREEN_SPACE_PASS .data()}); auto dummyNode = renderGraph->AddNode("Dummy Pass", { "Scene" }, { SHGraphicsConstants::RenderGraphEntityNames::SCREEN_SPACE_PASS .data()});
auto dummySubpass = dummyNode->AddSubpass("Dummy Subpass", {}, {}); auto dummySubpass = dummyNode->AddSubpass("Dummy Subpass", {}, {});
dummySubpass->AddInput("Scene"); dummySubpass->AddInput("Scene");
auto imGuiNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphNodeNames::IMGUI_PASS.data(), {"Present"}, {}); auto imGuiNode = renderGraph->AddNode(SHGraphicsConstants::RenderGraphEntityNames::IMGUI_PASS.data(), {"Present"}, {});
auto imGuiSubpass = imGuiNode->AddSubpass("ImGui Draw", {}, {}); auto imGuiSubpass = imGuiNode->AddSubpass("ImGui Draw", {}, {});
imGuiSubpass->AddColorOutput("Present"); imGuiSubpass->AddColorOutput("Present");
} }
#else #else
renderGraph->AddRenderToSwapchainNode("Scene", "Present", { SHGraphicsConstants::RenderGraphNodeNames::SCREEN_SPACE_PASS .data()}, {renderToSwapchainVS, renderToSwapchainFS}); renderGraph->AddRenderToSwapchainNode("Scene", "Present", { SHGraphicsConstants::RenderGraphEntityNames::SCREEN_SPACE_PASS .data()}, {renderToSwapchainVS, renderToSwapchainFS});
#endif #endif
@ -417,7 +417,7 @@ namespace SHADE
textRenderingSubSystem = resourceManager.Create<SHTextRenderingSubSystem>(); textRenderingSubSystem = resourceManager.Create<SHTextRenderingSubSystem>();
// initialize the text renderer // initialize the text renderer
auto uiNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::SCREEN_SPACE_PASS.data()); auto uiNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::SCREEN_SPACE_PASS.data());
textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS); textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS);
SHGlobalDescriptorSets::SetLightingSubSystem(lightingSubSystem); SHGlobalDescriptorSets::SetLightingSubSystem(lightingSubSystem);
@ -444,7 +444,7 @@ namespace SHADE
defaultMaterial = AddMaterial defaultMaterial = AddMaterial
( (
defaultVertShader, defaultFragShader, defaultVertShader, defaultFragShader,
renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data())->GetSubpass("G-Buffer Write") renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data())->GetSubpass("G-Buffer Write")
); );
defaultMaterial->SetProperty("data.textureIndex", defaultTexture->TextureArrayIndex); defaultMaterial->SetProperty("data.textureIndex", defaultTexture->TextureArrayIndex);
} }
@ -762,7 +762,7 @@ namespace SHADE
auto const& EVENT_DATA = reinterpret_cast<const SHEventSpec<SHLightEnableShadowEvent>*>(eventPtr.get())->data; auto const& EVENT_DATA = reinterpret_cast<const SHEventSpec<SHLightEnableShadowEvent>*>(eventPtr.get())->data;
auto* lightComp = SHComponentManager::GetComponent<SHLightComponent>(EVENT_DATA->lightEntity); auto* lightComp = SHComponentManager::GetComponent<SHLightComponent>(EVENT_DATA->lightEntity);
std::string resourceName = "ShadowMap " + std::to_string(EVENT_DATA->lightEntity); std::string resourceName = "ShadowMap " + std::to_string(EVENT_DATA->lightEntity);
Handle<SHSubpass> companionSubpass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data())->GetSubpass("G-Buffer Write"); Handle<SHSubpass> companionSubpass = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data())->GetSubpass("G-Buffer Write");
if (EVENT_DATA->generateRenderer) if (EVENT_DATA->generateRenderer)
{ {
@ -772,16 +772,16 @@ namespace SHADE
} }
// Add the shadow map resource to the graph // Add the shadow map resource to the graph
renderGraph->AddResource(resourceName, {SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH_STENCIL, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT}, resizeWidth, resizeHeight, vk::Format::eD24UnormS8Uint); renderGraph->AddResource(resourceName, {SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT}, resizeWidth, resizeHeight, vk::Format::eD32Sfloat);
// link resource to node. This means linking the resource and regenerating the node's renderpass and framebuffer. // link resource to node. This means linking the resource and regenerating the node's renderpass and framebuffer.
//auto shadowMapNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::SHADOW_MAP_PASS.data()); //auto shadowMapNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::SHADOW_MAP_PASS.data());
auto shadowMapNode = renderGraph->AddNodeAfter(SHGraphicsConstants::RenderGraphNodeNames::SHADOW_MAP_PASS.data() + resourceName, {resourceName.c_str()}, SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data()); auto shadowMapNode = renderGraph->AddNodeAfter(SHGraphicsConstants::RenderGraphEntityNames::SHADOW_MAP_PASS.data() + resourceName, {resourceName.c_str()}, SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data());
// Add a subpass to render to that shadow map // Add a subpass to render to that shadow map
auto newSubpass = shadowMapNode->RuntimeAddSubpass(resourceName + " Subpass", worldViewport, lightComp->GetRenderer()); auto newSubpass = shadowMapNode->RuntimeAddSubpass(resourceName + " Subpass", worldViewport, lightComp->GetRenderer());
//auto newSubpass = shadowMapNode->RuntimeAddSubpass(resourceName + " Subpass", worldViewport, lightComp->GetRenderer()); //auto newSubpass = shadowMapNode->RuntimeAddSubpass(resourceName + " Subpass", worldViewport, lightComp->GetRenderer());
newSubpass->AddDepthOutput(resourceName, SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH_STENCIL); newSubpass->AddDepthOutput(resourceName, SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH);
// regenerate the node // regenerate the node
shadowMapNode->RuntimeStandaloneRegenerate(); shadowMapNode->RuntimeStandaloneRegenerate();
@ -791,7 +791,7 @@ namespace SHADE
if (!shadowMapPipeline) if (!shadowMapPipeline)
{ {
SHPipelineLibrary tempLibrary{}; SHPipelineLibrary tempLibrary{};
Handle<SHRenderGraphNode> rgNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::SHADOW_MAP_PASS.data()); Handle<SHRenderGraphNode> rgNode = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::SHADOW_MAP_PASS.data());
tempLibrary.Init(device); tempLibrary.Init(device);
tempLibrary.CreateGraphicsPipelines({ shadowMapVS, {} }, shadowMapNode->GetRenderpass(), newSubpass, SHGraphicsPredefinedData::GetShadowMapViState()); tempLibrary.CreateGraphicsPipelines({ shadowMapVS, {} }, shadowMapNode->GetRenderpass(), newSubpass, SHGraphicsPredefinedData::GetShadowMapViState());
@ -799,6 +799,12 @@ namespace SHADE
} }
newSubpass->SetCompanionSubpass(companionSubpass, shadowMapPipeline); // set companion subpass and pipeline newSubpass->SetCompanionSubpass(companionSubpass, shadowMapPipeline); // set companion subpass and pipeline
// add the shadow map to the lighting system
uint32_t const NEW_SHADOW_MAP_INDEX = lightingSubSystem->AddShadowMap(renderGraph->GetRenderGraphResource(resourceName), EVENT_DATA->lightEntity);
auto nodeCompute = renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_PASS.data())->GetNodeCompute(SHGraphicsConstants::RenderGraphEntityNames::DEFERRED_COMPOSITE_COMPUTE.data());
nodeCompute->ModifyWriteDescImageComputeResource(SHGraphicsConstants::DescriptorSetBindings::SHADOW_MAP_IMAGE_SAMPLER_DATA, lightingSubSystem->GetViewSamplerLayout(NEW_SHADOW_MAP_INDEX), NEW_SHADOW_MAP_INDEX);
return eventPtr->handle; return eventPtr->handle;
} }
@ -1142,7 +1148,7 @@ namespace SHADE
Handle<SHRenderGraphNode> SHGraphicsSystem::GetPrimaryRenderpass() const noexcept Handle<SHRenderGraphNode> SHGraphicsSystem::GetPrimaryRenderpass() const noexcept
{ {
return renderGraph->GetNode(SHGraphicsConstants::RenderGraphNodeNames::GBUFFER_PASS.data()); return renderGraph->GetNode(SHGraphicsConstants::RenderGraphEntityNames::GBUFFER_PASS.data());
} }
Handle<SHVkPipeline> SHGraphicsSystem::GetDebugDrawPipeline(DebugDrawPipelineType type) const noexcept Handle<SHVkPipeline> SHGraphicsSystem::GetDebugDrawPipeline(DebugDrawPipelineType type) const noexcept

View File

@ -459,14 +459,14 @@ namespace SHADE
#pragma endregion #pragma endregion
#pragma region SHADOWS #pragma region SHADOWS
std::vector<uint32_t> shadowDescVariableSizes{ MAX_SHADOWS }; //std::vector<uint32_t> shadowDescVariableSizes{ MAX_SHADOWS };
shadowMapDescriptorSet = descPool->Allocate({SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::SHADOW)}, shadowDescVariableSizes); //shadowMapDescriptorSet = descPool->Allocate({SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::SHADOW)}, shadowDescVariableSizes);
#ifdef _DEBUG //#ifdef _DEBUG
const auto& SHADOW_MAP_DESC_SETS = shadowMapDescriptorSet->GetVkHandle(); // const auto& SHADOW_MAP_DESC_SETS = shadowMapDescriptorSet->GetVkHandle();
for (int i = 0; i < static_cast<int>(SHADOW_MAP_DESC_SETS.size()); ++i) // for (int i = 0; i < static_cast<int>(SHADOW_MAP_DESC_SETS.size()); ++i)
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSet, SHADOW_MAP_DESC_SETS[i], "[Descriptor Set] Shadow Map Data Frame #" + std::to_string(i)); // SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSet, SHADOW_MAP_DESC_SETS[i], "[Descriptor Set] Shadow Map Data Frame #" + std::to_string(i));
#endif //#endif
shadowMapSampler = inShadowMapSampler; shadowMapSampler = inShadowMapSampler;
//numLightComponents = 0; //numLightComponents = 0;
@ -583,7 +583,7 @@ namespace SHADE
} }
void SHLightingSubSystem::AddShadowMap(Handle<SHRenderGraphResource> newShadowMap, EntityID lightEntity) noexcept uint32_t SHLightingSubSystem::AddShadowMap(Handle<SHRenderGraphResource> newShadowMap, EntityID lightEntity) noexcept
{ {
// Add to container of shadow maps // Add to container of shadow maps
shadowMaps.emplace(lightEntity, newShadowMap); shadowMaps.emplace(lightEntity, newShadowMap);
@ -595,26 +595,28 @@ namespace SHADE
shadowMapImageSamplers.emplace_back(NEW_IMAGE_VIEW, shadowMapSampler, vk::ImageLayout::eShaderReadOnlyOptimal); shadowMapImageSamplers.emplace_back(NEW_IMAGE_VIEW, shadowMapSampler, vk::ImageLayout::eShaderReadOnlyOptimal);
// Update descriptor set // Update descriptor set
static constexpr uint32_t SHADOW_MAP_DESC_SET_INDEX = 0; //static constexpr uint32_t SHADOW_MAP_DESC_SET_INDEX = 0;
uint32_t const SHADOW_MAP_DESC_ARRAY_INDEX = static_cast<uint32_t>(shadowMapImageSamplers.size()) - 1u; //uint32_t const SHADOW_MAP_DESC_ARRAY_INDEX = static_cast<uint32_t>(shadowMapImageSamplers.size()) - 1u;
shadowMapDescriptorSet->ModifyWriteDescImage //shadowMapDescriptorSet->ModifyWriteDescImage
( //(
SHADOW_MAP_DESC_SET_INDEX, // SHADOW_MAP_DESC_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::SHADOW_MAP_IMAGE_SAMPLER_DATA, // SHGraphicsConstants::DescriptorSetBindings::SHADOW_MAP_IMAGE_SAMPLER_DATA,
shadowMapImageSamplers[SHADOW_MAP_DESC_ARRAY_INDEX], // shadowMapImageSamplers[SHADOW_MAP_DESC_ARRAY_INDEX],
SHADOW_MAP_DESC_ARRAY_INDEX // SHADOW_MAP_DESC_ARRAY_INDEX
); //);
// TODO: Definitely can be optimized by writing a function that modifies a specific descriptor in the array //// TODO: Definitely can be optimized by writing a function that modifies a specific descriptor in the array
shadowMapDescriptorSet->UpdateDescriptorSetImages //shadowMapDescriptorSet->UpdateDescriptorSetImages
( //(
SHADOW_MAP_DESC_SET_INDEX, // SHADOW_MAP_DESC_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::SHADOW_MAP_IMAGE_SAMPLER_DATA // SHGraphicsConstants::DescriptorSetBindings::SHADOW_MAP_IMAGE_SAMPLER_DATA
); //);
// add to barriers // add to barriers
shadowMapMemoryBarriers.push_back (vk::ImageMemoryBarrier shadowMapMemoryBarriers.push_back (vk::ImageMemoryBarrier
{ {
.srcAccessMask = vk::AccessFlagBits::eDepthStencilAttachmentWrite,
.dstAccessMask = vk::AccessFlagBits::eShaderRead,
.oldLayout = vk::ImageLayout::eDepthAttachmentOptimal, .oldLayout = vk::ImageLayout::eDepthAttachmentOptimal,
.newLayout = vk::ImageLayout::eShaderReadOnlyOptimal, .newLayout = vk::ImageLayout::eShaderReadOnlyOptimal,
.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED, .srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED,
@ -629,6 +631,9 @@ namespace SHADE
.layerCount = 1, .layerCount = 1,
} }
}); });
// return new index of shadow map
return static_cast<uint32_t>(shadowMapImageSamplers.size()) - 1u;
} }
void SHLightingSubSystem::PrepareShadowMapsForRead(Handle<SHVkCommandBuffer> cmdBuffer) noexcept void SHLightingSubSystem::PrepareShadowMapsForRead(Handle<SHVkCommandBuffer> cmdBuffer) noexcept
@ -642,4 +647,9 @@ namespace SHADE
return lightingDataDescSet; return lightingDataDescSet;
} }
std::tuple<Handle<SHVkImageView>, Handle<SHVkSampler>, vk::ImageLayout> const& SHLightingSubSystem::GetViewSamplerLayout(uint32_t index) const noexcept
{
return shadowMapImageSamplers[index];
}
} }

View File

@ -70,11 +70,15 @@ namespace SHADE
{ {
public: public:
using DynamicOffsetArray = std::array<std::vector<uint32_t>, static_cast<uint32_t>(SHGraphicsConstants::NUM_FRAME_BUFFERS)>; using DynamicOffsetArray = std::array<std::vector<uint32_t>, static_cast<uint32_t>(SHGraphicsConstants::NUM_FRAME_BUFFERS)>;
static constexpr uint32_t MAX_SHADOWS = 200;
private: private:
class PerTypeData class PerTypeData
{ {
public:
private: private:
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
/* STATIC MEMBER VARIABLES */ /* STATIC MEMBER VARIABLES */
@ -137,7 +141,6 @@ namespace SHADE
/* STATIC MEMBER VARIABLES */ /* STATIC MEMBER VARIABLES */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
static constexpr uint32_t MAX_SHADOWS = 200;
//! logical device used for creation //! logical device used for creation
Handle<SHVkLogicalDevice> logicalDevice; Handle<SHVkLogicalDevice> logicalDevice;
@ -174,7 +177,7 @@ namespace SHADE
//! Descriptor sets required to be given to the compute shader for shadow calculation. This will be a descriptor array. //! Descriptor sets required to be given to the compute shader for shadow calculation. This will be a descriptor array.
//! It will also be preallocated. //! It will also be preallocated.
Handle<SHVkDescriptorSetGroup> shadowMapDescriptorSet; //Handle<SHVkDescriptorSetGroup> shadowMapDescriptorSet;
//! Combined image samplers for the texture descriptors //! Combined image samplers for the texture descriptors
std::vector<std::tuple<Handle<SHVkImageView>, Handle<SHVkSampler>, vk::ImageLayout>> shadowMapImageSamplers; std::vector<std::tuple<Handle<SHVkImageView>, Handle<SHVkSampler>, vk::ImageLayout>> shadowMapImageSamplers;
@ -205,7 +208,7 @@ namespace SHADE
void Run (SHMatrix const& viewMat, uint32_t frameIndex) noexcept; void Run (SHMatrix const& viewMat, uint32_t frameIndex) noexcept;
void Exit (void) noexcept; void Exit (void) noexcept;
void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t setIndex, uint32_t frameIndex) noexcept; void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t setIndex, uint32_t frameIndex) noexcept;
void AddShadowMap (Handle<SHRenderGraphResource> newShadowMap, EntityID lightEntity) noexcept; uint32_t AddShadowMap (Handle<SHRenderGraphResource> newShadowMap, EntityID lightEntity) noexcept;
void PrepareShadowMapsForRead (Handle<SHVkCommandBuffer> cmdBuffer) noexcept; void PrepareShadowMapsForRead (Handle<SHVkCommandBuffer> cmdBuffer) noexcept;
//void RemoveShadowMap (uint32_t index) noexcept; //void RemoveShadowMap (uint32_t index) noexcept;
@ -213,6 +216,7 @@ namespace SHADE
/* SETTERS AND GETTERS */ /* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
Handle<SHVkDescriptorSetGroup> GetLightDataDescriptorSet (void) const noexcept; Handle<SHVkDescriptorSetGroup> GetLightDataDescriptorSet (void) const noexcept;
std::tuple<Handle<SHVkImageView>, Handle<SHVkSampler>, vk::ImageLayout> const& GetViewSamplerLayout (uint32_t index) const noexcept;
}; };
} }

View File

@ -442,7 +442,7 @@ namespace SHADE
return subpass; return subpass;
} }
Handle<SHRenderGraphNodeCompute> SHRenderGraphNode::AddNodeCompute(std::string nodeName, Handle<SHVkShaderModule> computeShaderModule, std::initializer_list<std::string> resources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, Handle<SHVkDescriptorSetLayout> customComputeLayout/* = {}*/, float numWorkGroupScale/* = 1.0f*/) noexcept Handle<SHRenderGraphNodeCompute> SHRenderGraphNode::AddNodeCompute(std::string nodeName, Handle<SHVkShaderModule> computeShaderModule, std::initializer_list<std::string> resources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, uint32_t variableDescCount/* = 0*/, float numWorkGroupScale/* = 1.0f*/) noexcept
{ {
// Look for the required resources in the graph // Look for the required resources in the graph
std::vector<Handle<SHRenderGraphResource>> nodeComputeResources{}; std::vector<Handle<SHRenderGraphResource>> nodeComputeResources{};
@ -458,7 +458,7 @@ namespace SHADE
std::vector<Handle<SHRenderGraphResource>> temp (nodeComputeResources); std::vector<Handle<SHRenderGraphResource>> temp (nodeComputeResources);
// Create the subpass compute with the resources // Create the subpass compute with the resources
auto nodeCompute = graphStorage->resourceHub->Create<SHRenderGraphNodeCompute>(std::move(nodeName), graphStorage, computeShaderModule, std::move(nodeComputeResources), std::move (dynamicBufferBindings), nodeComputes.empty(), customComputeLayout); auto nodeCompute = graphStorage->resourceHub->Create<SHRenderGraphNodeCompute>(std::move(nodeName), graphStorage, computeShaderModule, std::move(nodeComputeResources), std::move (dynamicBufferBindings), nodeComputes.empty(), variableDescCount);
nodeComputes.push_back(nodeCompute); nodeComputes.push_back(nodeCompute);
for (auto& resource : temp) for (auto& resource : temp)
@ -810,4 +810,15 @@ namespace SHADE
return attResources; return attResources;
} }
Handle<SHRenderGraphNodeCompute> SHRenderGraphNode::GetNodeCompute(std::string nodeComputeName) const noexcept
{
for (auto nc : nodeComputes)
{
if (nc->name == nodeComputeName)
return nc;
}
return {};
}
} }

View File

@ -109,7 +109,7 @@ namespace SHADE
/* PUBLIC MEMBER FUNCTIONS */ /* PUBLIC MEMBER FUNCTIONS */
/*-----------------------------------------------------------------------*/ /*-----------------------------------------------------------------------*/
Handle<SHSubpass> AddSubpass(std::string subpassName, Handle<SHViewport> viewport, Handle<SHRenderer> renderer) noexcept; Handle<SHSubpass> AddSubpass(std::string subpassName, Handle<SHViewport> viewport, Handle<SHRenderer> renderer) noexcept;
Handle<SHRenderGraphNodeCompute> AddNodeCompute(std::string nodeName, Handle<SHVkShaderModule> computeShaderModule, std::initializer_list<std::string> resources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings = {}, Handle<SHVkDescriptorSetLayout> customComputeLayout = {}, float numWorkGroupScale = 1.0f) noexcept; Handle<SHRenderGraphNodeCompute> AddNodeCompute(std::string nodeName, Handle<SHVkShaderModule> computeShaderModule, std::initializer_list<std::string> resources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings = {}, uint32_t variableDescCount = 0, float numWorkGroupScale = 1.0f) noexcept;
void Execute(Handle<SHVkCommandBuffer> commandBuffer, Handle<SHVkDescriptorPool> descPool, uint32_t frameIndex) noexcept; void Execute(Handle<SHVkCommandBuffer> commandBuffer, Handle<SHVkDescriptorPool> descPool, uint32_t frameIndex) noexcept;
Handle<SHVkPipeline> GetOrCreatePipeline(std::pair<Handle<SHVkShaderModule>, Handle<SHVkShaderModule>> const& vsFsPair, Handle<SHSubpass> subpass) noexcept; Handle<SHVkPipeline> GetOrCreatePipeline(std::pair<Handle<SHVkShaderModule>, Handle<SHVkShaderModule>> const& vsFsPair, Handle<SHSubpass> subpass) noexcept;
@ -127,6 +127,7 @@ namespace SHADE
Handle<SHSubpass> GetSubpass(std::string_view subpassName) const noexcept; Handle<SHSubpass> GetSubpass(std::string_view subpassName) const noexcept;
Handle<SHRenderGraphResource> GetResource (uint32_t resourceIndex) const noexcept; Handle<SHRenderGraphResource> GetResource (uint32_t resourceIndex) const noexcept;
std::vector<Handle<SHRenderGraphResource>> const& GetResources (void) const noexcept; std::vector<Handle<SHRenderGraphResource>> const& GetResources (void) const noexcept;
Handle<SHRenderGraphNodeCompute> GetNodeCompute (std::string nodeComputeName) const noexcept;
friend class SHRenderGraph; friend class SHRenderGraph;
}; };

View File

@ -63,7 +63,7 @@ namespace SHADE
} }
SHRenderGraphNodeCompute::SHRenderGraphNodeCompute(std::string nodeName, Handle<SHRenderGraphStorage> graphStorage, Handle<SHVkShaderModule> computeShaderModule, std::vector<Handle<SHRenderGraphResource>>&& subpassComputeResources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, bool followingEndRP, Handle<SHVkDescriptorSetLayout> customComputeLayout, float inNumWorkGroupScale/* = 1.0f*/) noexcept SHRenderGraphNodeCompute::SHRenderGraphNodeCompute(std::string nodeName, Handle<SHRenderGraphStorage> graphStorage, Handle<SHVkShaderModule> computeShaderModule, std::vector<Handle<SHRenderGraphResource>>&& subpassComputeResources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, bool followingEndRP, uint32_t variableDescCount, float inNumWorkGroupScale/* = 1.0f*/) noexcept
: computePipeline{} : computePipeline{}
, pipelineLayout{} , pipelineLayout{}
, resources{} , resources{}
@ -118,21 +118,11 @@ namespace SHADE
if (layouts.size() == descMappings.at(SHPredefinedDescriptorTypes::RENDER_GRAPH_NODE_COMPUTE_RESOURCE) + 1) if (layouts.size() == descMappings.at(SHPredefinedDescriptorTypes::RENDER_GRAPH_NODE_COMPUTE_RESOURCE) + 1)
{ {
Handle<SHVkDescriptorSetLayout> computeResourceLayout = {}; Handle<SHVkDescriptorSetLayout> computeResourceLayout = {};
uint32_t variableCounts = 0;
if (customComputeLayout)
{
// Just use the descriptor counts in bindings as the variable descriptor counts
auto const& bindings = customComputeLayout->GetBindings();
variableCounts = bindings.back().DescriptorCount;
computeResourceLayout = customComputeLayout;
}
else
computeResourceLayout = layouts[descMappings.at(SHPredefinedDescriptorTypes::RENDER_GRAPH_NODE_COMPUTE_RESOURCE)]; computeResourceLayout = layouts[descMappings.at(SHPredefinedDescriptorTypes::RENDER_GRAPH_NODE_COMPUTE_RESOURCE)];
// create compute resources // create compute resources
computeResource = graphStorage->resourceHub->Create<ComputeResource>(); computeResource = graphStorage->resourceHub->Create<ComputeResource>();
computeResource->descSet = graphStorage->descriptorPool->Allocate({ computeResourceLayout }, {variableCounts}); computeResource->descSet = graphStorage->descriptorPool->Allocate({ computeResourceLayout }, {variableDescCount});
#ifdef _DEBUG #ifdef _DEBUG
for (auto set : computeResource->descSet->GetVkHandle()) for (auto set : computeResource->descSet->GetVkHandle())
SET_VK_OBJ_NAME(graphStorage->logicalDevice, vk::ObjectType::eDescriptorSet, set, "[Descriptor Set] " + name + " Resources"); SET_VK_OBJ_NAME(graphStorage->logicalDevice, vk::ObjectType::eDescriptorSet, set, "[Descriptor Set] " + name + " Resources");
@ -257,6 +247,14 @@ namespace SHADE
} }
void SHRenderGraphNodeCompute::ModifyWriteDescImageComputeResource(uint32_t binding, SHVkDescriptorSetGroup::viewSamplerLayout const& viewSamplerLayout, uint32_t descArrayIndex) noexcept
{
static constexpr uint32_t COMPUTE_RESOURCE_SET_INDEX = 0;
computeResource->descSet->ModifyWriteDescImage(COMPUTE_RESOURCE_SET_INDEX, binding, viewSamplerLayout, descArrayIndex);
computeResource->descSet->UpdateDescriptorSetImage(COMPUTE_RESOURCE_SET_INDEX, binding, descArrayIndex);
}
void SHRenderGraphNodeCompute::AddPreComputeFunction(PreComputeFunction const& fn) noexcept void SHRenderGraphNodeCompute::AddPreComputeFunction(PreComputeFunction const& fn) noexcept
{ {
preComputeFunctions.push_back(fn); preComputeFunctions.push_back(fn);

View File

@ -93,7 +93,7 @@ namespace SHADE
void SetFollowingEndRenderpass (uint32_t flag) noexcept; void SetFollowingEndRenderpass (uint32_t flag) noexcept;
public: public:
SHRenderGraphNodeCompute(std::string nodeName, Handle<SHRenderGraphStorage> graphStorage, Handle<SHVkShaderModule> computeShaderModule, std::vector<Handle<SHRenderGraphResource>>&& subpassComputeResources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, bool followingEndRP, Handle<SHVkDescriptorSetLayout> customComputeLayout, float inNumWorkGroupScale = 1.0f) noexcept; SHRenderGraphNodeCompute(std::string nodeName, Handle<SHRenderGraphStorage> graphStorage, Handle<SHVkShaderModule> computeShaderModule, std::vector<Handle<SHRenderGraphResource>>&& subpassComputeResources, std::unordered_set<BindingAndSetHash>&& dynamicBufferBindings, bool followingEndRP, uint32_t variableDescCount, float inNumWorkGroupScale = 1.0f) noexcept;
void Execute (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept; void Execute (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void HandleResize (void) noexcept; void HandleResize (void) noexcept;
@ -103,6 +103,7 @@ namespace SHADE
void ModifyWriteDescBufferComputeResource (uint32_t binding, std::span<Handle<SHVkBuffer>> const& buffers, uint32_t offset, uint32_t range) noexcept; void ModifyWriteDescBufferComputeResource (uint32_t binding, std::span<Handle<SHVkBuffer>> const& buffers, uint32_t offset, uint32_t range) noexcept;
void ModifyWriteDescImageComputeResource(uint32_t binding, std::span<SHVkDescriptorSetGroup::viewSamplerLayout> const& viewSamplerLayouts) noexcept; void ModifyWriteDescImageComputeResource(uint32_t binding, std::span<SHVkDescriptorSetGroup::viewSamplerLayout> const& viewSamplerLayouts) noexcept;
void ModifyWriteDescImageComputeResource(uint32_t binding, SHVkDescriptorSetGroup::viewSamplerLayout const& viewSamplerLayout, uint32_t descArrayIndex) noexcept;
void AddPreComputeFunction (PreComputeFunction const& fn) noexcept; void AddPreComputeFunction (PreComputeFunction const& fn) noexcept;

View File

@ -164,7 +164,7 @@ namespace SHADE
switch (attachmentDescriptionType) switch (attachmentDescriptionType)
{ {
case SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH: case SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH:
imageLayout = vk::ImageLayout::eDepthAttachmentOptimal; imageLayout = vk::ImageLayout::eDepthStencilAttachmentOptimal;
break; break;
case SH_RENDER_GRAPH_RESOURCE_FLAGS::STENCIL: case SH_RENDER_GRAPH_RESOURCE_FLAGS::STENCIL:
imageLayout = vk::ImageLayout::eStencilAttachmentOptimal; imageLayout = vk::ImageLayout::eStencilAttachmentOptimal;
@ -299,6 +299,8 @@ namespace SHADE
if (inputReferences[i].attachment == attachmentIndex) if (inputReferences[i].attachment == attachmentIndex)
return true; return true;
} }
return false;
} }
bool SHSubpass::HasNoAttachments(void) const noexcept bool SHSubpass::HasNoAttachments(void) const noexcept