Merge branch 'main' into SP3-17-animation-system

# Conflicts:
#	SHADE_Engine/src/Graphics/MiddleEnd/Batching/SHBatch.cpp
#	SHADE_Engine/src/Graphics/MiddleEnd/Batching/SHBatch.h
#	SHADE_Engine/src/Graphics/MiddleEnd/Interface/SHGraphicsSystem.cpp
This commit is contained in:
Kah Wei 2023-01-04 15:52:08 +08:00
commit 3ca6859fcb
135 changed files with 4073 additions and 1869 deletions

4
.gitignore vendored
View File

@ -364,3 +364,7 @@ MigrationBackup/
*.filters
Assets/Editor/Layouts/UserLayout.ini
JSON/Schemas/Catalog/
Assets/Editor/Editor.SHConfig

File diff suppressed because it is too large Load Diff

View File

@ -11,13 +11,12 @@ layout(location = 0) out struct
vec4 Color;
} Out;
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
void main()

View File

@ -10,13 +10,12 @@ layout(location = 0) out struct
vec4 vertColor; // location 0
} Out;
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
void main()

View File

@ -17,12 +17,12 @@ struct AmbientLightStruct
};
layout(local_size_x = 16, local_size_y = 16) in;
layout(set = 4, binding = 0, rgba32f) uniform image2D positions;
layout(set = 4, binding = 1, rgba32f) uniform image2D normals;
layout(set = 4, binding = 2, rgba8) uniform image2D albedo;
layout(set = 4, binding = 3, r32ui) uniform uimage2D lightLayerData;
layout(set = 4, binding = 4, r8) uniform image2D ssaoBlurredImage;
layout(set = 4, binding = 5, rgba8) uniform image2D targetImage;
layout(set = 3, binding = 0, rgba32f) uniform image2D positions;
layout(set = 3, binding = 1, rgba32f) uniform image2D normals;
layout(set = 3, binding = 2, rgba8) uniform image2D albedo;
layout(set = 3, binding = 3, r32ui) uniform uimage2D lightLayerData;
layout(set = 3, binding = 4, r8) uniform image2D ssaoBlurredImage;
layout(set = 3, binding = 5, rgba8) uniform image2D targetImage;
layout(set = 1, binding = 0) uniform LightCounts
{

View File

@ -50,8 +50,8 @@
#define NUM_MASKS 8
layout(local_size_x = 16, local_size_y = 16) in;
layout(set = 4, binding = 0, rgba8) uniform image2D inputImage;
layout(set = 4, binding = 1, rgba8) uniform image2D resultImage;
layout(set = 3, binding = 0, rgba8) uniform image2D inputImage;
layout(set = 3, binding = 1, rgba8) uniform image2D resultImage;
const float kirsch[8][3][3] = {
{

View File

@ -28,7 +28,7 @@ layout(location = 3) flat in struct
} In2;
layout (set = 0, binding = 1) uniform sampler2D textures[]; // for textures (global)
layout (std430, set = 3, binding = 0) buffer MaterialProperties // For materials
layout (std430, set = 2, binding = 0) buffer MaterialProperties // For materials
{
MatPropData data[];
} MatProp;

Binary file not shown.

View File

@ -46,8 +46,8 @@
layout(local_size_x = 16, local_size_y = 16) in;
layout(set = 4, binding = 0, rgba8) uniform image2D inputImage;
layout(set = 4, binding = 1, rgba8) uniform image2D targetImage;
layout(set = 3, binding = 0, rgba8) uniform image2D inputImage;
layout(set = 3, binding = 1, rgba8) uniform image2D targetImage;
void main()

Binary file not shown.

View File

@ -5,8 +5,8 @@
#define SHM_WIDTH BLUR_WIDTH + 16 - 1
layout(local_size_x = 16, local_size_y = 16) in;
layout(set = 4, binding = 0, r8) uniform image2D ssaoImage;
layout(set = 4, binding = 1, r8) uniform image2D ssaoBlurImage;
layout(set = 3, binding = 0, r8) uniform image2D ssaoImage;
layout(set = 3, binding = 1, r8) uniform image2D ssaoBlurImage;
float GetSSAOValue(ivec2 uv, ivec2 imageSize)

Binary file not shown.

View File

@ -1,5 +1,7 @@
#version 450
#pragma vscode_glsllint_stage : comp
const uint NUM_SAMPLES = 64;
const uint NUM_ROTATIONS = 16;
const int ROTATION_KERNEL_W = 4;
@ -10,19 +12,19 @@ const float RADIUS = 0.2f;
const float BIAS = 0.0025f;
layout(local_size_x = 16, local_size_y = 16) in;
layout(set = 4, binding = 0, rgba32f) uniform image2D positions;
layout(set = 4, binding = 1, rgba32f) uniform image2D normals;
layout(set = 4, binding = 2, rgba32f) uniform image2D outputImage;
layout(set = 3, binding = 0, rgba32f) uniform image2D positions;
layout(set = 3, binding = 1, rgba32f) uniform image2D normals;
layout(set = 3, binding = 2, rgba32f) uniform image2D outputImage;
// SSAO data
layout(std430, set = 5, binding = 0) buffer SSAOData
layout(std430, set = 4, binding = 0) buffer SSAOData
{
vec4 samples[NUM_SAMPLES];
} ssaoData;
layout (set = 5, binding = 1) uniform sampler2D noiseTexture;
layout (set = 4, binding = 1) uniform sampler2D noiseTexture;
layout(set = 2, binding = 0) uniform CameraData
{

Binary file not shown.

View File

@ -28,7 +28,7 @@ layout(location = 3) flat in struct
} In2;
layout (set = 0, binding = 1) uniform sampler2D textures[]; // for textures (global)
layout (std430, set = 3, binding = 0) buffer MaterialProperties // For materials
layout (std430, set = 2, binding = 0) buffer MaterialProperties // For materials
{
MatPropData data[];
} MatProp;

Binary file not shown.

View File

@ -26,7 +26,7 @@ layout(location = 3) flat in struct
} In2;
layout (set = 0, binding = 1) uniform sampler2D textures[]; // for textures (global)
layout (std430, set = 3, binding = 0) buffer MaterialProperties // For materials
layout (std430, set = 2, binding = 0) buffer MaterialProperties // For materials
{
MatPropData data[];
} MatProp;

View File

@ -34,16 +34,15 @@ layout(location = 3) out struct
} Out2;
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
layout (std430, set = 3, binding = 0) buffer MaterialProperties // For materials
layout (std430, set = 2, binding = 0) buffer MaterialProperties // For materials
{
MatPropData data[];
} MatProp;

View File

@ -29,13 +29,12 @@ layout(location = 3) out struct
} Out2;
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
void main()

Binary file not shown.

View File

@ -28,7 +28,7 @@ layout(location = 3) flat in struct
layout(set = 4, binding = 0) uniform sampler2D fontBitmap;
layout(set = 2, binding = 0) uniform sampler2D fontBitmap;
layout(location = 0) out vec4 color;
layout(location = 1) out uint outEntityID;

Binary file not shown.

View File

@ -25,13 +25,12 @@ layout(location = 3) out struct
} Out2;
// Camera data
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
// push constants
@ -44,7 +43,7 @@ layout(std140, push_constant) uniform TestPushConstant
} testPushConstant;
// Descriptor sets
layout(std430, set = 4, binding = 1) buffer GlyphTransforms
layout(std430, set = 2, binding = 1) buffer GlyphTransforms
{
mat4 matrices[];
} glyphTransforms;
@ -96,6 +95,6 @@ void main()
Out2.textColor = testPushConstant.textColor;
// transform the vertex position to font space
gl_Position = cameraData.orthoMat * localModel * vec4(vertexPos, 1.0f);
gl_Position = cameraData.projMat * localModel * vec4(vertexPos, 1.0f);
// gl_Position = vec4(vertexPos, 1.0f);
}

Binary file not shown.

View File

@ -3,7 +3,7 @@
#extension GL_ARB_shading_language_420pack : enable
#extension GL_EXT_nonuniform_qualifier : require
layout (input_attachment_index = 0, set = 4, binding = 0) uniform subpassInput sceneTexture;
layout (input_attachment_index = 0, set = 0, binding = 0) uniform subpassInput sceneTexture;
layout(location = 0) out vec4 fragColor;

View File

@ -28,7 +28,7 @@ layout(location = 3) flat in struct
} In2;
layout (set = 0, binding = 1) uniform sampler2D textures[]; // for textures (global)
layout (std430, set = 3, binding = 0) buffer MaterialProperties // For materials
layout (std430, set = 2, binding = 0) buffer MaterialProperties // For materials
{
MatPropData data[];
} MatProp;

Binary file not shown.

View File

@ -29,13 +29,12 @@ layout(location = 3) out struct
} Out2;
layout(set = 2, binding = 0) uniform CameraData
layout(set = 1, binding = 0) uniform CameraData
{
vec4 position;
mat4 vpMat;
mat4 viewMat;
mat4 perspectiveMat;
mat4 orthoMat;
mat4 projMat;
} cameraData;
void main()
@ -60,7 +59,7 @@ void main()
Out.normal.rgb = normalize (Out.normal.rgb);
// clip space for rendering
gl_Position = cameraData.orthoMat * worldTransform * vec4 (aVertexPos, 1.0f);
gl_Position = cameraData.projMat * worldTransform * vec4 (aVertexPos, 1.0f);
gl_Position.z += 0.1f; // HAX
// gl_Position = vec4 (aVertexPos, 1.0f);
}

Binary file not shown.

View File

@ -20,10 +20,11 @@ echo "M - SDL"
echo "N - dotnet"
echo "O - tinyddsloader"
echo "P - fmod"
echo "Q - vswhere"
echo ---------------------------------------------------
echo.
choice /C ABCDEFGHIJKLMNOP /T 10 /D A
choice /C ABCDEFGHIJKLMNOPQ /T 10 /D A
set _e=%ERRORLEVEL%
if %_e%==1 goto VMA
@ -42,6 +43,7 @@ if %_e%==13 goto SDL
if %_e%==14 goto dotnet
if %_e%==15 goto tinyddsloader
if %_e%==16 goto fmod
if %_e%==17 goto vswhere
:VMA
echo -----------------------VMA----------------------------
@ -155,6 +157,13 @@ if %_e%==15 (goto :done) else (goto :fmod)
echo --------------------fmod-------------------------
rmdir "Dependencies/fmod" /S /Q
git clone https://github.com/SHADE-DP/FMOD.git "Dependencies/fmod"
if %_e%==16 (goto :done) else (goto :vswhere)
:vswhere
echo -----------------------vswhere----------------------------
rmdir "Dependencies/vswhere" /S /Q
mkdir "Dependencies/vswhere"
powershell -Command "& {wget https://github.com/microsoft/vswhere/releases/download/3.1.1/vswhere.exe -OutFile "Dependencies/vswhere/vswhere.exe"}"
:done
echo DONE!

View File

@ -17,3 +17,4 @@ IncludeDir["VULKAN"] = "$(VULKAN_SDK)"
IncludeDir["dotnet"] = "%{wks.location}\\Dependencies\\dotnet"
IncludeDir["tinyddsloader"] = "%{wks.location}\\Dependencies\\tinyddsloader"
IncludeDir["fmod"] = "%{wks.location}\\Dependencies\\fmod"
IncludeDir["vswhere"] = "%{wks.location}\\Dependencies\\vswhere"

View File

@ -67,6 +67,9 @@ namespace Sandbox
SHFileUtilities::SetWorkDirToExecDir();
WindowData wndData{};
auto& appConfig = SHConfigurationManager::LoadApplicationConfig(&wndData);
#if SHEDITOR
auto& editorConfig = SHConfigurationManager::LoadEditorConfig(&wndData);
#endif
window.Create(hInstance, hPrevInstance, lpCmdLine, nCmdShow, wndData);
// Create Systems
@ -158,8 +161,11 @@ namespace Sandbox
SHSystemManager::Init();
#if SHEDITOR
SHSceneManager::InitSceneManager<SBMainScene>(editorConfig.workingSceneID);
#else
SHSceneManager::InitSceneManager<SBMainScene>(appConfig.startingSceneID);
#endif
SHFrameRateController::UpdateFRC();
// Link up SHDebugDraw

View File

@ -124,7 +124,8 @@ project "SHADE_Engine"
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Debug\\ModelCompiler.exe\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.FontCompiler}\\bin\\Debug\\FontCompiler.exe\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodL.dll\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudioL.dll\" \"$(OutDir)\""
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudioL.dll\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.vswhere}\\vswhere.exe\" \"$(OutDir)\""
}
filter "configurations:Release"
@ -134,7 +135,8 @@ project "SHADE_Engine"
"xcopy /r /y /q \"%{IncludeDir.ModelCompiler}\\bin\\Release\\ModelCompiler.exe\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.FontCompiler}\\bin\\Release\\FontCompiler.exe\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmod.dll\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudio.dll\" \"$(OutDir)\""
"xcopy /r /y /q \"%{IncludeDir.fmod}\\lib\\fmodstudio.dll\" \"$(OutDir)\"",
"xcopy /r /y /q \"%{IncludeDir.vswhere}\\vswhere.exe\" \"$(OutDir)\""
}
filter "configurations:Publish"

View File

@ -226,7 +226,7 @@ namespace SHADE
const SHMatrix& SHCameraComponent::GetPerspectiveMatrix() const noexcept
{
return orthoProjMatrix;
return perspProjMatrix;
}
//void SHCameraComponent::SetMainCamera(size_t directorCameraIndex) noexcept

View File

@ -18,11 +18,17 @@ namespace SHADE
SHCommandManager::CommandStackPtr SHCommandManager::pCurrUndoStack(&undoStack);
SHCommandManager::CommandStackPtr SHCommandManager::pCurrRedoStack(&redoStack);
bool SHCommandManager::failedExecution(false);
void SHCommandManager::PerformCommand(BaseCommandPtr commandPtr, bool const& overrideValue)
{
*pCurrRedoStack = CommandStack(defaultStackSize);
commandPtr->Execute();
if(failedExecution)
{
failedExecution = false;
return;
}
*pCurrRedoStack = CommandStack(defaultStackSize);
if (overrideValue && !pCurrUndoStack->Empty())
{
pCurrUndoStack->Top()->Merge(commandPtr);
@ -68,12 +74,14 @@ namespace SHADE
void SHCommandManager::PopLatestCommandFromRedoStack()
{
pCurrRedoStack->Pop();
if(!pCurrRedoStack->Empty())
pCurrRedoStack->Pop();
}
void SHCommandManager::PopLatestCommandFromUndoStack()
{
pCurrUndoStack->Pop();
if(!pCurrUndoStack->Empty())
pCurrUndoStack->Pop();
}
void SHCommandManager::SwapStacks()

View File

@ -39,6 +39,7 @@ namespace SHADE
static void SwapStacks();
static void ClearAll();
static bool failedExecution;
static constexpr CommandStack::SizeType defaultStackSize = 100;
private:
static CommandStackPtr pCurrUndoStack;

View File

@ -14,6 +14,8 @@
#include "Editor/DragDrop/SHDragDrop.hpp"
#include "Editor/EditorWindow/MaterialInspector/SHMaterialInspector.h"
#include "Editor/EditorWindow/SHEditorWindowManager.h"
#include "Scripting/SHVSUtilities.h"
#include "Scripting/SHScriptEngine.h"
namespace SHADE
{
@ -249,6 +251,12 @@ namespace SHADE
matInspector->OpenMaterial(asset->id);
}
break;
case AssetType::SCRIPT:
if(auto scriptEngine = SHSystemManager::GetSystem<SHScriptEngine>())
{
scriptEngine->OpenFile(asset->path);
}
break;
case AssetType::MAX_COUNT: break;
default:;
}

View File

@ -84,33 +84,31 @@ namespace SHADE
editor->selectedEntities.clear();
}
ImGui::SeparatorEx(ImGuiSeparatorFlags_Horizontal);
if (ImGui::IsWindowFocused())
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_A))
{
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_A))
SelectAllEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_C))
{
CopySelectedEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && !ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyReleased(ImGuiKey_V))
{
PasteEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyReleased(ImGuiKey_V))
{
const auto editor = SHSystemManager::GetSystem<SHEditor>();
if (editor->selectedEntities.size() == 1)
{
SelectAllEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_C))
{
CopySelectedEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && !ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyReleased(ImGuiKey_V))
{
PasteEntities();
}
if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyReleased(ImGuiKey_V))
{
const auto editor = SHSystemManager::GetSystem<SHEditor>();
if (editor->selectedEntities.size() == 1)
{
PasteEntities(editor->selectedEntities.back());
}
}
if(ImGui::IsKeyReleased(ImGuiKey_Delete))
{
DeleteSelectedEntities();
PasteEntities(editor->selectedEntities.back());
}
}
if (ImGui::IsKeyReleased(ImGuiKey_Delete))
{
DeleteSelectedEntities();
}
}
if(ImGui::IsWindowHovered() && !ImGui::IsAnyItemHovered() && ImGui::IsMouseReleased(ImGuiMouseButton_Left))

View File

@ -19,6 +19,9 @@
#include "Reflection/SHReflectionMetadata.h"
#include "Resource/SHResourceManager.h"
#include "Physics/Collision/SHCollisionTagMatrix.h"
#include "Serialization/SHSerializationHelper.hpp"
#include "Tools/Utilities/SHClipboardUtilities.h"
#include "SHInspectorCommands.h"
namespace SHADE
{
template<typename T>
@ -46,11 +49,12 @@ namespace SHADE
if (ImGui::Selectable(std::format("{} Copy {}", ICON_MD_CONTENT_COPY, componentName.data()).data()))
{
//SHClipboardUtil::WriteStringToClipboard(SHClipboardUtil::CFNAME::CFCOMPONENT, SHComponentToString(component));
SHClipboardUtilities::WriteToClipboard(SHSerializationHelper::SerializeComponentToString<T>(component->GetEID()));
}
if (ImGui::Selectable(std::format("{} Paste {}", ICON_MD_CONTENT_PASTE, componentName.data()).data()))
{
//SHStringToComponent(component, SHClipboardUtil::ReadStringFromClipboard(SHClipboardUtil::CFNAME::CFCOMPONENT));
//SHSerializationHelper::DeserializeComponentFromString<T>(SHClipboardUtilities::GetDataFromClipboard(), component->GetEID());
SHCommandManager::PerformCommand(std::reinterpret_pointer_cast<SHBaseCommand>( std::make_shared<SHPasteComponentCommand<T>>(component->GetEID(), SHClipboardUtilities::GetDataFromClipboard())));
}
if (ImGui::Selectable(std::format("{} Delete {}", ICON_MD_DELETE, componentName.data()).data()))
{

View File

@ -0,0 +1,27 @@
#pragma once
#include "Editor/Command/SHCommand.hpp"
namespace SHADE
{
template<typename T>
class SHPasteComponentCommand final : SHBaseCommand
{
public:
struct Data
{
EntityID eid;
std::string oldComponentData;
std::string newComponentData;
};
SHPasteComponentCommand(EntityID eid, std::string const& newComponentData);
void Execute() override;
void Undo() override;
private:
Data data;
};
}
#include "SHInspectorCommands.hpp"

View File

@ -0,0 +1,26 @@
#pragma once
#include "SHInspectorCommands.h"
namespace SHADE
{
template<typename T>
SHPasteComponentCommand<T>::SHPasteComponentCommand(EntityID eid, std::string const& newComponentData)
:data(eid, {}, newComponentData)
{
data.oldComponentData = SHSerializationHelper::SerializeComponentToString<T>(eid);
}
template<typename T>
void SHPasteComponentCommand<T>::Execute()
{
bool result = SHSerializationHelper::DeserializeComponentFromString<T>(data.newComponentData, data.eid);
if(!result)
SHCommandManager::failedExecution = true;
}
template<typename T>
void SHPasteComponentCommand<T>::Undo()
{
SHSerializationHelper::DeserializeComponentFromString<T>(data.oldComponentData, data.eid);
}
}

View File

@ -196,10 +196,12 @@ namespace SHADE
if (!fragShader)
return;
auto const& mappings = SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::BATCHING);
// Get interface for the shader combination
auto interface = fragShader->GetReflectedData().GetDescriptorBindingInfo().GetShaderBlockInterface
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
mappings.at(SHPredefinedDescriptorTypes::MATERIALS),
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA
);
if (!interface)

View File

@ -81,126 +81,18 @@ namespace SHADE
if (ImGui::BeginMainMenuBar())
{
if (ImGui::BeginMenu("File"))
{
if(ImGui::Selectable("New Scene"))
{
SHSystemManager::GetSystem<SHEditor>()->NewScene();
}
if(ImGui::Selectable("Save"))
{
SHSystemManager::GetSystem<SHEditor>()->SaveScene();
}
if(ImGui::Selectable("Load"))
{
//SHSystemManager::GetSystem<SHEditor>()->LoadScene()
}
ImGui::EndMenu();
}
if(ImGui::BeginMenu("Edit"))
{
ImGui::BeginDisabled(!SHCommandManager::GetUndoStackSize());
if(ImGui::Button(std::format("{} Undo", ICON_MD_UNDO).data()))
{
SHCommandManager::UndoCommand();
}
ImGui::EndDisabled();
ImGui::BeginDisabled(!SHCommandManager::GetRedoStackSize());
if(ImGui::Button(std::format("{} Redo", ICON_MD_REDO).data()))
{
SHCommandManager::RedoCommand();
}
ImGui::EndDisabled();
ImGui::EndMenu();
}
if (ImGui::BeginMenu("Scripts"))
{
if (ImGui::Selectable("Generate Visual Studio Project"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
scriptEngine->GenerateScriptsCsProjFile();
}
ImGui::BeginDisabled(SHSystemManager::GetSystem<SHEditor>()->editorState != SHEditor::State::STOP);
if (ImGui::Selectable("Build Scripts - Debug"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
SHSerialization::SerializeSceneToFile(SHSceneManager::GetCurrentSceneAssetID());
scriptEngine->BuildScriptAssembly(true, true);
SHSceneManager::RestartScene(SHSceneManager::GetCurrentSceneAssetID());
}
if (ImGui::Selectable("Build Scripts - Release"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
SHSerialization::SerializeSceneToFile(SHSceneManager::GetCurrentSceneAssetID());
scriptEngine->BuildScriptAssembly(false, true);
SHSceneManager::RestartScene(SHSceneManager::GetCurrentSceneAssetID());
}
ImGui::EndDisabled();
ImGui::EndMenu();
}
DrawFileMenu();
DrawEditMenu();
DrawScriptsMenu();
DrawWindowMenu();
DrawThemeMenu();
DrawLayoutMenu();
DrawApplicationConfig();
if (ImGui::BeginMenu("Window"))
{
for (const auto& window : SHEditorWindowManager::editorWindows | std::views::values)
{
if (window.get() != this)
ImGui::Checkbox(window->windowName.data(), &window->isOpen);
}
ImGui::EndMenu();
}
if (ImGui::BeginMenu("Theme"))
{
const auto styles = rttr::type::get<SHEditor::Style>().get_enumeration();
auto values = styles.get_values();
for (auto style : values)
{
if (ImGui::Selectable(style.to_string().c_str()))
{
if (auto editor = SHSystemManager::GetSystem<SHEditor>())
editor->SetStyle(style.convert<SHEditor::Style>());
}
}
ImGui::EndMenu();
}
if(ImGui::BeginMenu("Layout"))
{
for(auto const& entry : layoutPaths)
{
if(ImGui::Selectable(entry.stem().string().c_str()))
{
ImGui::LoadIniSettingsFromDisk(entry.string().c_str());
}
}
ImGui::EndMenu();
}
if (ImGui::BeginMenu("Application Config"))
{
auto& appConfig = SHConfigurationManager::applicationConfig;
ImGui::InputText("Window Title", &appConfig.windowTitle);
ImGui::Checkbox("Start in Fullscreen", &appConfig.startInFullScreen);
SHEditorWidgets::DragN<float, 2>("Window Size", { "Width", "Height" }, { &appConfig.windowSize.x, &appConfig.windowSize.y });
//ImGui::InputScalar("Starting Scene", ImGuiDataType_U32, &appConfig.startingSceneID);
auto sceneAsset = SHAssetManager::GetData<SHSceneAsset>(appConfig.startingSceneID);
if(ImGui::BeginCombo("Starting Scne", sceneAsset ? sceneAsset->name.data() : ""))
{
auto scenes = SHAssetManager::GetAllRecordOfType(AssetType::SCENE);
for(auto const& scene : scenes)
{
if(ImGui::Selectable(scene.name.data()))
{
appConfig.startingSceneID = scene.id;
}
}
ImGui::EndCombo();
}
if (ImGui::Button("Save"))
{
SHConfigurationManager::SaveApplicationConfig();
}
ImGui::EndMenu();
}
std::string const sceneName{std::format("Current Scene: {}",SHSceneManager::GetSceneName().data())};
auto const size = ImGui::CalcTextSize(sceneName.data());
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - size.x - ImGui::GetStyle().FramePadding.x);
ImGui::Text("%s", sceneName.data());
ImGui::EndMainMenuBar();
}
@ -267,4 +159,148 @@ namespace SHADE
ImGui::PopStyleVar(3);
}
void SHEditorMenuBar::DrawFileMenu() noexcept
{
if (ImGui::BeginMenu("File"))
{
if (ImGui::Selectable("New Scene"))
{
SHSystemManager::GetSystem<SHEditor>()->NewScene();
}
if (ImGui::Selectable("Save"))
{
SHSystemManager::GetSystem<SHEditor>()->SaveScene();
}
if (ImGui::Selectable("Load"))
{
//SHSystemManager::GetSystem<SHEditor>()->LoadScene()
}
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawEditMenu() noexcept
{
if (ImGui::BeginMenu("Edit"))
{
ImGui::BeginDisabled(!SHCommandManager::GetUndoStackSize());
if (ImGui::Button(std::format("{} Undo", ICON_MD_UNDO).data()))
{
SHCommandManager::UndoCommand();
}
ImGui::EndDisabled();
ImGui::BeginDisabled(!SHCommandManager::GetRedoStackSize());
if (ImGui::Button(std::format("{} Redo", ICON_MD_REDO).data()))
{
SHCommandManager::RedoCommand();
}
ImGui::EndDisabled();
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawScriptsMenu() noexcept
{
if (ImGui::BeginMenu("Scripts"))
{
if (ImGui::Selectable("Generate Visual Studio Project"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
scriptEngine->GenerateScriptsCsProjFile();
}
if (ImGui::Selectable("Open Visual Studio Project"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
scriptEngine->OpenSolution();
}
ImGui::BeginDisabled(SHSystemManager::GetSystem<SHEditor>()->editorState != SHEditor::State::STOP);
if (ImGui::Selectable("Build Scripts - Debug"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
SHSerialization::SerializeSceneToFile(SHSceneManager::GetCurrentSceneAssetID());
scriptEngine->BuildScriptAssembly(true, true);
SHSceneManager::RestartScene(SHSceneManager::GetCurrentSceneAssetID());
}
if (ImGui::Selectable("Build Scripts - Release"))
{
auto* scriptEngine = static_cast<SHScriptEngine*>(SHSystemManager::GetSystem<SHScriptEngine>());
SHSerialization::SerializeSceneToFile(SHSceneManager::GetCurrentSceneAssetID());
scriptEngine->BuildScriptAssembly(false, true);
SHSceneManager::RestartScene(SHSceneManager::GetCurrentSceneAssetID());
}
ImGui::EndDisabled();
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawWindowMenu() noexcept
{
if (ImGui::BeginMenu("Window"))
{
for (const auto& window : SHEditorWindowManager::editorWindows | std::views::values)
{
if (window.get() != this)
ImGui::Checkbox(window->windowName.data(), &window->isOpen);
}
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawThemeMenu() noexcept
{
if (ImGui::BeginMenu("Theme"))
{
const auto styles = rttr::type::get<SHEditor::Style>().get_enumeration();
auto values = styles.get_values();
for (auto style : values)
{
if (ImGui::Selectable(style.to_string().c_str()))
{
if (auto editor = SHSystemManager::GetSystem<SHEditor>())
editor->SetStyle(style.convert<SHEditor::Style>());
}
}
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawLayoutMenu() noexcept
{
if (ImGui::BeginMenu("Layout"))
{
for (auto const& entry : layoutPaths)
{
if (ImGui::Selectable(entry.stem().string().c_str()))
{
ImGui::LoadIniSettingsFromDisk(entry.string().c_str());
}
}
ImGui::EndMenu();
}
}
void SHEditorMenuBar::DrawApplicationConfig() noexcept
{
if (ImGui::BeginMenu("Application Config"))
{
auto& appConfig = SHConfigurationManager::applicationConfig;
ImGui::InputText("Window Title", &appConfig.windowTitle);
ImGui::Checkbox("Start in Fullscreen", &appConfig.startInFullScreen);
SHEditorWidgets::DragN<float, 2>("Window Size", { "Width", "Height" }, { &appConfig.windowSize.x, &appConfig.windowSize.y });
//ImGui::InputScalar("Starting Scene", ImGuiDataType_U32, &appConfig.startingSceneID);
auto sceneAsset = SHAssetManager::GetData<SHSceneAsset>(appConfig.startingSceneID);
if (ImGui::BeginCombo("Starting Scene", sceneAsset ? sceneAsset->name.data() : ""))
{
auto scenes = SHAssetManager::GetAllRecordOfType(AssetType::SCENE);
for (auto const& scene : scenes)
{
if (ImGui::Selectable(scene.name.data()))
{
appConfig.startingSceneID = scene.id;
}
}
ImGui::EndCombo();
}
if (ImGui::Button("Save"))
{
SHConfigurationManager::SaveApplicationConfig();
}
ImGui::EndMenu();
}
}
}//namespace SHADE

View File

@ -17,6 +17,15 @@ namespace SHADE
void DrawMainMenuBar() noexcept;
void DrawSecondaryBar() const noexcept;
void DrawStatusBar() const noexcept;
void DrawFileMenu() noexcept;
void DrawEditMenu() noexcept;
void DrawScriptsMenu() noexcept;
void DrawWindowMenu() noexcept;
void DrawThemeMenu() noexcept;
void DrawLayoutMenu() noexcept;
void DrawApplicationConfig() noexcept;
float menuBarHeight = 20.0f;
std::vector<std::filesystem::path> layoutPaths;
};//class SHEditorMenuBar

View File

@ -94,6 +94,8 @@ namespace SHADE
}
}
editorConfig = &SHConfigurationManager::LoadEditorConfig();
//Add editor windows
SHEditorWindowManager::CreateEditorWindow<SHEditorMenuBar>();
SHEditorWindowManager::CreateEditorWindow<SHHierarchyPanel>();
@ -122,7 +124,7 @@ namespace SHADE
InitBackend();
SetStyle(Style::SHADE);
SetStyle(static_cast<Style>(editorConfig->style));
for (const auto& window : SHEditorWindowManager::editorWindows | std::views::values)
@ -160,26 +162,7 @@ namespace SHADE
RenderUnsavedChangesPrompt();
//PollPicking();
if(ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_Z))
{
SHCommandManager::RedoCommand();
}
else if(ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_Z))
{
SHCommandManager::UndoCommand();
}
if(ImGui::IsKeyReleased(ImGuiKey_F5))
{
Play();
}
else if (ImGui::IsKeyReleased(ImGuiKey_F6))
{
Pause();
}
else if (ImGui::IsKeyReleased(ImGuiKey_F7))
{
Stop();
}
ProcessShortcuts();
Render();
}
@ -376,10 +359,14 @@ namespace SHADE
ImGui_ImplVulkan_Shutdown();
ImGui_ImplSDL2_Shutdown();
ImGui::DestroyContext();
editorConfig->startMaximized = shWindow->GetWindowData().isMaximised;
SHConfigurationManager::SaveEditorConfig();
}
void SHEditor::SetStyle(Style style)
{
editorConfig->style = static_cast<uint32_t>(style);
switch (style)
{
default:
@ -501,10 +488,7 @@ namespace SHADE
imguiCommandBuffer = imguiCommandPool->RequestCommandBuffer(SH_CMD_BUFFER_TYPE::PRIMARY);
//auto const& renderers = gfxSystem->GetDefaultViewport()->GetRenderers();
auto const& renderers = gfxSystem->GetEditorViewport()->GetRenderers();
SHASSERT(!renderers.empty(), "No Renderers available")
auto renderGraph = renderers[SHGraphicsConstants::RenderGraphIndices::EDITOR]->GetRenderGraph();
auto renderGraph = gfxSystem->GetRenderGraph();
auto renderPass = renderGraph->GetNode("ImGui Node")->GetRenderpass();
if(ImGui_ImplVulkan_Init(&initInfo, renderPass->GetVkRenderpass()) == false)
@ -524,7 +508,7 @@ namespace SHADE
ImGui_ImplVulkan_DestroyFontUploadObjects();
renderGraph->GetNode("ImGui Node")->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer>& cmd, uint32_t frameIndex)
renderGraph->GetNode("ImGui Node")->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer> cmd, Handle<SHRenderer> renderer, uint32_t frameIndex)
{
cmd->BeginLabeledSegment("ImGui Draw");
ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), cmd->GetVkCommandBuffer());
@ -586,6 +570,7 @@ namespace SHADE
SHSceneManager::SetCurrentSceneName(newSceneName);
SHSceneManager::SetCurrentSceneAssetID(SHAssetManager::CreateNewAsset(AssetType::SCENE, newSceneName));
editorConfig->workingSceneID = SHSceneManager::GetCurrentSceneAssetID();
}
//Get data, if data is null, asset doesn't exist, prompt for a name and create a new asset with the name
@ -594,7 +579,7 @@ namespace SHADE
{
if(shWindow->IsUnsavedChanges())
shWindow->ToggleUnsavedChanges();
editorConfig->workingSceneID = SHSceneManager::GetCurrentSceneAssetID();
return true;
}
return false;
@ -662,6 +647,37 @@ namespace SHADE
LoadScene(SHSceneManager::GetCurrentSceneAssetID());
}
void SHEditor::ProcessShortcuts()
{
if(ImGui::IsKeyDown(ImGuiKey_LeftCtrl))
{
if(ImGui::IsKeyReleased(ImGuiKey_S))
{
SaveScene();
}
}
if (ImGui::IsKeyDown(ImGuiKey_LeftShift) && ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_Z))
{
SHCommandManager::RedoCommand();
}
else if (ImGui::IsKeyDown(ImGuiKey_LeftCtrl) && ImGui::IsKeyReleased(ImGuiKey_Z))
{
SHCommandManager::UndoCommand();
}
if (ImGui::IsKeyReleased(ImGuiKey_F5))
{
Play();
}
else if (ImGui::IsKeyReleased(ImGuiKey_F6))
{
Pause();
}
else if (ImGui::IsKeyReleased(ImGuiKey_F7))
{
Stop();
}
}
void SHEditor::NewFrame()
{
SDL_Event event;
@ -675,6 +691,18 @@ namespace SHADE
ImGuizmo::BeginFrame();
}
void SHEditor::SetSHWindow(SHWindow* inWindow)
{
shWindow = inWindow;
shWindow->RegisterWindowSizeCallback([&](uint32_t width, uint32_t height)
{
if(width > 0 && height > 0)
{
auto [width, height] = shWindow->GetWindowSize();
editorConfig->windowSize = { static_cast<float>(width), static_cast<float>(height) };
}
});
}
void SHEditor::EditorRoutine::Execute(double dt) noexcept
{

View File

@ -20,6 +20,7 @@
#include "Events/SHEventDefines.h"
#include "Events/SHEvent.h"
#include "Graphics/Windowing/SHWindow.h"
#include "Serialization/Configurations/SHConfigurationManager.h"
//#==============================================================#
//|| Library Includes ||
@ -108,7 +109,7 @@ namespace SHADE
void InitBackend();
void SetSDLWindow(SDL_Window* inSDLWindow){sdlWindow = inSDLWindow;};
void SetSHWindow(SHWindow* inWindow){shWindow = inWindow;}
void SetSHWindow(SHWindow* inWindow);
void PollPicking();
@ -122,11 +123,15 @@ namespace SHADE
void Pause();
void Stop();
void ProcessShortcuts();
// List of selected entities
std::vector<EntityID> selectedEntities;
State editorState = State::STOP;
SHEditorConfig* editorConfig;
private:
/**
* @brief Start new frame for editor

View File

@ -160,7 +160,7 @@ namespace SHADE
template <typename T, std::size_t N>
static bool DragN(const std::string& label, std::vector<std::string>const& componentLabels,
std::vector<T*> values, float speed = 0.1f, const char* displayFormat = "", T valueMin = T(), T valueMax = T(),
std::vector<T*> values, float speed = 0.1f, const char* displayFormat = "%.3f", T valueMin = T(), T valueMax = T(),
ImGuiSliderFlags flags = 0, bool* isHovered = nullptr)
{
const ImGuiWindow* const window = ImGui::GetCurrentWindow();

View File

@ -5,21 +5,22 @@ typedef uint32_t SHEventIdentifier;
typedef uint32_t SHEventHandle;
//Add your event identifiers here:
constexpr SHEventIdentifier SH_EXAMPLE_EVENT { 0 };
constexpr SHEventIdentifier SH_ENTITY_DESTROYED_EVENT { 1 };
constexpr SHEventIdentifier SH_ENTITY_CREATION_EVENT { 2 };
constexpr SHEventIdentifier SH_COMPONENT_ADDED_EVENT { 3 };
constexpr SHEventIdentifier SH_COMPONENT_REMOVED_EVENT { 4 };
constexpr SHEventIdentifier SH_SCENEGRAPH_CHANGE_PARENT_EVENT { 5 };
constexpr SHEventIdentifier SH_SCENEGRAPH_ADD_CHILD_EVENT { 6 };
constexpr SHEventIdentifier SH_SCENEGRAPH_REMOVE_CHILD_EVENT { 7 };
constexpr SHEventIdentifier SH_PHYSICS_COLLIDER_ADDED_EVENT { 8 };
constexpr SHEventIdentifier SH_PHYSICS_COLLIDER_REMOVED_EVENT { 9 };
constexpr SHEventIdentifier SH_EDITOR_ON_PLAY_EVENT { 10 };
constexpr SHEventIdentifier SH_EDITOR_ON_PAUSE_EVENT { 11 };
constexpr SHEventIdentifier SH_EDITOR_ON_STOP_EVENT { 12 };
constexpr SHEventIdentifier SH_SCENE_INIT_PRE { 13 };
constexpr SHEventIdentifier SH_SCENE_INIT_POST { 14 };
constexpr SHEventIdentifier SH_SCENE_EXIT_PRE { 15 };
constexpr SHEventIdentifier SH_SCENE_EXIT_POST { 16 };
constexpr SHEventIdentifier SH_EXAMPLE_EVENT { 0 };
constexpr SHEventIdentifier SH_ENTITY_DESTROYED_EVENT { 1 };
constexpr SHEventIdentifier SH_ENTITY_CREATION_EVENT { 2 };
constexpr SHEventIdentifier SH_COMPONENT_ADDED_EVENT { 3 };
constexpr SHEventIdentifier SH_COMPONENT_REMOVED_EVENT { 4 };
constexpr SHEventIdentifier SH_SCENEGRAPH_CHANGE_PARENT_EVENT { 5 };
constexpr SHEventIdentifier SH_SCENEGRAPH_ADD_CHILD_EVENT { 6 };
constexpr SHEventIdentifier SH_SCENEGRAPH_REMOVE_CHILD_EVENT { 7 };
constexpr SHEventIdentifier SH_PHYSICS_COLLIDER_ADDED_EVENT { 8 };
constexpr SHEventIdentifier SH_PHYSICS_COLLIDER_REMOVED_EVENT { 9 };
constexpr SHEventIdentifier SH_EDITOR_ON_PLAY_EVENT { 10 };
constexpr SHEventIdentifier SH_EDITOR_ON_PAUSE_EVENT { 11 };
constexpr SHEventIdentifier SH_EDITOR_ON_STOP_EVENT { 12 };
constexpr SHEventIdentifier SH_SCENE_INIT_PRE { 13 };
constexpr SHEventIdentifier SH_SCENE_INIT_POST { 14 };
constexpr SHEventIdentifier SH_SCENE_EXIT_PRE { 15 };
constexpr SHEventIdentifier SH_SCENE_EXIT_POST { 16 };
constexpr SHEventIdentifier SH_GRAPHICS_LIGHT_ENABLE_SHADOW_EVENT { 17 };

View File

@ -367,7 +367,7 @@ namespace SHADE
}
}
void SHVkCommandBuffer::BindDescriptorSet(Handle<SHVkDescriptorSetGroup> descSetGroup, SH_PIPELINE_TYPE bindPoint, uint32_t firstSet, std::span<uint32_t> dynamicOffsets)
void SHVkCommandBuffer::BindDescriptorSet(Handle<SHVkDescriptorSetGroup> descSetGroup, SH_PIPELINE_TYPE bindPoint, uint32_t firstSet, std::span<uint32_t> const dynamicOffsets)
{
uint32_t bindPointIndex = static_cast<uint32_t>(bindPoint);
vkCommandBuffer.bindDescriptorSets(SHVkUtil::GetPipelineBindPointFromType(bindPoint), bindPointData[bindPointIndex].boundPipelineLayoutHdl->GetVkPipelineLayout(), firstSet, descSetGroup->GetVkHandle(), dynamicOffsets);

View File

@ -125,7 +125,7 @@ namespace SHADE
void BindPipeline (Handle<SHVkPipeline> const& pipelineHdl) noexcept;
void BindVertexBuffer (uint32_t bindingPoint, Handle<SHVkBuffer> const& buffer, vk::DeviceSize offset) noexcept;
void BindIndexBuffer (Handle<SHVkBuffer> const& buffer, uint32_t startingIndex) const noexcept;
void BindDescriptorSet (Handle<SHVkDescriptorSetGroup> descSetGroup, SH_PIPELINE_TYPE bindPoint, uint32_t firstSet, std::span<uint32_t> dynamicOffsets);
void BindDescriptorSet (Handle<SHVkDescriptorSetGroup> descSetGroup, SH_PIPELINE_TYPE bindPoint, uint32_t firstSet, std::span<uint32_t> const dynamicOffsets);
// Draw Commands
void DrawArrays (uint32_t vertexCount, uint32_t instanceCount, uint32_t firstVertex, uint32_t firstInstance) const noexcept;

View File

@ -53,7 +53,6 @@ namespace SHADE
for (uint32_t i = 0; i < layouts.size(); ++i)
{
vkLayouts[i] = layouts[i]->GetVkHandle();
setIndexing.emplace(layouts[i]->GetSetIndex(), i);
}
// Check for variable descriptor count
@ -87,7 +86,7 @@ namespace SHADE
for (auto& binding : bindings)
{
BindingAndSetHash writeHash = binding.BindPoint;
writeHash |= static_cast<uint64_t>(layouts[i]->GetSetIndex()) << 32;
writeHash |= static_cast<uint64_t>(i) << 32;
// new write for the binding
updater.writeInfos.emplace_back();
@ -208,16 +207,13 @@ namespace SHADE
// Get binding + set hash
BindingAndSetHash bsHash = SHVkUtil::GenBindingSetHash(set, binding);
// to index a set
uint32_t setIndex = setIndexing[set];
// to index a write for a binding
uint32_t writeInfoIndex = updater.writeHashMap[bsHash];
// Initialize info for write
writeDescSet.descriptorType = layoutsUsed[setIndex]->GetBindings()[binding].Type;
writeDescSet.descriptorType = layoutsUsed[set]->GetBindings()[binding].Type;
writeDescSet.dstArrayElement = 0;
writeDescSet.dstSet = descSets[setIndex];
writeDescSet.dstSet = descSets[set];
writeDescSet.dstBinding = binding;
writeDescSet.pImageInfo = updater.writeInfos[writeInfoIndex].descImageInfos.data();
@ -233,16 +229,13 @@ namespace SHADE
// Get binding + set hash
BindingAndSetHash bsHash = SHVkUtil::GenBindingSetHash(set, binding);
// to index a set
uint32_t setIndex = setIndexing[set];
// to index a write for a binding
uint32_t writeInfoIndex = updater.writeHashMap[bsHash];
// Initialize info for write
writeDescSet.descriptorType = layoutsUsed[setIndex]->GetBindings()[binding].Type;
writeDescSet.descriptorType = layoutsUsed[set]->GetBindings()[binding].Type;
writeDescSet.dstArrayElement = 0;
writeDescSet.dstSet = descSets[setIndex];
writeDescSet.dstSet = descSets[set];
writeDescSet.dstBinding = binding;
writeDescSet.pBufferInfo = updater.writeInfos[writeInfoIndex].descBufferInfos.data();

View File

@ -21,7 +21,6 @@ namespace SHADE
class SHVkImageView;
class SHVkBuffer;
/*---------------------------------------------------------------------------------*/
/* Type Definitions */
/*---------------------------------------------------------------------------------*/
@ -91,10 +90,10 @@ namespace SHADE
//! Descriptor pool to allocate descriptor sets
Handle<SHVkDescriptorPool> descPool;
//! Sometimes when we pass in a layout, the set of the layout used in the
//! shader cannot be used to index into descSets. This is to mitigate that issue
//! when we update descriptor sets.
std::unordered_map<SetIndex, uint32_t> setIndexing;
////! Sometimes when we pass in a layout, the set of the layout used in the
////! shader cannot be used to index into descSets. This is to mitigate that issue
////! when we update descriptor sets.
//std::unordered_map<SetIndex, uint32_t> setIndexing;
//! Descriptor sets
std::vector<vk::DescriptorSet> descSets;

View File

@ -5,146 +5,138 @@
namespace SHADE
{
/*---------------------------------------------------------------------------------*/
/* Constructor/Destructor */
/*---------------------------------------------------------------------------------*/
SHVkDescriptorSetLayout::SHVkDescriptorSetLayout(Handle<SHVkLogicalDevice> device, SetIndex set, const std::vector<Binding>& bindings, bool genImmutableSamplers/* = false*/)
: device { device }
, layoutDesc { bindings }
, setIndex {set}
/*---------------------------------------------------------------------------------*/
/* Constructor/Destructor */
/*---------------------------------------------------------------------------------*/
SHVkDescriptorSetLayout::SHVkDescriptorSetLayout(Handle<SHVkLogicalDevice> device, const std::vector<Binding>& bindings, bool genImmutableSamplers/* = false*/)
: device{ device }
, layoutDesc{ bindings }
, immutableSampler{}
{
// Check if auto-binding point calculation configuration is valid
bool autoCalc = false;
for (const auto& binding : bindings)
{
// Check if auto-binding point calculation configuration is valid
bool autoCalc = false;
for (const auto& binding : bindings)
{
if (binding.BindPoint == Binding::AUTO_CALC_BINDING)
{
autoCalc = true;
}
else if (autoCalc)
{
throw std::invalid_argument("For auto calculation of bindings, all bindings must be set to AUTO_CALC_BINDING!");
}
}
vk::Sampler tempVkSampler = nullptr;
if (genImmutableSamplers)
{
// Create sampler
immutableSampler = device->CreateSampler(
{
.minFilter = vk::Filter::eLinear,
.magFilter = vk::Filter::eLinear,
.addressMode = vk::SamplerAddressMode::eRepeat,
.mipmapMode = vk::SamplerMipmapMode::eLinear,
.minLod = -1000,
.maxLod = 1000
}
);
tempVkSampler = immutableSampler->GetVkSampler();
}
// Fill up VK bindings with auto calculated bind points if needed
std::vector<vk::DescriptorSetLayoutBinding> layoutBindings;
layoutBindings.reserve(bindings.size());
int bindCount = 0;
for (const auto& binding : bindings)
{
const uint32_t CURR_BIND_POINT = autoCalc ? bindCount : binding.BindPoint;
const vk::DescriptorSetLayoutBinding VK_BINDING =
{
.binding = CURR_BIND_POINT,
.descriptorType = binding.Type,
.descriptorCount = binding.DescriptorCount,
.stageFlags = binding.Stage,
.pImmutableSamplers = genImmutableSamplers ? &tempVkSampler : nullptr,
};
layoutBindings.emplace_back(VK_BINDING);
// Save for future reference
layoutDesc[bindCount++].BindPoint = CURR_BIND_POINT;
}
// TODO: Check layout support with physical device
// Prepare binding flags
std::vector<vk::DescriptorBindingFlags> combinedBindings(bindings.size());
for (uint32_t i = 0; i < bindings.size(); ++i)
combinedBindings[i] = bindings[i].flags;
const vk::DescriptorSetLayoutBindingFlagsCreateInfo BINDING_FLAGS_CREATE_INFO
{
.bindingCount = static_cast<uint32_t>(bindings.size()), // Number of flags = number of bindings
.pBindingFlags = combinedBindings.data(), // address to flags
};
// Create the layout
const vk::DescriptorSetLayoutCreateInfo DESC_SET_LAYOUT_CREATE_INFO
{
.pNext = &BINDING_FLAGS_CREATE_INFO,
.flags = {},
.bindingCount = static_cast<uint32_t>(layoutBindings.size()),
.pBindings = layoutBindings.data(),
};
setLayout = device->GetVkLogicalDevice().createDescriptorSetLayout(DESC_SET_LAYOUT_CREATE_INFO);
}
SHVkDescriptorSetLayout::SHVkDescriptorSetLayout(SHVkDescriptorSetLayout&& rhs) noexcept
: device {rhs.device}
, setLayout {rhs.setLayout}
, layoutDesc{std::move (rhs.layoutDesc)}
, setIndex{ rhs.setIndex }
, immutableSampler{ rhs.immutableSampler }
{
rhs.setLayout = VK_NULL_HANDLE;
}
SHVkDescriptorSetLayout::~SHVkDescriptorSetLayout() noexcept
{
// Destroy layout
if (setLayout)
device->GetVkLogicalDevice().destroyDescriptorSetLayout(setLayout);
}
std::vector<SHVkDescriptorSetLayout::Binding> const& SHVkDescriptorSetLayout::GetBindings(void) const noexcept
{
return layoutDesc;
}
SetIndex SHVkDescriptorSetLayout::GetSetIndex(void) const noexcept
{
return setIndex;
}
uint32_t SHVkDescriptorSetLayout::GetNumDynamicOffsetsRequired(void) const noexcept
{
uint32_t numDynamicBindings = 0;
for (auto& binding : layoutDesc)
if (binding.BindPoint == Binding::AUTO_CALC_BINDING)
{
if (binding.Type == vk::DescriptorType::eUniformBufferDynamic || binding.Type == vk::DescriptorType::eStorageBufferDynamic)
++numDynamicBindings;
autoCalc = true;
}
else if (autoCalc)
{
throw std::invalid_argument("For auto calculation of bindings, all bindings must be set to AUTO_CALC_BINDING!");
}
return numDynamicBindings;
}
SHVkDescriptorSetLayout& SHVkDescriptorSetLayout::operator=(SHVkDescriptorSetLayout&& rhs) noexcept
vk::Sampler tempVkSampler = nullptr;
if (genImmutableSamplers)
{
if (&rhs == this)
return *this;
// Create sampler
immutableSampler = device->CreateSampler(
{
.minFilter = vk::Filter::eLinear,
.magFilter = vk::Filter::eLinear,
.addressMode = vk::SamplerAddressMode::eRepeat,
.mipmapMode = vk::SamplerMipmapMode::eLinear,
.minLod = -1000,
.maxLod = 1000
}
);
device = rhs.device;
setLayout = rhs.setLayout;
layoutDesc = std::move(rhs.layoutDesc);
setIndex = rhs.setIndex;
immutableSampler = rhs.immutableSampler;
rhs.setLayout = VK_NULL_HANDLE;
return *this;
tempVkSampler = immutableSampler->GetVkSampler();
}
// Fill up VK bindings with auto calculated bind points if needed
std::vector<vk::DescriptorSetLayoutBinding> layoutBindings;
layoutBindings.reserve(bindings.size());
int bindCount = 0;
for (const auto& binding : bindings)
{
const uint32_t CURR_BIND_POINT = autoCalc ? bindCount : binding.BindPoint;
const vk::DescriptorSetLayoutBinding VK_BINDING =
{
.binding = CURR_BIND_POINT,
.descriptorType = binding.Type,
.descriptorCount = binding.DescriptorCount,
.stageFlags = binding.Stage,
.pImmutableSamplers = genImmutableSamplers ? &tempVkSampler : nullptr,
};
layoutBindings.emplace_back(VK_BINDING);
// Save for future reference
layoutDesc[bindCount++].BindPoint = CURR_BIND_POINT;
}
// TODO: Check layout support with physical device
// Prepare binding flags
std::vector<vk::DescriptorBindingFlags> combinedBindings(bindings.size());
for (uint32_t i = 0; i < bindings.size(); ++i)
combinedBindings[i] = bindings[i].flags;
const vk::DescriptorSetLayoutBindingFlagsCreateInfo BINDING_FLAGS_CREATE_INFO
{
.bindingCount = static_cast<uint32_t>(bindings.size()), // Number of flags = number of bindings
.pBindingFlags = combinedBindings.data(), // address to flags
};
// Create the layout
const vk::DescriptorSetLayoutCreateInfo DESC_SET_LAYOUT_CREATE_INFO
{
.pNext = &BINDING_FLAGS_CREATE_INFO,
.flags = {},
.bindingCount = static_cast<uint32_t>(layoutBindings.size()),
.pBindings = layoutBindings.data(),
};
setLayout = device->GetVkLogicalDevice().createDescriptorSetLayout(DESC_SET_LAYOUT_CREATE_INFO);
}
SHVkDescriptorSetLayout::SHVkDescriptorSetLayout(SHVkDescriptorSetLayout&& rhs) noexcept
: device{ rhs.device }
, setLayout{ rhs.setLayout }
, layoutDesc{ std::move(rhs.layoutDesc) }
, immutableSampler{ rhs.immutableSampler }
{
rhs.setLayout = VK_NULL_HANDLE;
}
SHVkDescriptorSetLayout::~SHVkDescriptorSetLayout() noexcept
{
// Destroy layout
if (setLayout)
device->GetVkLogicalDevice().destroyDescriptorSetLayout(setLayout);
}
std::vector<SHVkDescriptorSetLayout::Binding> const& SHVkDescriptorSetLayout::GetBindings(void) const noexcept
{
return layoutDesc;
}
uint32_t SHVkDescriptorSetLayout::GetNumDynamicOffsetsRequired(void) const noexcept
{
uint32_t numDynamicBindings = 0;
for (auto& binding : layoutDesc)
{
if (binding.Type == vk::DescriptorType::eUniformBufferDynamic || binding.Type == vk::DescriptorType::eStorageBufferDynamic)
++numDynamicBindings;
}
return numDynamicBindings;
}
SHVkDescriptorSetLayout& SHVkDescriptorSetLayout::operator=(SHVkDescriptorSetLayout&& rhs) noexcept
{
if (&rhs == this)
return *this;
device = rhs.device;
setLayout = rhs.setLayout;
layoutDesc = std::move(rhs.layoutDesc);
immutableSampler = rhs.immutableSampler;
rhs.setLayout = VK_NULL_HANDLE;
return *this;
}
}

View File

@ -6,109 +6,107 @@
namespace SHADE
{
/*---------------------------------------------------------------------------------*/
/* Forward Declarations */
/*---------------------------------------------------------------------------------*/
class SHVkLogicalDevice;
class SHVkSampler;
/*---------------------------------------------------------------------------------*/
/* Forward Declarations */
/*---------------------------------------------------------------------------------*/
class SHVkLogicalDevice;
class SHVkSampler;
/*---------------------------------------------------------------------------------*/
/* Type Definitions */
/*---------------------------------------------------------------------------------*/
/*---------------------------------------------------------------------------------*/
/* Type Definitions */
/*---------------------------------------------------------------------------------*/
/// <summary>
/// RAII wrapper object for a Vulkan Descriptor Set Layout object.
/// </summary>
class SHVkDescriptorSetLayout
{
public:
/*-----------------------------------------------------------------------------*/
/* Type Definitions */
/*-----------------------------------------------------------------------------*/
/// <summary>
/// RAII wrapper object for a Vulkan Descriptor Set Layout object.
/// Object that describes how a descriptor binding in a DescriptorSetLayout is
/// structured.
/// </summary>
class SHVkDescriptorSetLayout
struct Binding
{
public:
/*-----------------------------------------------------------------------------*/
/* Type Definitions */
/*-----------------------------------------------------------------------------*/
/// <summary>
/// Object that describes how a descriptor binding in a DescriptorSetLayout is
/// structured.
/// </summary>
struct Binding
{
/*-------------------------------------------------------------------------*/
/* Constants */
/*-------------------------------------------------------------------------*/
/// <summary>
/// If set for the "BindPoint", binding points are automatically calculated.
/// </summary>
static constexpr uint32_t AUTO_CALC_BINDING = std::numeric_limits<uint32_t>::max();
/*-------------------------------------------------------------------------*/
/* Constants */
/*-------------------------------------------------------------------------*/
/// <summary>
/// If set for the "BindPoint", binding points are automatically calculated.
/// </summary>
static constexpr uint32_t AUTO_CALC_BINDING = std::numeric_limits<uint32_t>::max();
/// <summary>
/// For use in Binding DescriptorCount.
/// </summary>
static constexpr uint32_t VARIABLE_DESCRIPTOR_UPPER_BOUND = 2000;
/*-------------------------------------------------------------------------*/
/* Data Members */
/*-------------------------------------------------------------------------*/
/// <summary>
/// Type of element for the descriptor.
/// </summary>
vk::DescriptorType Type = {};
/// <summary>
/// Shader stage that this binding is for.
/// </summary>
vk::ShaderStageFlags Stage = {};
/// <summary>
/// Binding point for the Descriptor within the Descriptor Set.
/// </summary>
uint32_t BindPoint = AUTO_CALC_BINDING;
/// <summary>
/// Number of elements in the binding. When VK_DESCRIPTOR_BINDING_VARIABLE_DESCRIPTOR_COUNT_BIT
/// is used in VkDescriptorBindingFlagBits, this value represents the upper bound.
/// </summary>
uint32_t DescriptorCount = 1;
/// <summary>
/// For use in Binding DescriptorCount.
/// </summary>
static constexpr uint32_t VARIABLE_DESCRIPTOR_UPPER_BOUND = 2000;
/*-------------------------------------------------------------------------*/
/* Data Members */
/*-------------------------------------------------------------------------*/
/// <summary>
/// Type of element for the descriptor.
/// </summary>
vk::DescriptorType Type = {};
/// <summary>
/// Shader stage that this binding is for.
/// </summary>
vk::ShaderStageFlags Stage = {};
/// <summary>
/// Binding point for the Descriptor within the Descriptor Set.
/// </summary>
uint32_t BindPoint = AUTO_CALC_BINDING;
/// <summary>
/// Number of elements in the binding. When VK_DESCRIPTOR_BINDING_VARIABLE_DESCRIPTOR_COUNT_BIT
/// is used in VkDescriptorBindingFlagBits, this value represents the upper bound.
/// </summary>
uint32_t DescriptorCount = 1;
vk::DescriptorBindingFlags flags = {};
};
/*-----------------------------------------------------------------------------*/
/* Constructor/Destructors */
/*-----------------------------------------------------------------------------*/
SHVkDescriptorSetLayout() = delete;
/// <summary>
/// Constructs a DescriptorSetLayout with the specified properties and device.
/// </summary>
/// <param name="device"></param>
/// <param name="bindings"></param>
SHVkDescriptorSetLayout(Handle<SHVkLogicalDevice> device, SetIndex setIndex, const std::vector<Binding>& bindings, bool genImmutableSamplers = false);
SHVkDescriptorSetLayout(const SHVkDescriptorSetLayout&) = delete;
SHVkDescriptorSetLayout(SHVkDescriptorSetLayout&& rhs) noexcept;
/// <summary>
/// Destructor which will unload and deallocate all resources for this Set.
/// </summary>
~SHVkDescriptorSetLayout() noexcept;
/*-----------------------------------------------------------------------------*/
/* Overloaded Operators */
/*-----------------------------------------------------------------------------*/
SHVkDescriptorSetLayout& operator=(const SHVkDescriptorSetLayout&) = delete;
SHVkDescriptorSetLayout& operator=(SHVkDescriptorSetLayout&& rhs) noexcept;
/*-----------------------------------------------------------------------------*/
/* Getter Functions */
/*-----------------------------------------------------------------------------*/
/// <summary>
/// Retrieves the handle to the Vulkan Descriptor Set Layout handle.
/// </summary>
/// <returns>Handle to the Vulkan Descriptor Set Layout handle.</returns>
inline const vk::DescriptorSetLayout& GetVkHandle() const { return setLayout; }
std::vector<Binding> const& GetBindings (void) const noexcept;
SetIndex GetSetIndex (void) const noexcept;
uint32_t GetNumDynamicOffsetsRequired (void) const noexcept;
private:
/*-----------------------------------------------------------------------------*/
/* Data Members */
/*-----------------------------------------------------------------------------*/
Handle<SHVkLogicalDevice> device;
vk::DescriptorSetLayout setLayout;
std::vector<Binding> layoutDesc; // Stores description of the layout
SetIndex setIndex; // Index of the set
Handle<SHVkSampler> immutableSampler;
vk::DescriptorBindingFlags flags = {};
};
/*-----------------------------------------------------------------------------*/
/* Constructor/Destructors */
/*-----------------------------------------------------------------------------*/
SHVkDescriptorSetLayout() = delete;
/// <summary>
/// Constructs a DescriptorSetLayout with the specified properties and device.
/// </summary>
/// <param name="device"></param>
/// <param name="bindings"></param>
SHVkDescriptorSetLayout(Handle<SHVkLogicalDevice> device, const std::vector<Binding>& bindings, bool genImmutableSamplers = false);
SHVkDescriptorSetLayout(const SHVkDescriptorSetLayout&) = delete;
SHVkDescriptorSetLayout(SHVkDescriptorSetLayout&& rhs) noexcept;
/// <summary>
/// Destructor which will unload and deallocate all resources for this Set.
/// </summary>
~SHVkDescriptorSetLayout() noexcept;
/*-----------------------------------------------------------------------------*/
/* Overloaded Operators */
/*-----------------------------------------------------------------------------*/
SHVkDescriptorSetLayout& operator=(const SHVkDescriptorSetLayout&) = delete;
SHVkDescriptorSetLayout& operator=(SHVkDescriptorSetLayout&& rhs) noexcept;
/*-----------------------------------------------------------------------------*/
/* Getter Functions */
/*-----------------------------------------------------------------------------*/
/// <summary>
/// Retrieves the handle to the Vulkan Descriptor Set Layout handle.
/// </summary>
/// <returns>Handle to the Vulkan Descriptor Set Layout handle.</returns>
inline const vk::DescriptorSetLayout& GetVkHandle() const { return setLayout; }
std::vector<Binding> const& GetBindings(void) const noexcept;
uint32_t GetNumDynamicOffsetsRequired(void) const noexcept;
private:
/*-----------------------------------------------------------------------------*/
/* Data Members */
/*-----------------------------------------------------------------------------*/
Handle<SHVkLogicalDevice> device;
vk::DescriptorSetLayout setLayout;
std::vector<Binding> layoutDesc; // Stores description of the layout
Handle<SHVkSampler> immutableSampler;
};
}

View File

@ -561,9 +561,9 @@ namespace SHADE
}
Handle<SHVkDescriptorSetLayout> SHVkLogicalDevice::CreateDescriptorSetLayout(SetIndex setIndex, std::vector<SHVkDescriptorSetLayout::Binding> const& bindings, bool genImmutableSamplers/* = false*/) noexcept
Handle<SHVkDescriptorSetLayout> SHVkLogicalDevice::CreateDescriptorSetLayout(std::vector<SHVkDescriptorSetLayout::Binding> const& bindings, bool genImmutableSamplers/* = false*/) noexcept
{
return SHVkInstance::GetResourceManager().Create <SHVkDescriptorSetLayout>(GetHandle(), setIndex, bindings, genImmutableSamplers);
return SHVkInstance::GetResourceManager().Create <SHVkDescriptorSetLayout>(GetHandle(), bindings, genImmutableSamplers);
}
Handle<SHVkDescriptorPool> SHVkLogicalDevice::CreateDescriptorPools(const SHVkDescriptorPool::Config& config /*= {}*/) noexcept

View File

@ -190,7 +190,7 @@ namespace SHADE
Handle<SHVkRenderpass> CreateRenderpass (std::span<vk::AttachmentDescription> const vkDescriptions, std::vector<SHVkSubpassParams> const& subpasses) noexcept;
Handle<SHVkRenderpass> CreateRenderpass (std::span<vk::AttachmentDescription> const vkDescriptions, std::span<vk::SubpassDescription> const spDescs, std::span<vk::SubpassDependency> const spDeps) noexcept;
Handle<SHVkFramebuffer> CreateFramebuffer (Handle<SHVkRenderpass> const& renderpassHdl, std::vector<Handle<SHVkImageView>> const& attachments, uint32_t inWidth, uint32_t inHeight) noexcept;
Handle<SHVkDescriptorSetLayout> CreateDescriptorSetLayout (SetIndex setIndex, std::vector<SHVkDescriptorSetLayout::Binding> const& bindings, bool genImmutableSamplers = false) noexcept;
Handle<SHVkDescriptorSetLayout> CreateDescriptorSetLayout (std::vector<SHVkDescriptorSetLayout::Binding> const& bindings, bool genImmutableSamplers = false) noexcept;
Handle<SHVkDescriptorPool> CreateDescriptorPools (const SHVkDescriptorPool::Config& config = {}) noexcept;
Handle<SHVkDescriptorSetGroup> CreateDescriptorSetGroup(Handle<SHVkDescriptorPool> pool,
std::vector<Handle<SHVkDescriptorSetLayout>> const& layouts,

View File

@ -0,0 +1,14 @@
#pragma once
#include <string>
#include <initializer_list>
#include "ECS_Base/SHECSMacros.h"
namespace SHADE
{
struct SHLightEnableShadowEvent
{
//! We need to get the light component and initialize the relevant variables.
EntityID lightEntity;
};
}

View File

@ -25,7 +25,7 @@ of DigiPen Institute of Technology is prohibited.
#include "Graphics/Descriptors/SHVkDescriptorSetGroup.h"
#include "ECS_Base/Managers/SHComponentManager.h"
#include "Math/Transform/SHTransformComponent.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Graphics/Descriptors/SHVkDescriptorPool.h"
#include "Scene/SHSceneManager.h"
#include "UI/SHUIComponent.h"
@ -414,10 +414,13 @@ namespace SHADE
// - EID data
instancedIntegerData.reserve(numTotalElements);
instancedIntegerData.clear();
auto const& descMappings = SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::BATCHING);
// - Material Properties Data
const Handle<SHShaderBlockInterface> SHADER_INFO = pipeline->GetPipelineLayout()->GetShaderBlockInterface
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
descMappings.at(SHPredefinedDescriptorTypes::MATERIALS),
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
vk::ShaderStageFlagBits::eFragment
);
@ -587,11 +590,14 @@ namespace SHADE
cmdBuffer->BindVertexBuffer(SHGraphicsConstants::VertexBufferBindings::INTEGER_DATA, instancedIntegerBuffer[frameIndex], 0);
if (matPropsDescSet[frameIndex])
{
auto const& descMappings = SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::BATCHING);
cmdBuffer->BindDescriptorSet
(
matPropsDescSet[frameIndex],
SH_PIPELINE_TYPE::GRAPHICS,
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
//SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
descMappings.at(SHPredefinedDescriptorTypes::MATERIALS),
dynamicOffset
);
}
@ -610,6 +616,31 @@ namespace SHADE
cmdBuffer->EndLabeledSegment();
}
/*-----------------------------------------------------------------------------------*/
/* SHBatch - Getter Functions */
/*-----------------------------------------------------------------------------------*/
Handle<SHVkBuffer> SHBatch::GetTransformBuffer(uint32_t frameIndex) const noexcept
{
if (frameIndex >= transformDataBuffer.size())
{
SHLOG_WARNING("[SHBatch] Attempted to retrieve a transform buffer of an invalid index.");
return {};
}
return transformDataBuffer[frameIndex];
}
Handle<SHVkBuffer> SHBatch::GetMDIBuffer(uint32_t frameIndex) const noexcept
{
if (frameIndex >= drawDataBuffer.size())
{
SHLOG_WARNING("[SHBatch] Attempted to retrieve a MDI draw data buffer of an invalid index.");
return {};
}
return drawDataBuffer[frameIndex];
}
/*---------------------------------------------------------------------------------*/
/* SHBatch - Helper Functions */
/*---------------------------------------------------------------------------------*/
@ -635,7 +666,7 @@ namespace SHADE
{
matPropsDescSet[frameIndex] = descPool->Allocate
(
{ SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE] },
SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::MATERIALS),
{ 0 }
);
#ifdef _DEBUG
@ -646,17 +677,20 @@ namespace SHADE
}
#endif
}
static constexpr uint32_t MATERIAL_DESC_SET_INDEX = 0;
std::array<Handle<SHVkBuffer>, 1> bufferList = { matPropsBuffer[frameIndex] };
matPropsDescSet[frameIndex]->ModifyWriteDescBuffer
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
MATERIAL_DESC_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
bufferList,
0, static_cast<uint32_t>(matPropsDataSize)
);
matPropsDescSet[frameIndex]->UpdateDescriptorSetBuffer
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
MATERIAL_DESC_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA
);
}

View File

@ -94,6 +94,8 @@ namespace SHADE
/*---------------------------------------------------------------------------------*/
Handle<SHVkPipeline> GetPipeline() const noexcept { return pipeline; };
bool IsEmpty() const noexcept { return subBatches.empty(); }
Handle<SHVkBuffer> GetTransformBuffer(uint32_t frameIndex) const noexcept;
Handle<SHVkBuffer> GetMDIBuffer(uint32_t frameIndex) const noexcept;
private:
/*---------------------------------------------------------------------------------*/
@ -135,7 +137,6 @@ namespace SHADE
TripleBuffer boneMatrixBuffer;
TripleBuffer boneFirstIndexBuffer;
TripleDescSet boneMatricesDescSet;
/*-----------------------------------------------------------------------------*/
/* Helper Functions */
/*-----------------------------------------------------------------------------*/

View File

@ -54,7 +54,7 @@ namespace SHADE
/*-----------------------------------------------------------------------------*/
void Add(const SHRenderable* renderable) noexcept;
void Remove(const SHRenderable* renderable) noexcept;
void Clear() noexcept;
void Clear() noexcept;
void UpdateBuffers(uint32_t frameIndex, Handle<SHVkDescriptorPool> descPool);
void Build(Handle<SHVkLogicalDevice> device, Handle<SHVkDescriptorPool> descPool, uint32_t frameIndex) noexcept;
void Draw(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
@ -63,6 +63,7 @@ namespace SHADE
/* Getter Functions */
/*-----------------------------------------------------------------------------*/
Handle<SHSubpass> GetSubpass() const noexcept { return subpass; };
const std::vector<SHBatch>& GetBatches() const noexcept { return batches; }
private:
/*-----------------------------------------------------------------------------*/

View File

@ -0,0 +1,17 @@
#include "SHpch.h"
#include "SHDescriptorMappings.h"
namespace SHADE
{
void SHDescriptorMappings::AddMappings(std::initializer_list<std::pair<SHPredefinedDescriptorTypes, uint32_t>> inMappings) noexcept
{
for (auto& map : inMappings)
mappings.emplace(map);
}
SHDescriptorMappings::MapType const& SHDescriptorMappings::GetMappings(void) const noexcept
{
return mappings;
}
}

View File

@ -0,0 +1,29 @@
#pragma once
#include <unordered_map>
#include "Graphics/MiddleEnd/GlobalData/SHPredefinedDescriptorTypes.h"
namespace SHADE
{
class SHDescriptorMappings
{
public:
using MapType = std::unordered_map<SHPredefinedDescriptorTypes, uint32_t>;
private:
//! To map an enum value from descriptor set types to set indices
MapType mappings;
public:
/*-----------------------------------------------------------------------*/
/* PUBLIC MEMBER FUNCTIONS */
/*-----------------------------------------------------------------------*/
void AddMappings (std::initializer_list<std::pair<SHPredefinedDescriptorTypes, uint32_t>> inMappings) noexcept;
/*-----------------------------------------------------------------------*/
/* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/
MapType const& GetMappings (void) const noexcept;
};
}

View File

@ -0,0 +1,51 @@
#include "SHpch.h"
#include "SHGlobalDescriptorSets.h"
#include "Graphics/MiddleEnd/Lights/SHLightingSubSystem.h"
#include "Graphics/Commands/SHVkCommandBuffer.h"
namespace SHADE
{
Handle<SHVkDescriptorSetGroup> SHGlobalDescriptorSets::staticGlobalDataDescriptorSet;
Handle<SHLightingSubSystem> SHGlobalDescriptorSets::lightingSubSystem;
//void SHGlobalDescriptorSets::BindLightingData(Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t firstSet) noexcept
//{
// // Bind descriptor set for light data
// cmdBuffer->BindDescriptorSet(SHGlobalDescriptorSets::GetLightDescriptorSet(), SH_PIPELINE_TYPE::COMPUTE, descMappings[SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::LIGHTS], const std::span{ TEX_DYNAMIC_OFFSET.data(), 1 });
//}
void SHGlobalDescriptorSets::BindLightingData(Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex, uint32_t frameIndex) noexcept
{
lightingSubSystem->BindDescSet(cmdBuffer, setIndex, frameIndex);
}
void SHGlobalDescriptorSets::BindStaticGlobalData(Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex) noexcept
{
// Bind descriptor set for static global data
static std::array<uint32_t, 1> TEX_DYNAMIC_OFFSET{ 0 };
cmdBuffer->BindDescriptorSet(staticGlobalDataDescriptorSet, pipelineType, setIndex, std::span{ TEX_DYNAMIC_OFFSET.data(), 1 });
}
/***************************************************************************/
/*!
\brief
Sets the Handle to descriptor set for lights.
\param lightDescSet
The handle to set to.
*/
/***************************************************************************/
void SHGlobalDescriptorSets::SetLightingSubSystem(Handle<SHLightingSubSystem> system) noexcept
{
lightingSubSystem = system;
}
void SHGlobalDescriptorSets::SetStaticGlobalDataDescriptorSet(Handle<SHVkDescriptorSetGroup> staticGlobalDescSet) noexcept
{
staticGlobalDataDescriptorSet = staticGlobalDescSet;
}
}

View File

@ -0,0 +1,36 @@
#pragma once
#include "Graphics/Descriptors/SHVkDescriptorSetGroup.h"
#include "Resource/SHHandle.h"
#include "Graphics/Pipeline/SHPipelineType.h"
namespace SHADE
{
class SHLightingSubSystem;
class SHVkCommandBuffer;
// This class is mainly for descriptors that are truly global, meaning they only come from 1 place and they are shared between many systems
class SHGlobalDescriptorSets
{
private:
//! Static global descriptor sets for miscellaneous data and textures
static Handle<SHVkDescriptorSetGroup> staticGlobalDataDescriptorSet;
//! Lighting sub system required to get information to bind descriptor sets for light data
static Handle<SHLightingSubSystem> lightingSubSystem;
public:
/*-----------------------------------------------------------------------*/
/* PUBLIC MEMBER FUNCTIONS */
/*-----------------------------------------------------------------------*/
static void BindLightingData (Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex, uint32_t frameIndex) noexcept;
static void BindStaticGlobalData (Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex) noexcept;
/*-----------------------------------------------------------------------*/
/* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/
static void SetLightingSubSystem (Handle<SHLightingSubSystem> system) noexcept;
static void SetStaticGlobalDataDescriptorSet (Handle<SHVkDescriptorSetGroup> staticGlobalDescSet) noexcept;
};
}

View File

@ -1,143 +0,0 @@
#include "SHpch.h"
#include "SHGraphicsGlobalData.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/Pipeline/SHPipelineState.h"
#include "Graphics/Pipeline/SHVkPipelineLayout.h"
#include "Graphics/Descriptors/SHVkDescriptorSetLayout.h"
#include "Graphics/MiddleEnd/Lights/SHLightData.h"
#include "Tools/Utilities/SHUtilities.h"
namespace SHADE
{
/*-----------------------------------------------------------------------------------*/
/* Static Definitions */
/*-----------------------------------------------------------------------------------*/
std::vector<Handle<SHVkDescriptorSetLayout>> SHGraphicsGlobalData::globalDescSetLayouts;
SHVertexInputState SHGraphicsGlobalData::defaultVertexInputState;
Handle<SHVkPipelineLayout> SHGraphicsGlobalData::dummyPipelineLayout;
void SHGraphicsGlobalData::InitHighFrequencyGlobalData(void) noexcept
{
}
/*-----------------------------------------------------------------------------------*/
/* Function Definitions */
/*-----------------------------------------------------------------------------------*/
void SHGraphicsGlobalData::InitDescSetLayouts(Handle<SHVkLogicalDevice> logicalDevice) noexcept
{
SHVkDescriptorSetLayout::Binding genericDataBinding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::GENERIC_DATA,
.DescriptorCount = 1,
};
SHVkDescriptorSetLayout::Binding texturesBinding
{
.Type = vk::DescriptorType::eCombinedImageSampler,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::IMAGE_AND_SAMPLERS_DATA,
.DescriptorCount = 2000, // we can have up to 2000 textures for now
.flags = vk::DescriptorBindingFlagBits::eVariableDescriptorCount,
};
// For global data (generic data and textures)
Handle<SHVkDescriptorSetLayout> staticGlobalLayout = logicalDevice->CreateDescriptorSetLayout(SHGraphicsConstants::DescriptorSetIndex::STATIC_GLOBALS, { genericDataBinding, texturesBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, staticGlobalLayout->GetVkHandle(), "[Descriptor Set Layout] Static Globals");
std::vector<SHVkDescriptorSetLayout::Binding> lightBindings{};
// This is the binding we use to count the lights (binding 0)
lightBindings.push_back(SHVkDescriptorSetLayout::Binding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eCompute,
.BindPoint = 0,
.DescriptorCount = 1,
});
for (uint32_t i = 1; i <= SHUtilities::ConvertEnum(SH_LIGHT_TYPE::NUM_TYPES); ++i)
{
lightBindings.push_back (SHVkDescriptorSetLayout::Binding
{
.Type = vk::DescriptorType::eStorageBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eCompute,
.BindPoint = i,
.DescriptorCount = 1,
});
}
// For Dynamic global data (lights)
Handle<SHVkDescriptorSetLayout> dynamicGlobalLayout = logicalDevice->CreateDescriptorSetLayout(SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS, lightBindings);
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, dynamicGlobalLayout->GetVkHandle(), "[Descriptor Set Layout] Dynamic Globals");
// For High frequency global data (camera)
SHVkDescriptorSetLayout::Binding cameraDataBinding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA,
.DescriptorCount = 1,
};
Handle<SHVkDescriptorSetLayout> cameraDataGlobalLayout = logicalDevice->CreateDescriptorSetLayout(SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS, { cameraDataBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, cameraDataGlobalLayout->GetVkHandle(), "[Descriptor Set Layout] High Frequency Globals");
// For per instance data (transforms, materials, etc.)
SHVkDescriptorSetLayout::Binding materialDataBinding
{
.Type = vk::DescriptorType::eStorageBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eVertex,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
.DescriptorCount = 1,
};
Handle<SHVkDescriptorSetLayout> materialDataPerInstanceLayout = logicalDevice->CreateDescriptorSetLayout(SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE, { materialDataBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, materialDataPerInstanceLayout->GetVkHandle(), "[Descriptor Set Layout] Material Globals");
globalDescSetLayouts.push_back(staticGlobalLayout);
globalDescSetLayouts.push_back(dynamicGlobalLayout);
globalDescSetLayouts.push_back(cameraDataGlobalLayout);
globalDescSetLayouts.push_back(materialDataPerInstanceLayout);
dummyPipelineLayout = logicalDevice->CreatePipelineLayoutDummy(SHPipelineLayoutParamsDummy{globalDescSetLayouts});
}
void SHGraphicsGlobalData::InitDefaultVertexInputState(void) noexcept
{
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // positions at binding 0
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_2D) }); // UVs at binding 1
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // Normals at binding 2
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // Tangents at binding 3
defaultVertexInputState.AddBinding(true, true, { SHVertexAttribute(SHAttribFormat::MAT_4D) }); // Transform at binding 4 - 7 (4 slots)
defaultVertexInputState.AddBinding(true, true, { SHVertexAttribute(SHAttribFormat::UINT32_2D) }); // Instanced integer data at index 8
}
void SHGraphicsGlobalData::Init(Handle<SHVkLogicalDevice> logicalDevice) noexcept
{
InitDescSetLayouts(logicalDevice);
InitDefaultVertexInputState();
}
std::vector<Handle<SHVkDescriptorSetLayout>> const& SHGraphicsGlobalData::GetDescSetLayouts(void) noexcept
{
return globalDescSetLayouts;
}
SHVertexInputState const& SHGraphicsGlobalData::GetDefaultViState(void) noexcept
{
return defaultVertexInputState;
}
Handle<SHVkPipelineLayout> SHGraphicsGlobalData::GetDummyPipelineLayout(void) noexcept
{
return dummyPipelineLayout;
}
}

View File

@ -1,49 +0,0 @@
#pragma once
#include "SH_API.h"
#include "Graphics/Pipeline/SHPipelineState.h"
#include "Graphics/MiddleEnd/Interface/SHGraphicsConstants.h"
namespace SHADE
{
class SHVkLogicalDevice;
class SHVkDescriptorSetLayout;
class SHVkDescriptorSetGroup;
class SHVkPipelineLayout;
class SH_API SHGraphicsGlobalData
{
private:
//! Global descriptor set layouts. Used to allocate descriptor sets
static std::vector<Handle<SHVkDescriptorSetLayout>> globalDescSetLayouts;
//! Default vertex input state (used by everything).
static SHVertexInputState defaultVertexInputState;
//! Since we want to bind global data but can't do so without a pipeline layout,
//! we create a dummy pipeline layout to use it for binding.
static Handle<SHVkPipelineLayout> dummyPipelineLayout;
static void InitHighFrequencyGlobalData (void) noexcept;
static void InitDescSetLayouts (Handle<SHVkLogicalDevice> logicalDevice) noexcept;
static void InitDefaultVertexInputState (void) noexcept;
public:
/*-----------------------------------------------------------------------*/
/* Constructors */
/*-----------------------------------------------------------------------*/
SHGraphicsGlobalData() = delete;
/*-----------------------------------------------------------------------*/
/* PUBLIC MEMBER FUNCTIONS */
/*-----------------------------------------------------------------------*/
static void Init (Handle<SHVkLogicalDevice> logicalDevice) noexcept;
/*-----------------------------------------------------------------------*/
/* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/
static std::vector<Handle<SHVkDescriptorSetLayout>> const& GetDescSetLayouts (void) noexcept;
static SHVertexInputState const& GetDefaultViState (void) noexcept;
static Handle<SHVkPipelineLayout> GetDummyPipelineLayout (void) noexcept;
};
}

View File

@ -0,0 +1,256 @@
#include "SHpch.h"
#include "SHGraphicsPredefinedData.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/Pipeline/SHPipelineState.h"
#include "Graphics/Pipeline/SHVkPipelineLayout.h"
#include "Graphics/Descriptors/SHVkDescriptorSetLayout.h"
#include "Graphics/MiddleEnd/Lights/SHLightData.h"
namespace SHADE
{
/*-----------------------------------------------------------------------------------*/
/* Static Definitions */
/*-----------------------------------------------------------------------------------*/
std::vector<Handle<SHVkDescriptorSetLayout>> SHGraphicsPredefinedData::predefinedLayouts;
SHVertexInputState SHGraphicsPredefinedData::defaultVertexInputState;
std::vector<SHGraphicsPredefinedData::PerSystem> SHGraphicsPredefinedData::perSystemData;
//SHGraphicsPredefinedData::PerSystem SHGraphicsPredefinedData::batchingSystemData;
//SHGraphicsPredefinedData::PerSystem SHGraphicsPredefinedData::textSystemData;
//SHGraphicsPredefinedData::PerSystem SHGraphicsPredefinedData::renderGraphNodeComputeData;
void SHGraphicsPredefinedData::InitDescMappings(void) noexcept
{
perSystemData[SHUtilities::ConvertEnum(SystemType::BATCHING)].descMappings.AddMappings
({
{SHPredefinedDescriptorTypes::STATIC_DATA, 0},
{SHPredefinedDescriptorTypes::CAMERA, 1},
{SHPredefinedDescriptorTypes::MATERIALS, 2},
});
perSystemData[SHUtilities::ConvertEnum(SystemType::TEXT_RENDERING)].descMappings.AddMappings
({
{SHPredefinedDescriptorTypes::STATIC_DATA, 0},
{SHPredefinedDescriptorTypes::CAMERA, 1},
{SHPredefinedDescriptorTypes::FONT, 2},
});
perSystemData[SHUtilities::ConvertEnum(SystemType::RENDER_GRAPH_NODE_COMPUTE)].descMappings.AddMappings
({
{SHPredefinedDescriptorTypes::STATIC_DATA, 0},
{SHPredefinedDescriptorTypes::LIGHTS, 1},
{SHPredefinedDescriptorTypes::CAMERA, 2},
{SHPredefinedDescriptorTypes::RENDER_GRAPH_RESOURCE, 3},
{SHPredefinedDescriptorTypes::RENDER_GRAPH_NODE_COMPUTE_RESOURCE, 4},
});
}
void SHGraphicsPredefinedData::InitDummyPipelineLayouts(Handle<SHVkLogicalDevice> logicalDevice) noexcept
{
perSystemData[SHUtilities::ConvertEnum(SystemType::BATCHING)].dummyPipelineLayout = logicalDevice->CreatePipelineLayoutDummy(SHPipelineLayoutParamsDummy{ perSystemData[SHUtilities::ConvertEnum(SystemType::BATCHING)].descSetLayouts });
perSystemData[SHUtilities::ConvertEnum(SystemType::TEXT_RENDERING)].dummyPipelineLayout = logicalDevice->CreatePipelineLayoutDummy(SHPipelineLayoutParamsDummy{ perSystemData[SHUtilities::ConvertEnum(SystemType::TEXT_RENDERING)].descSetLayouts });
perSystemData[SHUtilities::ConvertEnum(SystemType::RENDER_GRAPH_NODE_COMPUTE)].dummyPipelineLayout = logicalDevice->CreatePipelineLayoutDummy(SHPipelineLayoutParamsDummy{ perSystemData[SHUtilities::ConvertEnum(SystemType::RENDER_GRAPH_NODE_COMPUTE)].descSetLayouts });
}
/*-----------------------------------------------------------------------------------*/
/* Function Definitions */
/*-----------------------------------------------------------------------------------*/
void SHGraphicsPredefinedData::InitDescSetLayouts(Handle<SHVkLogicalDevice> logicalDevice) noexcept
{
SHVkDescriptorSetLayout::Binding genericDataBinding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::GENERIC_DATA,
.DescriptorCount = 1,
};
SHVkDescriptorSetLayout::Binding texturesBinding
{
.Type = vk::DescriptorType::eCombinedImageSampler,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::IMAGE_AND_SAMPLERS_DATA,
.DescriptorCount = 2000, // we can have up to 2000 textures for now
.flags = vk::DescriptorBindingFlagBits::eVariableDescriptorCount,
};
// For global data (generic data and textures)
Handle<SHVkDescriptorSetLayout> staticGlobalLayout = logicalDevice->CreateDescriptorSetLayout({ genericDataBinding, texturesBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, staticGlobalLayout->GetVkHandle(), "[Descriptor Set Layout] Static Globals");
std::vector<SHVkDescriptorSetLayout::Binding> lightBindings{};
// This is the binding we use to count the lights (binding 0)
lightBindings.push_back(SHVkDescriptorSetLayout::Binding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eCompute,
.BindPoint = 0,
.DescriptorCount = 1,
});
for (uint32_t i = 1; i <= SHUtilities::ConvertEnum(SH_LIGHT_TYPE::NUM_TYPES); ++i)
{
lightBindings.push_back (SHVkDescriptorSetLayout::Binding
{
.Type = vk::DescriptorType::eStorageBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eCompute,
.BindPoint = i,
.DescriptorCount = 1,
});
}
// For Dynamic global data (lights)
Handle<SHVkDescriptorSetLayout> lightDataDescSetLayout = logicalDevice->CreateDescriptorSetLayout(lightBindings);
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, lightDataDescSetLayout->GetVkHandle(), "[Descriptor Set Layout] Dynamic Globals");
// For High frequency global data (camera)
SHVkDescriptorSetLayout::Binding cameraDataBinding
{
.Type = vk::DescriptorType::eUniformBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eVertex | vk::ShaderStageFlagBits::eCompute,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA,
.DescriptorCount = 1,
};
Handle<SHVkDescriptorSetLayout> cameraDataGlobalLayout = logicalDevice->CreateDescriptorSetLayout({ cameraDataBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, cameraDataGlobalLayout->GetVkHandle(), "[Descriptor Set Layout] High Frequency Globals");
// For per instance data (transforms, materials, etc.)
SHVkDescriptorSetLayout::Binding materialDataBinding
{
.Type = vk::DescriptorType::eStorageBufferDynamic,
.Stage = vk::ShaderStageFlagBits::eFragment | vk::ShaderStageFlagBits::eVertex,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
.DescriptorCount = 1,
};
Handle<SHVkDescriptorSetLayout> materialDataPerInstanceLayout = logicalDevice->CreateDescriptorSetLayout({ materialDataBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, materialDataPerInstanceLayout->GetVkHandle(), "[Descriptor Set Layout] Material Globals");
// font bitmap data (texture)
SHVkDescriptorSetLayout::Binding fontBitmapBinding
{
.Type = vk::DescriptorType::eCombinedImageSampler,
.Stage = vk::ShaderStageFlagBits::eFragment,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA,
.DescriptorCount = 1,
};
// font data in the form of matrices
SHVkDescriptorSetLayout::Binding fontMatrixBinding
{
.Type = vk::DescriptorType::eStorageBuffer,
.Stage = vk::ShaderStageFlagBits::eVertex,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::FONT_MATRIX_DATA,
.DescriptorCount = 1,
};
Handle<SHVkDescriptorSetLayout> fontDataDescSetLayout = logicalDevice->CreateDescriptorSetLayout({ fontBitmapBinding, fontMatrixBinding });
SET_VK_OBJ_NAME(logicalDevice, vk::ObjectType::eDescriptorSetLayout, fontDataDescSetLayout->GetVkHandle(), "[Descriptor Set Layout] Font Data");
predefinedLayouts.push_back(staticGlobalLayout);
predefinedLayouts.push_back(lightDataDescSetLayout);
predefinedLayouts.push_back(cameraDataGlobalLayout);
predefinedLayouts.push_back(materialDataPerInstanceLayout);
predefinedLayouts.push_back(fontDataDescSetLayout);
perSystemData[SHUtilities::ConvertEnum(SystemType::BATCHING)].descSetLayouts = GetPredefinedDescSetLayouts
(
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::STATIC_DATA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::CAMERA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::MATERIALS
);
perSystemData[SHUtilities::ConvertEnum(SystemType::TEXT_RENDERING)].descSetLayouts = GetPredefinedDescSetLayouts
(
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::STATIC_DATA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::CAMERA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::FONT
);
perSystemData[SHUtilities::ConvertEnum(SystemType::RENDER_GRAPH_NODE_COMPUTE)].descSetLayouts = GetPredefinedDescSetLayouts
(
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::STATIC_DATA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::CAMERA |
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::LIGHTS
);
}
void SHGraphicsPredefinedData::InitDefaultVertexInputState(void) noexcept
{
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // positions at binding 0
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_2D) }); // UVs at binding 1
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // Normals at binding 2
defaultVertexInputState.AddBinding(false, false, { SHVertexAttribute(SHAttribFormat::FLOAT_3D) }); // Tangents at binding 3
defaultVertexInputState.AddBinding(true, true, { SHVertexAttribute(SHAttribFormat::MAT_4D) }); // Transform at binding 4 - 7 (4 slots)
defaultVertexInputState.AddBinding(true, true, { SHVertexAttribute(SHAttribFormat::UINT32_2D) }); // Instanced integer data at index 8
}
void SHGraphicsPredefinedData::Init(Handle<SHVkLogicalDevice> logicalDevice) noexcept
{
perSystemData.resize(SHUtilities::ConvertEnum(SystemType::NUM_TYPES));
InitDescSetLayouts(logicalDevice);
InitDefaultVertexInputState();
InitDescMappings();
InitDummyPipelineLayouts (logicalDevice);
}
std::vector<Handle<SHVkDescriptorSetLayout>> SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes types) noexcept
{
std::vector<Handle<SHVkDescriptorSetLayout>> layoutsFound;
for (uint8_t i = 0; i < numPredefinedDescSetLayoutTypes; ++i)
{
auto result = types & static_cast<SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes>(static_cast<uint64_t>(1) << i);
if (static_cast<uint64_t>(result))
layoutsFound.push_back(predefinedLayouts[i]);
}
return layoutsFound;
}
SHVertexInputState const& SHGraphicsPredefinedData::GetDefaultViState(void) noexcept
{
return defaultVertexInputState;
}
SHGraphicsPredefinedData::PerSystem const& SHGraphicsPredefinedData::GetSystemData(SystemType systemType) noexcept
{
return perSystemData[static_cast<uint32_t>(systemType)];
}
SHDescriptorMappings::MapType const& SHGraphicsPredefinedData::GetMappings(SystemType systemType) noexcept
{
return perSystemData[static_cast<uint32_t>(systemType)].descMappings.GetMappings();
}
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes operator|(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes lhs, SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes rhs) noexcept
{
return static_cast<SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes>(static_cast<uint64_t>(lhs) | static_cast<uint64_t>(rhs));
}
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes operator&(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes lhs, SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes rhs) noexcept
{
return static_cast<SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes>(static_cast<uint64_t>(lhs) & static_cast<uint64_t>(rhs));
}
//SHGraphicsPredefinedData::PerSystem const& SHGraphicsPredefinedData::GetBatchingSystemData(void) noexcept
//{
// return batchingSystemData;
//}
//SHGraphicsPredefinedData::PerSystem const& SHGraphicsPredefinedData::GetTextSystemData(void) noexcept
//{
// return textSystemData;
//}
//SHGraphicsPredefinedData::PerSystem const& SHGraphicsPredefinedData::GetRenderGraphNodeComputeData(void) noexcept
//{
// return renderGraphNodeComputeData;
//}
}

View File

@ -0,0 +1,102 @@
#pragma once
#include "SH_API.h"
#include "Graphics/Pipeline/SHPipelineState.h"
#include "Graphics/MiddleEnd/Interface/SHGraphicsConstants.h"
#include "Graphics/MiddleEnd/GlobalData/SHDescriptorMappings.h"
#include "Tools/Utilities/SHUtilities.h"
#include "Tools/SHEnumWrapper.h"
#include <unordered_map>
namespace SHADE
{
class SHVkLogicalDevice;
class SHVkDescriptorSetLayout;
class SHVkDescriptorSetGroup;
class SHVkPipelineLayout;
class SH_API SHGraphicsPredefinedData
{
public:
static constexpr uint8_t numPredefinedDescSetLayoutTypes = 64;
// This enum is mainly to initialize a bit field to retrieve bit fields from SHPRedefinedData
enum class PredefinedDescSetLayoutTypes : uint64_t
{
STATIC_DATA = 0x01,
LIGHTS = 0x02,
CAMERA = 0x04,
MATERIALS = 0x08,
FONT = 0x10,
};
enum class SystemType
{
BATCHING = 0,
TEXT_RENDERING,
RENDER_GRAPH_NODE_COMPUTE,
NUM_TYPES
};
struct PerSystem
{
//! vector of descriptor set layouts used by a system
std::vector<Handle<SHVkDescriptorSetLayout>> descSetLayouts;
//! pipeline layout used for binding descriptor sets in the system
Handle<SHVkPipelineLayout> dummyPipelineLayout;
//! Descriptor type mappings for the system
SHDescriptorMappings descMappings;
};
private:
//! Global descriptor set layouts. Used to allocate descriptor sets
static std::vector<Handle<SHVkDescriptorSetLayout>> predefinedLayouts;
//! Default vertex input state (used by everything).
static SHVertexInputState defaultVertexInputState;
//! Predefined data for each type of system
static std::vector<PerSystem> perSystemData;
////! predefined data for the batching system
//static PerSystem batchingSystemData;
////! predefined data for the text system
//static PerSystem textSystemData;
////! predefined data for the render graph node computes
//static PerSystem renderGraphNodeComputeData;
static void InitDescMappings (void) noexcept;
static void InitDummyPipelineLayouts (Handle<SHVkLogicalDevice> logicalDevice) noexcept;
static void InitDescSetLayouts (Handle<SHVkLogicalDevice> logicalDevice) noexcept;
static void InitDefaultVertexInputState (void) noexcept;
public:
/*-----------------------------------------------------------------------*/
/* Constructors */
/*-----------------------------------------------------------------------*/
SHGraphicsPredefinedData() = delete;
/*-----------------------------------------------------------------------*/
/* PUBLIC MEMBER FUNCTIONS */
/*-----------------------------------------------------------------------*/
static void Init (Handle<SHVkLogicalDevice> logicalDevice) noexcept;
/*-----------------------------------------------------------------------*/
/* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/
static std::vector<Handle<SHVkDescriptorSetLayout>> GetPredefinedDescSetLayouts (SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes types) noexcept;
static SHVertexInputState const& GetDefaultViState (void) noexcept;
static PerSystem const& GetSystemData (SystemType systemType) noexcept;
static SHDescriptorMappings::MapType const& GetMappings (SystemType systemType) noexcept;
//static PerSystem const& GetBatchingSystemData(void) noexcept;
//static PerSystem const& GetTextSystemData(void) noexcept;
//static PerSystem const& GetRenderGraphNodeComputeData(void) noexcept;
};
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes operator| (SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes lhs, SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes rhs) noexcept;
SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes operator& (SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes lhs, SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes rhs) noexcept;
}

View File

@ -0,0 +1,19 @@
#pragma once
namespace SHADE
{
// This enum is different from PredefinedDescSetLayoutTypes in that it is used to initialize a hash table to
// with the values here as keys and set indices as values. It is worth noting that some values here
// are not in the above table. This is because those values don't have predefined descriptor set layouts.
// Their layouts and set indices are instead created through introspection in the pipeline layout.
enum class SHPredefinedDescriptorTypes
{
STATIC_DATA,
LIGHTS,
CAMERA,
MATERIALS,
FONT,
RENDER_GRAPH_RESOURCE,
RENDER_GRAPH_NODE_COMPUTE_RESOURCE,
};
}

View File

@ -99,10 +99,10 @@ namespace SHADE
createMeshBatches();
// Register function for subpass
auto const& RENDERERS = gfxSystem->GetDefaultViewport()->GetRenderers();
auto renderGraph = RENDERERS[SHGraphicsConstants::RenderGraphIndices::WORLD]->GetRenderGraph();
//auto const& RENDERERS = gfxSystem->GetDefaultViewport()->GetRenderers();
auto renderGraph = gfxSystem->GetRenderGraph();
auto subPass = renderGraph->GetNode("Debug Draw")->GetSubpass("Debug Draw");
subPass->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
subPass->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex)
{
const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex();
cmdBuffer->BeginLabeledSegment("SHDebugDraw (No Depth Test)");
@ -126,7 +126,7 @@ namespace SHADE
cmdBuffer->EndLabeledSegment();
});
auto subPassWithDepth = renderGraph->GetNode("Debug Draw with Depth")->GetSubpass("Debug Draw with Depth");
subPassWithDepth->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
subPassWithDepth->AddExteriorDrawCalls([this](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex)
{
const uint32_t FRAME_IDX = gfxSystem->GetCurrentFrameIndex();
cmdBuffer->BeginLabeledSegment("SHDebugDraw (Depth Tested)");

View File

@ -31,68 +31,68 @@ namespace SHADE
static constexpr uint32_t EDITOR = 0;
};
struct DescriptorSetIndex
{
/***************************************************************************/
/*!
\brief
DescriptorSet Index for static global values like generic data, and
texture samplers
*/
/***************************************************************************/
static constexpr uint32_t STATIC_GLOBALS = 0;
/***************************************************************************/
/*!
\brief
DescriptorSet Index for dynamic global values like lights.
*/
/***************************************************************************/
static constexpr uint32_t DYNAMIC_GLOBALS = 1;
/***************************************************************************/
/*!
\brief
DescriptorSet Index for high frequency changing global values like
camera matrices.
*/
/***************************************************************************/
static constexpr uint32_t HIGH_FREQUENCY_GLOBALS = 2;
/***************************************************************************/
/*!
\brief
DescriptorSet Index for per-instance/material changing values.
*/
/***************************************************************************/
static constexpr uint32_t PER_INSTANCE = 3;
/***************************************************************************/
/*!
\brief
DescriptorSet Index for render graph resources. Unlike the sets from
1 to 3 and 6, this set index does not have hard coded bindings and is
NOT part of the layouts included in the global data.
*/
/***************************************************************************/
static constexpr uint32_t RENDERGRAPH_RESOURCE = 4;
/***************************************************************************/
/*!
\brief
DescriptorSet Index for render graph node compute resources. For data
that we wish to pass to compute shaders in the render graph, this is
the set to use. Unlike the sets from 1 to 3 and 6, this set index does not have
hard coded bindings and is NOT part of the layouts included in the global
data.
*/
/***************************************************************************/
static constexpr uint32_t RENDERGRAPH_NODE_COMPUTE_RESOURCE = 5;
//struct DescriptorSetIndex
//{
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for static global values like generic data, and
// texture samplers
// */
// /***************************************************************************/
// static constexpr uint32_t STATIC_GLOBALS = 0;
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for dynamic global values like lights.
// */
// /***************************************************************************/
// static constexpr uint32_t DYNAMIC_GLOBALS = 1;
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for high frequency changing global values like
// camera matrices.
// */
// /***************************************************************************/
// static constexpr uint32_t HIGH_FREQUENCY_GLOBALS = 2;
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for per-instance/material changing values.
// */
// /***************************************************************************/
// static constexpr uint32_t PER_INSTANCE = 3;
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for render graph resources. Unlike the sets from
// 1 to 3 and 6, this set index does not have hard coded bindings and is
// NOT part of the layouts included in the global data.
// */
// /***************************************************************************/
// static constexpr uint32_t RENDERGRAPH_RESOURCE = 4;
// /***************************************************************************/
// /*!
// \brief
// DescriptorSet Index for render graph node compute resources. For data
// that we wish to pass to compute shaders in the render graph, this is
// the set to use. Unlike the sets from 1 to 3 and 6, this set index does not have
// hard coded bindings and is NOT part of the layouts included in the global
// data.
// */
// /***************************************************************************/
// static constexpr uint32_t RENDERGRAPH_NODE_COMPUTE_RESOURCE = 5;
/***************************************************************************/
/*!
\brief
To store font data.
*/
/***************************************************************************/
static constexpr uint32_t FONT_DATA = 4;
};
// /***************************************************************************/
// /*!
// \brief
// To store font data.
//
// */
// /***************************************************************************/
// static constexpr uint32_t FONT_DATA = 4;
//};
struct DescriptorSetBindings
{

View File

@ -19,7 +19,6 @@ of DigiPen Institute of Technology is prohibited.
#include "Camera/SHCameraSystem.h"
#include "Editor/SHEditor.h"
#include "ECS_Base/Managers/SHSystemManager.h"
//#include "SHRenderer.h"
#include "Graphics/Windowing/SHWindow.h"
#include "Graphics/MiddleEnd/PerFrame/SHPerFrameData.h"
#include "Graphics/MiddleEnd/Interface/SHViewport.h"
@ -31,7 +30,7 @@ of DigiPen Institute of Technology is prohibited.
#include "Graphics/MiddleEnd/Interface/SHRenderable.h"
#include "Graphics/MiddleEnd/Batching/SHSuperBatch.h"
#include "SHGraphicsConstants.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Graphics/Buffers/SHVkBuffer.h"
#include "Graphics/Images/SHVkSampler.h"
#include "Assets/Asset Types/SHTextureAsset.h"
@ -44,6 +43,7 @@ of DigiPen Institute of Technology is prohibited.
#include "../Meshes/SHPrimitiveGenerator.h"
#include "Graphics/MiddleEnd/TextRendering/SHFreetypeInstance.h"
#include "Graphics/MiddleEnd/TextRendering/SHTextRenderingSubSystem.h"
#include "Graphics/MiddleEnd/GlobalData/SHGlobalDescriptorSets.h"
namespace SHADE
{
@ -139,7 +139,7 @@ namespace SHADE
static constexpr AssetID RENDER_SC_FS = 36869006; renderToSwapchainFS = SHResourceManager::LoadOrGet<SHVkShaderModule>(RENDER_SC_FS);
}
void SHGraphicsSystem::InitSceneRenderGraph(void) noexcept
void SHGraphicsSystem::InitRenderGraph(void) noexcept
{
/*-----------------------------------------------------------------------*/
/* MIDDLE END SETUP
@ -153,60 +153,59 @@ namespace SHADE
auto windowDims = window->GetWindowSize();
auto cameraSystem = SHSystemManager::GetSystem<SHCameraSystem>();
// Set Up Cameras
screenCamera = resourceManager.Create<SHCamera>();
screenCamera->SetLookAt(SHVec3(0.0f, 0.0f, -1.0f), SHVec3(0.0f, 0.0f, 1.0f), SHVec3(0.0f, 1.0f, 0.0f));
screenCamera->SetOrthographic(static_cast<float>(windowDims.first), static_cast<float>(windowDims.second), 0.01f, 100.0f);
worldCamera = resourceManager.Create<SHCamera>();
worldCamera->SetLookAt(SHVec3(0.0f, 0.0f, 0.0f), SHVec3(0.0f, 0.0f, -2.0f), SHVec3(0.0f, 1.0f, 0.0f));
worldCamera->SetPerspective(90.0f, static_cast<float>(windowDims.first), static_cast<float>(windowDims.second), 0.0f, 100.0f);
worldCameraDirector = cameraSystem->CreateDirector();
/*-----------------------------------------------------------------------*/
/* PREPARE RENDERERS */
/*-----------------------------------------------------------------------*/
// Add world renderer to default viewport
worldRenderer = AddRenderer(SHRenderer::PROJECTION_TYPE::PERSPECTIVE);
worldRenderer->SetCameraDirector(worldCameraDirector);
// Add screen renderer to default viewport
screenRenderer = AddRenderer(SHRenderer::PROJECTION_TYPE::ORTHOGRAPHIC);
screenRenderer->SetCameraDirector(worldCameraDirector);
// Create Default Viewport
worldViewport = AddViewport(vk::Viewport(0.0f, 0.0f, static_cast<float>(window->GetWindowSize().first), static_cast<float>(window->GetWindowSize().second), 0.0f, 1.0f));
// Get render graph from default viewport world renderer
worldRenderGraph = resourceManager.Create<SHRenderGraph>();
std::vector<Handle<SHVkCommandPool>> renderContextCmdPools{ swapchain->GetNumImages() };
for (uint32_t i = 0; i < renderContextCmdPools.size(); ++i)
{
renderContextCmdPools[i] = renderContext.GetFrameData(i).cmdPoolHdls[0];
}
// Get render graph from default viewport world renderer
renderGraph = resourceManager.Create<SHRenderGraph>();
/*-----------------------------------------------------------------------*/
/* WORLD RENDER GRAPH RESOURCES */
/*-----------------------------------------------------------------------*/
// Initialize world render graph
worldRenderGraph->Init("World Render Graph", device, swapchain, &resourceManager);
worldRenderGraph->AddResource("Position", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32G32B32A32Sfloat);
worldRenderGraph->AddResource("Normals", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32G32B32A32Sfloat);
renderGraph->Init("World Render Graph", device, swapchain, &resourceManager, renderContextCmdPools);
renderGraph->AddResource("Position", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32G32B32A32Sfloat);
renderGraph->AddResource("Normals", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32G32B32A32Sfloat);
//worldRenderGraph->AddResource("Tangents", { SH_ATT_DESC_TYPE_FLAGS::COLOR, SH_ATT_DESC_TYPE_FLAGS::INPUT, SH_ATT_DESC_TYPE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32G32B32A32Sfloat);
worldRenderGraph->AddResource("Albedo", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second);
worldRenderGraph->AddResource("Depth Buffer", { SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH_STENCIL }, windowDims.first, windowDims.second, vk::Format::eD32SfloatS8Uint);
worldRenderGraph->AddResource("Entity ID", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::SHARED }, windowDims.first, windowDims.second, vk::Format::eR32Uint, 1, vk::ImageUsageFlagBits::eTransferSrc);
worldRenderGraph->AddResource("Light Layer Indices", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32Uint, 1, vk::ImageUsageFlagBits::eTransferSrc);
worldRenderGraph->AddResource("Scene", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE, SH_RENDER_GRAPH_RESOURCE_FLAGS::SHARED }, windowDims.first, windowDims.second);
worldRenderGraph->AddResource("SSAO", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR8Unorm);
worldRenderGraph->AddResource("SSAO Blur", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR8Unorm);
renderGraph->AddResource("Albedo", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second);
renderGraph->AddResource("Depth Buffer", { SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH_STENCIL }, windowDims.first, windowDims.second, vk::Format::eD32SfloatS8Uint);
renderGraph->AddResource("Entity ID", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::SHARED }, windowDims.first, windowDims.second, vk::Format::eR32Uint, 1, vk::ImageUsageFlagBits::eTransferSrc);
renderGraph->AddResource("Light Layer Indices", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR32Uint, 1, vk::ImageUsageFlagBits::eTransferSrc);
renderGraph->AddResource("Scene", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE, SH_RENDER_GRAPH_RESOURCE_FLAGS::SHARED }, windowDims.first, windowDims.second);
renderGraph->AddResource("SSAO", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR8Unorm);
renderGraph->AddResource("SSAO Blur", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR, SH_RENDER_GRAPH_RESOURCE_FLAGS::INPUT, SH_RENDER_GRAPH_RESOURCE_FLAGS::STORAGE }, windowDims.first, windowDims.second, vk::Format::eR8Unorm);
renderGraph->AddResource("Present", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR_PRESENT }, windowDims.first, windowDims.second);
/*-----------------------------------------------------------------------*/
/* MAIN NODE */
/*-----------------------------------------------------------------------*/
auto gBufferNode = worldRenderGraph->AddNode("G-Buffer",
auto gBufferNode = renderGraph->AddNode("G-Buffer",
{
"Position",
"Entity ID",
"Light Layer Indices",
"Normals",
//"Tangents",
"Albedo",
"Depth Buffer",
"Scene",
"SSAO",
"SSAO Blur"
},
@ -215,20 +214,21 @@ namespace SHADE
/*-----------------------------------------------------------------------*/
/* G-BUFFER SUBPASS INIT */
/*-----------------------------------------------------------------------*/
auto gBufferSubpass = gBufferNode->AddSubpass("G-Buffer Write");
auto gBufferSubpass = gBufferNode->AddSubpass("G-Buffer Write", worldViewport, worldRenderer);
gBufferSubpass->AddColorOutput("Position");
gBufferSubpass->AddColorOutput("Entity ID");
gBufferSubpass->AddColorOutput("Light Layer Indices");
gBufferSubpass->AddColorOutput("Normals");
//gBufferSubpass->AddColorOutput("Tangents");
gBufferSubpass->AddColorOutput("Albedo");
gBufferSubpass->AddDepthOutput("Depth Buffer", SH_RENDER_GRAPH_RESOURCE_FLAGS::DEPTH_STENCIL);
/*-----------------------------------------------------------------------*/
/* SSAO PASS AND DATA INIT */
/*-----------------------------------------------------------------------*/
ssaoStorage = resourceManager.Create<SHSSAO>();
// command buffer operation to transfer data for ssao
ssaoTransferCmdBuffer = graphicsCmdPool->RequestCommandBuffer(SH_CMD_BUFFER_TYPE::PRIMARY);
SET_VK_OBJ_NAME(device, vk::ObjectType::eCommandBuffer, ssaoTransferCmdBuffer->GetVkCommandBuffer(), "[Command Buffer] SSAO Pass (Graphics)");
ssaoTransferCmdBuffer->BeginRecording();
@ -237,95 +237,102 @@ namespace SHADE
ssaoTransferCmdBuffer->EndRecording();
graphicsQueue->SubmitCommandBuffer({ ssaoTransferCmdBuffer });
// Set up Debug Draw Passes
// - Depth Tested
auto debugDrawNodeDepth = worldRenderGraph->AddNode("Debug Draw with Depth", { "Scene", "Depth Buffer" }, {"G-Buffer"});
auto debugDrawDepthSubpass = debugDrawNodeDepth->AddSubpass("Debug Draw with Depth");
debugDrawDepthSubpass->AddColorOutput("Scene");
debugDrawDepthSubpass->AddDepthOutput("Depth Buffer");
// - No Depth Test
auto debugDrawNode = worldRenderGraph->AddNode("Debug Draw", { "Scene" }, { "Debug Draw with Depth" });
auto debugDrawSubpass = debugDrawNode->AddSubpass("Debug Draw");
debugDrawSubpass->AddColorOutput("Scene");
// wait for command buffer to finish executing
graphicsQueue->WaitIdle();
ssaoStorage->PrepareRotationVectorsVkData(device);
// Add the pass to generate an image with just SSAO data
Handle<SHRenderGraphNodeCompute> ssaoPass = gBufferNode->AddNodeCompute("SSAO", ssaoShader, { "Position", "Normals", "SSAO" });
auto ssaoDataBuffer = ssaoStorage->GetBuffer();
ssaoPass->ModifyWriteDescBufferComputeResource(SHGraphicsConstants::DescriptorSetIndex::RENDERGRAPH_NODE_COMPUTE_RESOURCE, SHSSAO::DESC_SET_BUFFER_BINDING, { &ssaoDataBuffer, 1 }, 0, ssaoStorage->GetBuffer()->GetSizeStored());
ssaoPass->ModifyWriteDescBufferComputeResource(SHSSAO::DESC_SET_BUFFER_BINDING, { &ssaoDataBuffer, 1 }, 0, ssaoStorage->GetBuffer()->GetSizeStored());
auto viewSamplerLayout = ssaoStorage->GetViewSamplerLayout();
ssaoPass->ModifyWriteDescImageComputeResource(SHGraphicsConstants::DescriptorSetIndex::RENDERGRAPH_NODE_COMPUTE_RESOURCE, SHSSAO::DESC_SET_IMAGE_BINDING, {&viewSamplerLayout, 1});
ssaoPass->ModifyWriteDescImageComputeResource(SHSSAO::DESC_SET_IMAGE_BINDING, { &viewSamplerLayout, 1 });
ssaoPass->SetRenderer(worldRenderer);
// Add another pass to blur SSAO
Handle<SHRenderGraphNodeCompute> ssaoBlurPass = gBufferNode->AddNodeCompute("SSAO Blur Step", ssaoBlurShader, { "SSAO", "SSAO Blur" });
/*-----------------------------------------------------------------------*/
/* SHADOW MAP PASS */
/*-----------------------------------------------------------------------*/
// Shadow map pass will have no resources bound at first. Lighting system will add resources to the node.
// It will initially also not have any subpasses since they will be added for each light that casts shadows.
//auto shadowMapPass = renderGraph->AddNode("Shadow Map Pass", {}, {});
Handle<SHRenderGraphNodeCompute> ssaoBlurPass = gBufferNode->AddNodeCompute("SSAO Blur Step", ssaoBlurShader, {"SSAO", "SSAO Blur"});
/*-----------------------------------------------------------------------*/
/* DEFERRED COMPOSITE NODE */
/*-----------------------------------------------------------------------*/
// This pass will facilitate both lighting and shadows in 1 single pass.
auto deferredCompositeNode = renderGraph->AddNode("Deferred Comp Pass",
{
"Position",
"Light Layer Indices",
"Normals",
"Albedo",
"Scene",
"SSAO Blur"
},
{"G-Buffer"});
/*-----------------------------------------------------------------------*/
/* DEFERRED COMPOSITE SUBPASS INIT */
/*-----------------------------------------------------------------------*/
gBufferNode->AddNodeCompute("Deferred Composite", deferredCompositeShader, {"Position", "Normals", "Albedo", "Light Layer Indices", "SSAO Blur", "Scene"});
{
//// Dummy Node to transition scene render graph resource
//auto dummyNode = worldRenderGraph->AddNode("Dummy Pass", { "Scene" }, { "Debug Draw" }); // no predecessors
//auto dummySubpass = dummyNode->AddSubpass("Dummy Subpass");
//dummySubpass->AddInput("Scene");
}
deferredCompositeNode->AddNodeCompute("Deferred Composite", deferredCompositeShader, { "Position", "Normals", "Albedo", "Light Layer Indices", "SSAO Blur", "Scene" });
/*-----------------------------------------------------------------------*/
/* GENERATE WORLD RENDER GRAPH */
/* DEBUG DRAW PASS INIT */
/*-----------------------------------------------------------------------*/
// Generate world render graph
worldRenderGraph->Generate();
// Set up Debug Draw Passes
// - Depth Tested
auto debugDrawNodeDepth = renderGraph->AddNode("Debug Draw with Depth", { "Scene", "Depth Buffer" }, {"G-Buffer", "Deferred Comp Pass"});
auto debugDrawDepthSubpass = debugDrawNodeDepth->AddSubpass("Debug Draw with Depth", worldViewport, worldRenderer);
debugDrawDepthSubpass->AddColorOutput("Scene");
debugDrawDepthSubpass->AddDepthOutput("Depth Buffer");
// - No Depth Test
auto debugDrawNode = renderGraph->AddNode("Debug Draw", { "Scene" }, { "Debug Draw with Depth" });
auto debugDrawSubpass = debugDrawNode->AddSubpass("Debug Draw", worldViewport, worldRenderer);
debugDrawSubpass->AddColorOutput("Scene");
/*-----------------------------------------------------------------------*/
/* SCREEN RENDER GRAPH */
/* SCREEN SPACE PASS */
/*-----------------------------------------------------------------------*/
// Initialize screen render graph
screenRenderGraph = resourceManager.Create<SHRenderGraph>();
screenRenderGraph->Init("Screen Render Graph", device, swapchain, &resourceManager);
screenRenderGraph->LinkNonOwningResource(worldRenderGraph, "Scene");
screenRenderGraph->LinkNonOwningResource(worldRenderGraph, "Entity ID");
screenRenderGraph->AddResource("Present", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR_PRESENT }, windowDims.first, windowDims.second);
auto screenSpaceNode = screenRenderGraph->AddNode("Screen Space Pass", { "Scene", "Entity ID"}, {});
auto uiSubpass = screenSpaceNode->AddSubpass("UI");
auto screenSpaceNode = renderGraph->AddNode("Screen Space Pass", { "Scene", "Entity ID" }, {"Deferred Comp Pass", "G-Buffer", "Debug Draw" });
auto uiSubpass = screenSpaceNode->AddSubpass("UI", worldViewport, screenRenderer);
uiSubpass->AddColorOutput("Scene");
uiSubpass->AddColorOutput("Entity ID");
uiSubpass->AddExteriorDrawCalls([=](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
uiSubpass->AddExteriorDrawCalls([=](Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex)
{
textRenderingSubSystem->Render(cmdBuffer, frameIndex);
textRenderingSubSystem->Render(cmdBuffer, renderer, frameIndex);
});
/*-----------------------------------------------------------------------*/
/* RENDER TO SWAPCHAIN IMAGE FOR PRESENT PASS */
/*-----------------------------------------------------------------------*/
#ifdef SHEDITOR
{
// Dummy Node to transition scene render graph resource
auto dummyNode = screenRenderGraph->AddNode("Dummy Pass", { "Scene" }, { "Screen Space Pass" }); // no predecessors
auto dummySubpass = dummyNode->AddSubpass("Dummy Subpass");
auto dummyNode = renderGraph->AddNode("Dummy Pass", { "Scene" }, { "Screen Space Pass" });
auto dummySubpass = dummyNode->AddSubpass("Dummy Subpass", {}, {});
dummySubpass->AddInput("Scene");
}
auto imGuiNode = renderGraph->AddNode("ImGui Node", { "Present" }, {});
auto imGuiSubpass = imGuiNode->AddSubpass("ImGui Draw", {}, {});
imGuiSubpass->AddColorOutput("Present");
}
#else
screenRenderGraph->AddRenderToSwapchainNode("Scene", "Present", {"Screen Space Pass"}, {renderToSwapchainVS, renderToSwapchainFS});
renderGraph->AddRenderToSwapchainNode("Scene", "Present", { "Screen Space Pass" }, { renderToSwapchainVS, renderToSwapchainFS });
#endif
screenRenderGraph->Generate();
/*-----------------------------------------------------------------------*/
/* BIND RENDER GRAPH TO RENDERER */
/* GENERATE RENDER GRAPH */
/*-----------------------------------------------------------------------*/
// Add world renderer to default viewport
worldRenderer = worldViewport->AddRenderer(resourceManager, swapchain->GetNumImages(), renderContextCmdPools, descPool, SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS], worldRenderGraph);
worldRenderer->SetCamera(worldCamera);
worldRenderer->SetCameraDirector(worldCameraDirector);
// Add screen renderer to default viewport
screenRenderer = worldViewport->AddRenderer(resourceManager, swapchain->GetNumImages(), renderContextCmdPools, descPool, SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS], screenRenderGraph);
screenRenderer->SetCamera(screenCamera);
screenRenderer->SetCameraDirector(worldCameraDirector);
// Generate render graph
renderGraph->Generate();
// Create debug draw pipeline
debugDrawPipeline = createDebugDrawPipeline(debugDrawNode->GetRenderpass(), debugDrawSubpass, false, false, false);
@ -356,13 +363,10 @@ namespace SHADE
void SHGraphicsSystem::InitMiddleEnd(void) noexcept
{
SHGraphicsGlobalData::Init(device);
SHGraphicsPredefinedData::Init(device);
InitSceneRenderGraph();
InitRenderGraph();
#ifdef SHEDITOR
InitEditorRenderGraph();
#endif
// Create Semaphore
for (auto& semaHandle : graphSemaphores)
@ -374,7 +378,7 @@ namespace SHADE
void SHGraphicsSystem::InitSubsystems(void) noexcept
{
mousePickSystem = resourceManager.Create<SHMousePickSystem>();
mousePickSubSystem = resourceManager.Create<SHMousePickSystem>();
std::vector<Handle<SHVkCommandPool>> cmdPools;
cmdPools.reserve(swapchain->GetNumImages());
@ -382,11 +386,11 @@ namespace SHADE
cmdPools.push_back(renderContext.GetFrameData(i).cmdPoolHdls[0]);
// Mouse picking system for the editor (Will still run with editor disabled)
mousePickSystem->Init(device, cmdPools, worldRenderGraph->GetRenderGraphResource("Entity ID"));
mousePickSubSystem->Init(device, cmdPools, renderGraph->GetRenderGraphResource("Entity ID"));
// Register the post offscreen render to the system
postOffscreenRender = resourceManager.Create<SHPostOffscreenRenderSystem>();
postOffscreenRender->Init(device, worldRenderGraph->GetRenderGraphResource("Scene"), descPool);
postOffscreenRenderSubSystem = resourceManager.Create<SHPostOffscreenRenderSystem>();
postOffscreenRenderSubSystem->Init(device, renderGraph->GetRenderGraphResource("Scene"), descPool);
lightingSubSystem = resourceManager.Create<SHLightingSubSystem>();
lightingSubSystem->Init(device, descPool);
@ -394,11 +398,10 @@ namespace SHADE
textRenderingSubSystem = resourceManager.Create<SHTextRenderingSubSystem>();
// initialize the text renderer
auto uiNode = screenRenderGraph->GetNode("Screen Space Pass");
textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS, [=](Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex)
{
screenRenderer->BindDescSet(cmdBuffer, frameIndex);
});
auto uiNode = renderGraph->GetNode("Screen Space Pass");
textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS);
SHGlobalDescriptorSets::SetLightingSubSystem(lightingSubSystem);
}
@ -422,42 +425,21 @@ namespace SHADE
defaultMaterial = AddMaterial
(
defaultVertShader, defaultFragShader,
worldRenderGraph->GetNode("G-Buffer")->GetSubpass("G-Buffer Write")
renderGraph->GetNode("G-Buffer")->GetSubpass("G-Buffer Write")
);
defaultMaterial->SetProperty("data.textureIndex", defaultTexture->TextureArrayIndex);
}
#ifdef SHEDITOR
void SHGraphicsSystem::InitEditorRenderGraph(void) noexcept
void SHGraphicsSystem::InitEvents(void) noexcept
{
auto windowDims = window->GetWindowSize();
// Create Default Viewport
editorViewport = AddViewport(vk::Viewport(0.0f, 0.0f, static_cast<float>(windowDims.first), static_cast<float>(windowDims.second), 0.0f, 1.0f));
// Get render graph from viewport editor renderer
editorRenderGraph = resourceManager.Create<SHRenderGraph>();
std::vector<Handle<SHVkCommandPool>> renderContextCmdPools{ swapchain->GetNumImages() };
for (uint32_t i = 0; i < renderContextCmdPools.size(); ++i)
renderContextCmdPools[i] = renderContext.GetFrameData(i).cmdPoolHdls[0];
editorRenderGraph->Init("Editor Render Graph", device, swapchain, &resourceManager);
editorRenderGraph->AddResource("Present", { SH_RENDER_GRAPH_RESOURCE_FLAGS::COLOR_PRESENT }, windowDims.first, windowDims.second);
auto imguiNode = editorRenderGraph->AddNode("ImGui Node", { "Present"}, {});
auto imguiSubpass = imguiNode->AddSubpass("ImGui Draw");
imguiSubpass->AddColorOutput("Present");
// Generate world render graph
editorRenderGraph->Generate();
// Add world renderer to default viewport
editorRenderer = editorViewport->AddRenderer(resourceManager, swapchain->GetNumImages(), renderContextCmdPools, descPool, SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS], editorRenderGraph);
editorRenderer->SetCamera(worldCamera);
std::shared_ptr<SHEventReceiverSpec<SHGraphicsSystem>> thisReceiver
{
std::make_shared<SHEventReceiverSpec<SHGraphicsSystem>>(this, &SHGraphicsSystem::ReceiveLightEnableShadowEvent)
};
ReceiverPtr receiver = std::dynamic_pointer_cast<SHEventReceiver>(thisReceiver);
SHEventManager::SubscribeTo(SH_GRAPHICS_LIGHT_ENABLE_SHADOW_EVENT, receiver);
}
#endif
/*---------------------------------------------------------------------------------*/
/* Constructor/Destructors */
@ -546,104 +528,52 @@ namespace SHADE
textRenderingSubSystem->Run(frameIndex);
// For every viewport
for (int vpIndex = 0; vpIndex < static_cast<int>(viewports.size()); ++vpIndex)
for (auto renderer : renderers)
{
auto& renderers = viewports[vpIndex]->GetRenderers();
// For every renderer
for (int renIndex = 0; renIndex < static_cast<int>(renderers.size()); ++renIndex)
{
/*-----------------------------------------------------------------------*/
/* Renderer start */
/*-----------------------------------------------------------------------*/
// get command buffer of the renderer in the current frame
auto currentCmdBuffer = renderers[renIndex]->GetCommandBuffer(frameIndex);
// Begin recording the command buffer
currentCmdBuffer->BeginRecording();
// set viewport and scissor
uint32_t w = static_cast<uint32_t>(viewports[vpIndex]->GetWidth());
uint32_t h = static_cast<uint32_t>(viewports[vpIndex]->GetHeight());
currentCmdBuffer->SetViewportScissor (static_cast<float>(w), static_cast<float>(h), w, h);
// Force set the pipeline layout
currentCmdBuffer->ForceSetPipelineLayout(SHGraphicsGlobalData::GetDummyPipelineLayout(), SH_PIPELINE_TYPE::GRAPHICS);
currentCmdBuffer->ForceSetPipelineLayout(SHGraphicsGlobalData::GetDummyPipelineLayout(), SH_PIPELINE_TYPE::COMPUTE);
// Bind all the buffers required for meshes
for (auto& [buffer, bindingPoint] : MESH_DATA)
{
// Ignore invalid buffers
if (!buffer)
continue;
// Assign based on type
if (buffer->GetUsageBits() & vk::BufferUsageFlagBits::eVertexBuffer)
currentCmdBuffer->BindVertexBuffer(bindingPoint, buffer, 0);
else if (buffer->GetUsageBits() & vk::BufferUsageFlagBits::eIndexBuffer)
currentCmdBuffer->BindIndexBuffer(buffer, 0);
}
lightingSubSystem->BindDescSet(currentCmdBuffer, frameIndex);
// Bind textures
auto textureDescSet = texLibrary.GetTextureDescriptorSetGroup();
if (textureDescSet)
{
std::array<uint32_t, 1> texDynamicOffset {0};
currentCmdBuffer->BindDescriptorSet
(
textureDescSet,
SH_PIPELINE_TYPE::GRAPHICS,
0,
texDynamicOffset
);
}
// bind camera data
//renderers[renIndex]->UpdateDataAndBind(currentCmdBuffer, frameIndex);
#ifdef SHEDITOR
if (renderers[renIndex] == worldRenderer)
{
auto editorSystem = SHSystemManager::GetSystem<SHEditor>();
if (editorSystem->editorState != SHEditor::State::PLAY)
worldRenderer->UpdateDataAndBind(currentCmdBuffer, frameIndex, cameraSystem->GetEditorCamera()->GetViewMatrix(), cameraSystem->GetEditorCamera()->GetProjMatrix(), cameraSystem->GetEditorCamera()->GetOrthoMatrix());
else
renderers[renIndex]->UpdateDataAndBind(currentCmdBuffer, frameIndex);
}
if (renderer == worldRenderer)
{
auto editorSystem = SHSystemManager::GetSystem<SHEditor>();
if (editorSystem->editorState != SHEditor::State::PLAY)
worldRenderer->UpdateDataManual(frameIndex, cameraSystem->GetEditorCamera()->GetViewMatrix(), cameraSystem->GetEditorCamera()->GetProjMatrix());
else
renderers[renIndex]->UpdateDataAndBind(currentCmdBuffer, frameIndex);
#else
renderers[renIndex]->UpdateDataAndBind(currentCmdBuffer, frameIndex);
#endif
// Draw the scene
renderers[renIndex]->Draw(frameIndex, descPool);
// End the command buffer recording
currentCmdBuffer->EndRecording();
/*-----------------------------------------------------------------------*/
/* Renderer end */
/*-----------------------------------------------------------------------*/
// submit a command buffer from the current render graph and make it wait for the previous render graph before submitting it to GPU.
graphicsQueue->SubmitCommandBuffer
(
{ currentCmdBuffer },
{ (vpIndex == viewports.size() - 1 && renIndex == renderers.size() - 1) ? frameData.semRenderFinishHdl : graphSemaphores[!semIndex] },
{ (vpIndex == 0 && renIndex == 0) ? frameData.semImgAvailableHdl : graphSemaphores[semIndex] },
{ vk::PipelineStageFlagBits::eColorAttachmentOutput },
{ (vpIndex == viewports.size() - 1 && renIndex == renderers.size() - 1) ? frameData.fenceHdl : Handle<SHVkFence>{} }
);
semIndex = !semIndex;
renderer->UpdateData(frameIndex);
}
else
renderer->UpdateData(frameIndex);
#else
renderers[renIndex]->UpdateDataAndBind(frameIndex);
#endif
}
renderGraph->Begin(frameIndex);
auto cmdBuffer = renderGraph->GetCommandBuffer(frameIndex);
// Bind all the buffers required for meshes
for (auto& [buffer, bindingPoint] : MESH_DATA)
{
if (buffer->GetUsageBits() & vk::BufferUsageFlagBits::eVertexBuffer)
cmdBuffer->BindVertexBuffer(bindingPoint, buffer, 0);
else if (buffer->GetUsageBits() & vk::BufferUsageFlagBits::eIndexBuffer)
cmdBuffer->BindIndexBuffer(buffer, 0);
}
renderGraph->Execute(frameIndex, descPool);
renderGraph->End(frameIndex);
graphicsQueue->SubmitCommandBuffer
(
{ renderGraph->GetCommandBuffer(frameIndex) },
{ frameData.semRenderFinishHdl },
{ frameData.semImgAvailableHdl },
{ vk::PipelineStageFlagBits::eColorAttachmentOutput },
{ frameData.fenceHdl }
);
}
/***************************************************************************/
/*!
@ -681,12 +611,8 @@ namespace SHADE
// #BackEndTest: For for the fence initialized by queue submit
renderContext.WaitForFence();
// Finalise all batches
for (auto vp : viewports)
for (auto renderer : vp->GetRenderers())
{
renderer->GetRenderGraph()->FinaliseBatch(renderContext.GetCurrentFrame(), descPool);
}
// finalize batches for render graph
renderGraph->FinaliseBatch(renderContext.GetCurrentFrame(), descPool);
// #BackEndTest: Acquire the next image in the swapchain available
renderContext.AcquireNextIamge();
@ -727,7 +653,7 @@ namespace SHADE
const uint32_t CURR_FRAME_IDX = renderContext.GetCurrentFrame();
auto& currFrameData = renderContext.GetCurrentFrameData();
mousePickSystem->Run(graphicsQueue, CURR_FRAME_IDX);
mousePickSubSystem->Run(graphicsQueue, CURR_FRAME_IDX);
// #BackEndTest: queues an image for presentation
if (auto result = graphicsQueue->Present(swapchain, { currFrameData.semRenderFinishHdl }, CURR_FRAME_IDX); result != vk::Result::eSuccess)
@ -767,6 +693,52 @@ namespace SHADE
viewports.erase(iter);
}
/*---------------------------------------------------------------------------------*/
/* Renderer Registration Functions */
/*---------------------------------------------------------------------------------*/
Handle<SHRenderer> SHGraphicsSystem::AddRenderer(SHRenderer::PROJECTION_TYPE projectionType)
{
std::vector<Handle<SHVkCommandPool>> renderContextCmdPools{ swapchain->GetNumImages() };
for (uint32_t i = 0; i < renderContextCmdPools.size(); ++i)
{
renderContextCmdPools[i] = renderContext.GetFrameData(i).cmdPoolHdls[0];
}
// Create the renderer
auto renderer = resourceManager.Create<SHRenderer>(device, swapchain->GetNumImages(), descPool, projectionType);
// Store
renderers.emplace_back(renderer);
// Return
return renderer;
}
void SHGraphicsSystem::RemoveRenderer(Handle<SHRenderer> renderer)
{
auto iter = std::find(renderers.begin(), renderers.end(), renderer);
if (iter == renderers.end())
{
SHLOG_WARNING("Attempted to remove a Renderer that does not belong to a viewport!");
return;
}
// Remove it
iter->Free();
renderers.erase(iter);
}
SHEventHandle SHGraphicsSystem::ReceiveLightEnableShadowEvent(SHEventPtr event) noexcept
{
// Add the shadow map resource to the graph
// link resource to node. This means linking the resource and regenerating the node's renderpass and framebuffer.
// Add a subpass to render to that shadow map
//renderGraph->GetNode ();
return event->handle;
}
Handle<SHMaterial> SHGraphicsSystem::AddMaterial(Handle<SHVkShaderModule> vertShader, Handle<SHVkShaderModule> fragShader, Handle<SHSubpass> subpass)
{
// Retrieve pipeline from pipeline storage or create if unavailable
@ -890,6 +862,8 @@ namespace SHADE
);
device->WaitIdle();
graphicsTexCmdBuffer.Free(); graphicsTexCmdBuffer = {};
SHGlobalDescriptorSets::SetStaticGlobalDataDescriptorSet(texLibrary.GetTextureDescriptorSetGroup());
}
Handle<SHTexture> SHGraphicsSystem::GetTextureHandle(SHTexture::Index textureId) const
@ -907,7 +881,7 @@ namespace SHADE
void SHGraphicsSystem::BuildFonts(void) noexcept
{
fontLibrary.BuildFonts(device, graphicsQueue, graphicsCmdPool, descPool, textRenderingSubSystem->GetFontDataDescSetLayout(), resourceManager);
fontLibrary.BuildFonts(device, graphicsQueue, graphicsCmdPool, descPool, SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::FONT)[0], resourceManager);
}
#pragma endregion ADD_REMOVE
@ -1051,6 +1025,10 @@ namespace SHADE
graphSemaphores[0].Free();
graphSemaphores[1].Free();
for (auto& semaHandle : graphSemaphores)
semaHandle = device->CreateSemaphore();
auto windowDims = window->GetWindowSize();
// Resize the swapchain
@ -1058,23 +1036,21 @@ namespace SHADE
renderContext.HandleResize();
worldRenderGraph->HandleResize(resizeWidth, resizeHeight);
renderGraph->HandleResize(resizeWidth, resizeHeight);
#ifdef SHEDITOR
editorRenderGraph->HandleResize(windowDims.first, windowDims.second);
// NOTE: These 2 lines are actually not necessary because the editor viewport is not even used for
// setting dynamic viewport or scissor state. ImGUI takes care of that for us.
//editorViewport->SetWidth(windowDims.first);
//editorViewport->SetHeight(windowDims.second);
#endif
screenRenderGraph->HandleResize(resizeWidth, resizeHeight);
mousePickSystem->HandleResize();
postOffscreenRender->HandleResize();
mousePickSubSystem->HandleResize();
postOffscreenRenderSubSystem->HandleResize();
worldViewport->SetWidth(static_cast<float>(resizeWidth));
worldViewport->SetHeight(static_cast<float>(resizeHeight));
//worldCamera->SetPerspective(90.0f, static_cast<float>(resizeWidth), static_cast<float>(resizeHeight), 0.0f, 100.0f);
//screenCamera->SetOrthographic(static_cast<float>(resizeWidth), static_cast<float>(resizeHeight), 0.01f, 100.0f);
auto cameraSystem = SHSystemManager::GetSystem<SHCameraSystem>();
#ifdef SHEDITOR
cameraSystem->GetEditorCamera()->SetWidth(static_cast<float>(resizeWidth));
@ -1083,8 +1059,6 @@ namespace SHADE
#endif
for (auto& semaHandle : graphSemaphores)
semaHandle = device->CreateSemaphore();
}
void SHGraphicsSystem::AwaitGraphicsExecution()
@ -1098,9 +1072,14 @@ namespace SHADE
}
Handle<SHRenderGraph> SHGraphicsSystem::GetRenderGraph(void) const noexcept
{
return renderGraph;
}
Handle<SHRenderGraphNode> SHGraphicsSystem::GetPrimaryRenderpass() const noexcept
{
return worldRenderGraph->GetNode(G_BUFFER_RENDER_GRAPH_NODE_NAME.data());
return renderGraph->GetNode(G_BUFFER_RENDER_GRAPH_NODE_NAME.data());
}
Handle<SHVkPipeline> SHGraphicsSystem::GetDebugDrawPipeline(DebugDrawPipelineType type) const noexcept
@ -1133,7 +1112,7 @@ namespace SHADE
device, SHPipelineLayoutParams
{
.shaderModules = { (instanced ? debugMeshVertShader : debugVertShader) , debugFragShader },
.globalDescSetLayouts = SHGraphicsGlobalData::GetDescSetLayouts()
.predefinedDescSetLayouts = SHGraphicsPredefinedData::GetSystemData(SHGraphicsPredefinedData::SystemType::BATCHING).descSetLayouts
}
);
auto pipeline = resourceManager.Create<SHVkPipeline>(device, pipelineLayout, nullptr, renderPass, subpass);

View File

@ -34,6 +34,8 @@ of DigiPen Institute of Technology is prohibited.
#include "Graphics/MiddleEnd/PostProcessing/SHSSAO.h"
#include "Camera/SHCameraDirector.h"
#include "Graphics/MiddleEnd/TextRendering/SHFontLibrary.h"
#include "Graphics/MiddleEnd/Interface/SHRenderer.h"
#include "Graphics/Events/SHGraphicsEvents.h"
namespace SHADE
{
@ -49,9 +51,7 @@ namespace SHADE
class SHVkImage;
class SHVkFramebuffer;
class SHVkCommandBuffer;
class SHRenderer;
class SHViewport;
class SHCamera;
class SHVkShaderModule;
class SHMaterial;
class SHMaterialInstance;
@ -99,14 +99,11 @@ namespace SHADE
{
private:
void InitBoilerplate (void) noexcept;
void InitSceneRenderGraph (void) noexcept;
void InitRenderGraph (void) noexcept;
void InitMiddleEnd (void) noexcept;
void InitSubsystems (void) noexcept;
void InitBuiltInResources (void);
#ifdef SHEDITOR
void InitEditorRenderGraph (void) noexcept;
#endif
void InitEvents (void) noexcept;
public:
class SH_API BeginRoutine final : public SHSystemRoutine
@ -171,6 +168,17 @@ namespace SHADE
Handle<SHViewport> AddViewport(const vk::Viewport& viewport);
void RemoveViewport(Handle<SHViewport> viewport);
/*-----------------------------------------------------------------------------*/
/* Renderers Registration Functions */
/*-----------------------------------------------------------------------------*/
Handle<SHRenderer> AddRenderer(SHRenderer::PROJECTION_TYPE projectionType);
void RemoveRenderer(Handle<SHRenderer> renderer);
/*-----------------------------------------------------------------------*/
/* Light functions */
/*-----------------------------------------------------------------------*/
SHEventHandle ReceiveLightEnableShadowEvent (SHEventPtr event) noexcept;
/*-----------------------------------------------------------------------------*/
/* Material Functions */
/*-----------------------------------------------------------------------------*/
@ -382,8 +390,9 @@ namespace SHADE
#ifdef SHEDITOR
Handle<SHViewport> GetEditorViewport () const {return editorViewport;};
#endif
Handle<SHMousePickSystem> GetMousePickSystem(void) const noexcept {return mousePickSystem;};
Handle<SHPostOffscreenRenderSystem> GetPostOffscreenRenderSystem(void) const noexcept {return postOffscreenRender;};
Handle<SHMousePickSystem> GetMousePickSystem(void) const noexcept {return mousePickSubSystem;};
Handle<SHPostOffscreenRenderSystem> GetPostOffscreenRenderSystem(void) const noexcept {return postOffscreenRenderSubSystem;};
Handle<SHRenderGraph> GetRenderGraph (void) const noexcept;
Handle<SHRenderGraphNode> GetPrimaryRenderpass() const noexcept;
Handle<SHVkPipeline> GetDebugDrawPipeline(DebugDrawPipelineType type) const noexcept;
uint32_t GetCurrentFrameIndex(void) const noexcept { return renderContext.GetCurrentFrame(); }
@ -441,10 +450,8 @@ namespace SHADE
// Renderers
Handle<SHRenderer> worldRenderer;
Handle<SHRenderer> screenRenderer;
std::vector<Handle<SHRenderer>> renderers;
// Temp Cameras
Handle<SHCamera> worldCamera;
Handle<SHCamera> screenCamera;
DirectorHandle worldCameraDirector;
@ -483,15 +490,15 @@ namespace SHADE
std::array<Handle<SHMesh>, MAX_PRIMITIVE_TYPES> primitiveMeshes;
// Render Graphs
Handle<SHRenderGraph> worldRenderGraph;
Handle<SHRenderGraph> screenRenderGraph;
Handle<SHRenderGraph> renderGraph;
//Handle<SHRenderGraph> screenRenderGraph;
#ifdef SHEDITOR
Handle<SHRenderGraph> editorRenderGraph;
//Handle<SHRenderGraph> editorRenderGraph;
#endif
// Sub systems
Handle<SHMousePickSystem> mousePickSystem;
Handle<SHPostOffscreenRenderSystem> postOffscreenRender;
Handle<SHMousePickSystem> mousePickSubSystem;
Handle<SHPostOffscreenRenderSystem> postOffscreenRenderSubSystem;
Handle<SHLightingSubSystem> lightingSubSystem;
Handle<SHTextRenderingSubSystem> textRenderingSubSystem;
Handle<SHSSAO> ssaoStorage;

View File

@ -9,6 +9,8 @@
#include "ECS_Base/Managers/SHSystemManager.h"
#include "SHGraphicsSystem.h"
#include "SHMaterialInstance.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
namespace SHADE
{
@ -95,9 +97,11 @@ namespace SHADE
/*-----------------------------------------------------------------------------------*/
Handle<SHShaderBlockInterface> SHMaterial::GetShaderBlockInterface() const noexcept
{
auto const& mappings = SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::BATCHING);
return pipeline->GetPipelineLayout()->GetShaderBlockInterface
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
mappings.at (SHPredefinedDescriptorTypes::MATERIALS),
//SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
vk::ShaderStageFlagBits::eFragment
);

View File

@ -16,6 +16,7 @@ of DigiPen Institute of Technology is prohibited.
#include "SHMaterial.h"
#include "Graphics/Pipeline/SHVkPipeline.h"
#include "Tools/Logger/SHLogger.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
namespace SHADE
{
@ -78,11 +79,12 @@ namespace SHADE
/*-----------------------------------------------------------------------------------*/
Handle<SHShaderBlockInterface> SHMaterialInstance::getShaderBlockInterface() const noexcept
{
return baseMaterial->GetPipeline()->GetPipelineLayout()->GetShaderBlockInterface
(
SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
vk::ShaderStageFlagBits::eFragment
);
return baseMaterial->GetPipeline()->GetPipelineLayout()->GetShaderBlockInterface
(
SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::BATCHING).at(SHPredefinedDescriptorTypes::MATERIALS),
//SHGraphicsConstants::DescriptorSetIndex::PER_INSTANCE,
SHGraphicsConstants::DescriptorSetBindings::BATCHED_PER_INST_DATA,
vk::ShaderStageFlagBits::eFragment
);
}
}

View File

@ -56,7 +56,7 @@ namespace SHADE
};
// Create descriptor set layout
offscreenRenderDescSetLayout = logicalDevice->CreateDescriptorSetLayout(0, { imageBinding }, false);
offscreenRenderDescSetLayout = logicalDevice->CreateDescriptorSetLayout({ imageBinding }, false);
// Create descriptor set
offscreenRenderDescSet = descriptorPool->Allocate({ offscreenRenderDescSetLayout }, { 1 });

View File

@ -14,7 +14,6 @@ of DigiPen Institute of Technology is prohibited.
#include "SHRenderer.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "SHViewport.h"
#include "Graphics/Buffers/SHVkBuffer.h"
#include "Graphics/Framebuffer/SHVkFramebuffer.h"
#include "SHMaterial.h"
@ -22,22 +21,22 @@ of DigiPen Institute of Technology is prohibited.
#include "Graphics/Descriptors/SHVkDescriptorSetGroup.h"
#include "Graphics/Buffers/SHVkBuffer.h"
#include "Camera/SHCameraDirector.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
namespace SHADE
{
/*-----------------------------------------------------------------------------------*/
/* Constructor/Destructors */
/*-----------------------------------------------------------------------------------*/
SHRenderer::SHRenderer(Handle<SHVkLogicalDevice> logicalDevice, uint32_t numFrames, std::vector<Handle<SHVkCommandPool>>& cmdPools, Handle<SHVkDescriptorPool> descriptorPool, Handle<SHVkDescriptorSetLayout> cameraDescLayout, Handle<SHViewport> viewport, Handle<SHRenderGraph> renderGraph)
: viewport { viewport }
, renderGraph { renderGraph }
SHRenderer::SHRenderer(Handle<SHVkLogicalDevice> logicalDevice, uint32_t numFrames, Handle<SHVkDescriptorPool> descriptorPool, PROJECTION_TYPE type)
: projectionType{type}
{
commandBuffers.resize(static_cast<std::size_t>(numFrames));
//commandBuffers.resize(static_cast<std::size_t>(numFrames));
for (uint32_t i = 0; i < commandBuffers.size(); ++i)
commandBuffers[i] = cmdPools[i]->RequestCommandBuffer(SH_CMD_BUFFER_TYPE::PRIMARY);
//for (uint32_t i = 0; i < commandBuffers.size(); ++i)
// commandBuffers[i] = cmdPools[i]->RequestCommandBuffer(SH_CMD_BUFFER_TYPE::PRIMARY);
cameraDescriptorSet = descriptorPool->Allocate({ cameraDescLayout }, { 1 });
cameraDescriptorSet = descriptorPool->Allocate(SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::CAMERA), { 1 });
#ifdef _DEBUG
const auto& CAM_DESC_SETS = cameraDescriptorSet->GetVkHandle();
@ -51,25 +50,16 @@ namespace SHADE
std::array cameraBufferArray{cameraBuffer};
cameraDescriptorSet->ModifyWriteDescBuffer(SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS, SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA, std::span<Handle<SHVkBuffer>>{ cameraBufferArray.data(), cameraBufferArray.size()}, 0, sizeof (SHShaderCameraData));
// We use index 0 because the descriptor set is standalone created from a single desc set layout. What the driver sees is that this set is at index 0 during updating.
static constexpr uint8_t SET_0 = 0;
cameraDescriptorSet->UpdateDescriptorSetBuffer(SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS, SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA);
cameraDescriptorSet->ModifyWriteDescBuffer(SET_0, SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA, std::span<Handle<SHVkBuffer>>{ cameraBufferArray.data(), cameraBufferArray.size()}, 0, sizeof (SHShaderCameraData));
cameraDescriptorSet->UpdateDescriptorSetBuffer(SET_0, SHGraphicsConstants::DescriptorSetBindings::CAMERA_DATA);
}
SHRenderer::~SHRenderer(void)
{
//for (auto& cmdBuffer : commandBuffers)
//{
// cmdBuffer.Free();
//}
}
/*-----------------------------------------------------------------------------------*/
/* Camera Registration */
/*-----------------------------------------------------------------------------------*/
void SHRenderer::SetCamera(Handle<SHCamera> _camera)
{
camera = _camera;
}
void SHRenderer::SetCameraDirector(Handle<SHCameraDirector> director) noexcept
@ -77,63 +67,55 @@ namespace SHADE
cameraDirector = director;
}
/*-----------------------------------------------------------------------------------*/
/* Drawing Functions */
/*-----------------------------------------------------------------------------------*/
void SHRenderer::Draw(uint32_t frameIndex, Handle<SHVkDescriptorPool> descPool) noexcept
void SHRenderer::UpdateData(uint32_t frameIndex) noexcept
{
renderGraph->Execute(frameIndex, commandBuffers[frameIndex], descPool);
}
void SHRenderer::UpdateDataAndBind(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept
{
if (camera && cameraDirector)
if (cameraDirector)
{
//UpdateDataAndBind(cmdBuffer, frameIndex, SHMatrix::Transpose(cameraDirector->GetVPMatrix()));
UpdateDataAndBind(cmdBuffer, frameIndex, cameraDirector->GetViewMatrix(), cameraDirector->GetProjMatrix(), cameraDirector->GetOrthoMatrix());
switch (projectionType)
{
case PROJECTION_TYPE::DEFAULT:
UpdateDataManual(frameIndex, cameraDirector->GetViewMatrix(), cameraDirector->GetProjMatrix());
break;
case PROJECTION_TYPE::PERSPECTIVE:
UpdateDataManual(frameIndex, cameraDirector->GetViewMatrix(), cameraDirector->GetPerspectiveMatrix());
break;
case PROJECTION_TYPE::ORTHOGRAPHIC:
UpdateDataManual(frameIndex, cameraDirector->GetViewMatrix(), cameraDirector->GetOrthoMatrix());
break;
default:
UpdateDataManual(frameIndex, cameraDirector->GetViewMatrix(), cameraDirector->GetProjMatrix());
break;
}
}
}
void SHRenderer::UpdateDataAndBind(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex, SHMatrix const& viewMatrix, SHMatrix const& projMatrix, SHMatrix const& orthoMatrix) noexcept
void SHRenderer::UpdateDataManual(uint32_t frameIndex, SHMatrix const& viewMatrix, SHMatrix const& projMatrix) noexcept
{
SetViewProjectionMatrix(viewMatrix, projMatrix, orthoMatrix);
SetViewProjectionMatrix(viewMatrix, projMatrix);
//cpuCameraData.viewProjectionMatrix = camera->GetViewProjectionMatrix();
cameraBuffer->WriteToMemory(&cpuCameraData, sizeof(SHShaderCameraData), 0, cameraDataAlignedSize * frameIndex);
BindDescSet(cmdBuffer, frameIndex);
//BindDescSet(cmdBuffer, frameIndex);
}
void SHRenderer::BindDescSet(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept
void SHRenderer::BindDescriptorSet(Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex, uint32_t frameIndex) noexcept
{
std::array<uint32_t, 1> dynamicOffsets{ frameIndex * cameraDataAlignedSize };
cmdBuffer->BindDescriptorSet(cameraDescriptorSet, SH_PIPELINE_TYPE::GRAPHICS, SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS, std::span{ dynamicOffsets.data(), 1 });
cmdBuffer->BindDescriptorSet(cameraDescriptorSet, SH_PIPELINE_TYPE::COMPUTE, SHGraphicsConstants::DescriptorSetIndex::HIGH_FREQUENCY_GLOBALS, std::span{ dynamicOffsets.data(), 1 });
cmdBuffer->BindDescriptorSet(cameraDescriptorSet, pipelineType, setIndex, std::span{ dynamicOffsets.data(), 1 });
}
void SHRenderer::UpdateCameraDataToBuffer(void) noexcept
void SHRenderer::SetViewProjectionMatrix(SHMatrix const& viewMatrix, SHMatrix const& projMatrix) noexcept
{
}
void SHRenderer::SetViewProjectionMatrix(SHMatrix const& viewMatrix, SHMatrix const& projMatrix, SHMatrix const& orthoMatrix) noexcept
{
//cpuCameraData.viewProjectionMatrix = camera->GetViewMatrix() * camera->GetProjectionMatrix();
cpuCameraData.viewProjectionMatrix = SHMatrix::Transpose(projMatrix * viewMatrix);
cpuCameraData.viewMatrix = SHMatrix::Transpose(viewMatrix);
cpuCameraData.projectionMatrix = SHMatrix::Transpose(projMatrix);
cpuCameraData.orthoMatrix = SHMatrix::Transpose (orthoMatrix);
}
Handle<SHRenderGraph> SHRenderer::GetRenderGraph(void) const noexcept
{
return renderGraph;
}
Handle<SHVkCommandBuffer> SHRenderer::GetCommandBuffer(uint32_t frameIndex) const noexcept
{
return commandBuffers[frameIndex];
}
//Handle<SHVkCommandBuffer> SHRenderer::GetCommandBuffer(uint32_t frameIndex) const noexcept
//{
// return commandBuffers[frameIndex];
//}
Handle<SHCameraDirector> SHRenderer::GetCameraDirector(void) const noexcept
{

View File

@ -32,12 +32,11 @@ namespace SHADE
class SHVkFramebuffer;
class SHMaterial;
class SHVkLogicalDevice;
class SHViewport;
class SHVkImageView;
class SHVkCommandBuffer;
class SHCamera;
class SHVkDescriptorSetGroup;
class SHGraphicsGlobalData;
class SHGraphicsPredefinedData;
class SHVkDescriptorPool;
class SHVkBuffer;
class SHCameraDirector;
@ -48,7 +47,6 @@ namespace SHADE
SHMatrix viewProjectionMatrix;
SHMatrix viewMatrix;
SHMatrix projectionMatrix;
SHMatrix orthoMatrix;
};
/*---------------------------------------------------------------------------------*/
@ -64,35 +62,36 @@ namespace SHADE
/***********************************************************************************/
class SHRenderer
{
public:
enum class PROJECTION_TYPE
{
DEFAULT,
PERSPECTIVE,
ORTHOGRAPHIC
};
/*-----------------------------------------------------------------------------*/
/* Constructor/Destructors */
/*-----------------------------------------------------------------------------*/
SHRenderer(Handle<SHVkLogicalDevice> logicalDevice, uint32_t numFrames, std::vector<Handle<SHVkCommandPool>>& cmdPools, Handle<SHVkDescriptorPool> descriptorPool, Handle<SHVkDescriptorSetLayout> cameraDescLayout, Handle<SHViewport> viewport, Handle<SHRenderGraph> renderGraph);
SHRenderer(Handle<SHVkLogicalDevice> logicalDevice, uint32_t numFrames, Handle<SHVkDescriptorPool> descriptorPool, PROJECTION_TYPE type);
~SHRenderer(void);
/*-----------------------------------------------------------------------------*/
/* Camera Registration */
/*-----------------------------------------------------------------------------*/
void SetCamera(Handle<SHCamera> _camera);
void SetCameraDirector (Handle<SHCameraDirector> director) noexcept;
/*-----------------------------------------------------------------------------*/
/* Drawing Functions */
/*-----------------------------------------------------------------------------*/
void Draw(uint32_t frameIndex, Handle<SHVkDescriptorPool> descPool) noexcept;
void UpdateDataAndBind(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void UpdateDataAndBind(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex, SHMatrix const& viewMatrix, SHMatrix const& projMatrix, SHMatrix const& orthoMatrix) noexcept;
void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void UpdateCameraDataToBuffer (void) noexcept;
void SetViewProjectionMatrix (SHMatrix const& viewMatrix, SHMatrix const& projMatrix, SHMatrix const& orthoMatrix) noexcept;
void UpdateData(uint32_t frameIndex) noexcept;
void UpdateDataManual(uint32_t frameIndex, SHMatrix const& viewMatrix, SHMatrix const& projMatrix) noexcept;
void BindDescriptorSet (Handle<SHVkCommandBuffer> cmdBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex, uint32_t frameIndex) noexcept;
void SetViewProjectionMatrix (SHMatrix const& viewMatrix, SHMatrix const& projMatrix) noexcept;
/*-----------------------------------------------------------------------------*/
/* Setters and Getters */
/*-----------------------------------------------------------------------------*/
Handle<SHRenderGraph> GetRenderGraph (void) const noexcept;
Handle<SHVkCommandBuffer> GetCommandBuffer(uint32_t frameIndex) const noexcept;
Handle<SHCameraDirector> GetCameraDirector (void) const noexcept;
private:
@ -102,9 +101,6 @@ namespace SHADE
//! Vulkan UBOs need to be aligned, this is pad SHShaderCameraData struct
uint32_t cameraDataAlignedSize;
Handle<SHViewport> viewport;
Handle<SHCamera> camera;
Handle<SHRenderGraph> renderGraph;
Handle<SHVkDescriptorSetGroup> cameraDescriptorSet;
Handle<SHVkBuffer> cameraBuffer;
@ -114,10 +110,10 @@ namespace SHADE
// GPU.
SHShaderCameraData cpuCameraData;
//! Command buffers for the render graph
std::vector<Handle<SHVkCommandBuffer>> commandBuffers;
////! Command buffers for the render graph
//std::vector<Handle<SHVkCommandBuffer>> commandBuffers;
PROJECTION_TYPE projectionType;
};
}

View File

@ -46,34 +46,6 @@ namespace SHADE
);
}
/*---------------------------------------------------------------------------------*/
/* Renderer Registration Functions */
/*---------------------------------------------------------------------------------*/
Handle<SHRenderer> SHViewport::AddRenderer(SHResourceHub& resourceManager, uint32_t numFrames, std::vector<Handle<SHVkCommandPool>>& cmdPools, Handle<SHVkDescriptorPool> descriptorPool, Handle<SHVkDescriptorSetLayout> cameraDescLayout, Handle<SHRenderGraph> renderGraph)
{
// Create the renderer
auto renderer = resourceManager.Create<SHRenderer>(device, numFrames, cmdPools, descriptorPool, cameraDescLayout, GetHandle(), renderGraph);
// Store
renderers.emplace_back(renderer);
// Return
return renderer;
}
void SHViewport::RemoveRenderer(Handle<SHRenderer> renderer)
{
auto iter = std::find(renderers.begin(), renderers.end(), renderer);
if (iter == renderers.end())
{
SHLOG_WARNING("Attempted to remove a Renderer that does not belong to a viewport!");
return;
}
// Remove it
iter->Free();
renderers.erase(iter);
}
void SHViewport::SetWidth(float w) noexcept
{
viewport.width = w;

View File

@ -56,11 +56,11 @@ namespace SHADE
/*-----------------------------------------------------------------------------*/
void SetUp(Handle<SHVkCommandBuffer> commandBuffer);
/*-----------------------------------------------------------------------------*/
/* Renderers Registration Functions */
/*-----------------------------------------------------------------------------*/
Handle<SHRenderer> AddRenderer(SHResourceHub& resourceManager, uint32_t numFrames, std::vector<Handle<SHVkCommandPool>>& cmdPools, Handle<SHVkDescriptorPool> descriptorPool, Handle<SHVkDescriptorSetLayout> cameraDescLayout, Handle<SHRenderGraph> renderGraph);
void RemoveRenderer(Handle<SHRenderer> renderer);
///*-----------------------------------------------------------------------------*/
///* Renderers Registration Functions */
///*-----------------------------------------------------------------------------*/
//Handle<SHRenderer> AddRenderer(SHResourceHub& resourceManager, uint32_t numFrames, std::vector<Handle<SHVkCommandPool>>& cmdPools, Handle<SHVkDescriptorPool> descriptorPool, Handle<SHVkDescriptorSetLayout> cameraDescLayout, Handle<SHRenderGraph> renderGraph);
//void RemoveRenderer(Handle<SHRenderer> renderer);
/*-----------------------------------------------------------------------------*/
/* Setters */
@ -79,7 +79,7 @@ namespace SHADE
float GetHeight() const { return viewport.height; }
float GetMinDepth() const { return viewport.minDepth; }
float GetMaxDepth() const { return viewport.maxDepth; }
std::vector<Handle<SHRenderer>>& GetRenderers() { return renderers; }
//std::vector<Handle<SHRenderer>>& GetRenderers() { return renderers; }
private:
@ -88,7 +88,7 @@ namespace SHADE
/*-----------------------------------------------------------------------------*/
Handle<SHVkLogicalDevice> device;
vk::Viewport viewport;
std::vector<Handle<SHRenderer>> renderers;
//std::vector<Handle<SHRenderer>> renderers;
};
}

View File

@ -1,5 +1,7 @@
#include "SHpch.h"
#include "SHLightComponent.h"
#include "Graphics/Events/SHGraphicsEvents.h"
#include "Events/SHEventManager.hpp"
namespace SHADE
{
@ -104,6 +106,21 @@ namespace SHADE
//MakeDirty();
}
void SHLightComponent::SetEnableShadow(bool flag) noexcept
{
lightData.castShadows = flag;
// If the flag is true
if (flag && lightData.shadowMapIndex == SHLightData::INVALID_SHADOW_MAP_INDEX)
{
// Create new event and broadcast it
SHLightEnableShadowEvent newEvent;
newEvent.lightEntity = GetEID();
SHEventManager::BroadcastEvent<SHLightEnableShadowEvent>(newEvent, SH_GRAPHICS_LIGHT_ENABLE_SHADOW_EVENT);
}
}
SHLightData const& SHLightComponent::GetLightData(void) const noexcept
{
return lightData;

View File

@ -25,7 +25,6 @@ namespace SHADE
////! If the light's data is already in the buffers, this will be set to true.
//bool bound;
public:
/*-----------------------------------------------------------------------*/
/* LIFECYCLE FUNCTIONS */
@ -49,6 +48,7 @@ namespace SHADE
//void Unbind (void) noexcept;
//void SetBound (uint32_t inIndexInBuffer) noexcept;
void SetStrength (float value) noexcept; // serialized
void SetEnableShadow (bool flag) noexcept;
SHLightData const& GetLightData (void) const noexcept;
@ -59,7 +59,7 @@ namespace SHADE
uint32_t const& GetCullingMask (void) const noexcept; // serialized
//bool IsDirty (void) const noexcept;
//bool GetBound (void) const noexcept;
uint32_t GetIndexInBuffer (void) const noexcept;
//uint32_t GetIndexInBuffer (void) const noexcept;
float GetStrength (void) const noexcept;
RTTR_ENABLE()
};

View File

@ -16,6 +16,12 @@ namespace SHADE
// Diffuse color set to 1
color = SHVec4::One;
// light will default not cast shadows
castShadows = false;
// shadow map index is invalid.
shadowMapIndex = INVALID_SHADOW_MAP_INDEX;
}
}

View File

@ -26,6 +26,8 @@ namespace SHADE
/***************************************************************************/
struct SHLightData
{
static constexpr uint32_t INVALID_SHADOW_MAP_INDEX = std::numeric_limits<uint32_t>::max();
//! position of the light
SHVec3 position;
@ -46,6 +48,13 @@ namespace SHADE
//! Strength of the light
float strength;
//! Whether or not the light will cast a shadow. More technically, whether or
//! not the light will result in the addition of a depth map into the render graph
//! to be used for shadow mapping calculations.
bool castShadows;
//! Index of the shadow map when it gets placed in the descriptor array of textures (that are all shadow maps).
uint32_t shadowMapIndex;
void Reset (void) noexcept;
//! TODO:

View File

@ -1,6 +1,6 @@
#include "SHpch.h"
#include "SHLightingSubSystem.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Tools/Utilities/SHUtilities.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/Buffers/SHVkBuffer.h"
@ -320,15 +320,16 @@ namespace SHADE
void SHLightingSubSystem::UpdateDescSet(uint32_t binding) noexcept
{
auto buffer = perTypeData[binding].GetDataBuffer();
static constexpr uint32_t LIGHTING_DATA_SET_INDEX = 0;
// We bind the buffer with the correct desc set binding
lightingDataDescSet->ModifyWriteDescBuffer(SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS,
lightingDataDescSet->ModifyWriteDescBuffer(LIGHTING_DATA_SET_INDEX,
binding + 1, // we want to +1 here because the first binding is reserved for count
{ &buffer, 1 },
0,
perTypeData[binding].GetDataSize() * perTypeData[binding].GetMaxLights());
lightingDataDescSet->UpdateDescriptorSetBuffer(SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS, binding + 1); // +1 here, same reason. see above
lightingDataDescSet->UpdateDescriptorSetBuffer(LIGHTING_DATA_SET_INDEX, binding + 1); // +1 here, same reason. see above
}
/***************************************************************************/
@ -385,7 +386,7 @@ namespace SHADE
std::fill (variableSizes.begin(), variableSizes.end(), 1);
// Create the descriptor set
lightingDataDescSet = descPool->Allocate({ SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS] }, variableSizes);
lightingDataDescSet = descPool->Allocate({ SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::LIGHTS) }, variableSizes);
#ifdef _DEBUG
const auto& CAM_DESC_SETS = lightingDataDescSet->GetVkHandle();
for (int i = 0; i < static_cast<int>(CAM_DESC_SETS.size()); ++i)
@ -408,8 +409,9 @@ namespace SHADE
// Create the GPU buffer to hold light count
lightCountsBuffer = logicalDevice->CreateBuffer(lightCountsAlignedSize * SHGraphicsConstants::NUM_FRAME_BUFFERS, nullptr, lightCountsAlignedSize * SHGraphicsConstants::NUM_FRAME_BUFFERS, vk::BufferUsageFlagBits::eUniformBuffer, VMA_MEMORY_USAGE_AUTO, VMA_ALLOCATION_CREATE_MAPPED_BIT | VMA_ALLOCATION_CREATE_HOST_ACCESS_SEQUENTIAL_WRITE_BIT, "Light Count Data");
lightingDataDescSet->ModifyWriteDescBuffer(SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS, SHGraphicsConstants::DescriptorSetBindings::LIGHTING_COUNT, {&lightCountsBuffer, 1}, 0, sizeof (uint32_t) * NUM_LIGHT_TYPES);
lightingDataDescSet->UpdateDescriptorSetBuffer(SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS, SHGraphicsConstants::DescriptorSetBindings::LIGHTING_COUNT);
static constexpr uint32_t LIGHTING_DATA_SET_INDEX = 0;
lightingDataDescSet->ModifyWriteDescBuffer(LIGHTING_DATA_SET_INDEX, SHGraphicsConstants::DescriptorSetBindings::LIGHTING_COUNT, { &lightCountsBuffer, 1 }, 0, sizeof(uint32_t) * NUM_LIGHT_TYPES);
lightingDataDescSet->UpdateDescriptorSetBuffer(LIGHTING_DATA_SET_INDEX, SHGraphicsConstants::DescriptorSetBindings::LIGHTING_COUNT);
for (uint32_t i = 0; i < SHGraphicsConstants::NUM_FRAME_BUFFERS; ++i)
{
@ -517,11 +519,16 @@ namespace SHADE
}
void SHLightingSubSystem::BindDescSet(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept
void SHLightingSubSystem::BindDescSet(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t setIndex, uint32_t frameIndex) noexcept
{
//Bind descriptor set(We bind at an offset because the buffer holds NUM_FRAME_BUFFERS sets of data).
cmdBuffer->BindDescriptorSet(lightingDataDescSet, SH_PIPELINE_TYPE::COMPUTE, SHGraphicsConstants::DescriptorSetIndex::DYNAMIC_GLOBALS, { dynamicOffsets[frameIndex] });
cmdBuffer->BindDescriptorSet(lightingDataDescSet, SH_PIPELINE_TYPE::COMPUTE, setIndex, { dynamicOffsets[frameIndex] });
}
Handle<SHVkDescriptorSetGroup> SHLightingSubSystem::GetLightDataDescriptorSet(void) const noexcept
{
return lightingDataDescSet;
}
}

View File

@ -4,6 +4,7 @@
#include "Math/Vector/SHVec3.h"
#include "Math/Vector/SHVec4.h"
#include "SHLightData.h"
#include <array>
#include "Graphics/MiddleEnd/Interface/SHGraphicsConstants.h"
namespace SHADE
@ -57,8 +58,11 @@ namespace SHADE
class SH_API SHLightingSubSystem
{
private:
public:
using DynamicOffsetArray = std::array<std::vector<uint32_t>, static_cast<uint32_t>(SHGraphicsConstants::NUM_FRAME_BUFFERS)>;
private:
class PerTypeData
{
private:
@ -130,7 +134,7 @@ namespace SHADE
std::array<PerTypeData, static_cast<uint32_t>(SH_LIGHT_TYPE::NUM_TYPES)> perTypeData;
//! Container to store dynamic offsets for binding descriptor sets
std::array<std::vector<uint32_t>, static_cast<uint32_t>(SHGraphicsConstants::NUM_FRAME_BUFFERS)> dynamicOffsets;
DynamicOffsetArray dynamicOffsets;
//! holds the data that represents how many lights are in the scene
std::array<uint32_t, static_cast<uint32_t>(SH_LIGHT_TYPE::NUM_TYPES)> lightCountsData;
@ -162,7 +166,8 @@ namespace SHADE
void Run (SHMatrix const& viewMat, uint32_t frameIndex) noexcept;
void Exit (void) noexcept;
void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t setIndex, uint32_t frameIndex) noexcept;
Handle<SHVkDescriptorSetGroup> GetLightDataDescriptorSet (void) const noexcept;
};
}

View File

@ -1,7 +1,7 @@
#include "SHpch.h"
#include "SHPipelineLibrary.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Graphics/RenderGraph/SHSubpass.h"
#include "Graphics/SHVkUtil.h"
@ -13,7 +13,7 @@ namespace SHADE
SHPipelineLayoutParams params
{
.shaderModules = {vsFsPair.first, vsFsPair.second},
.globalDescSetLayouts = SHGraphicsGlobalData::GetDescSetLayouts()
.predefinedDescSetLayouts = SHGraphicsPredefinedData::GetSystemData(SHGraphicsPredefinedData::SystemType::BATCHING).descSetLayouts
};
// Create the pipeline layout
@ -21,7 +21,7 @@ namespace SHADE
// Create the pipeline and configure the default vertex input state
auto newPipeline = logicalDevice->CreateGraphicsPipeline(pipelineLayout, nullptr, renderpass, subpass);
newPipeline->GetPipelineState().SetVertexInputState(SHGraphicsGlobalData::GetDefaultViState());
newPipeline->GetPipelineState().SetVertexInputState(SHGraphicsPredefinedData::GetDefaultViState());
SHColorBlendState colorBlendState{};
colorBlendState.logic_op_enable = VK_FALSE;

View File

@ -10,7 +10,7 @@ namespace SHADE
class SHVkDescriptorSetLayouts;
class SHVkPipeline;
class SHSubpass;
class SHGraphicsGlobalData;
class SHGraphicsPredefinedData;
// Pipeline library is a PURELY MIDDLE END SYSTEM. It is responsible for only creating pipelines from shaders and caching
// them so that they don't need to be recreated again.

View File

@ -1,7 +1,7 @@
#include "SHpch.h"
#include "SHFont.h"
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Graphics/Descriptors/SHVkDescriptorSetGroup.h"
#include "Graphics/Buffers/SHVkBuffer.h"
#include "Graphics/Images/SHVkSampler.h"
@ -121,17 +121,23 @@ namespace SHADE
descSet = descPool->Allocate({ layout }, { 1 });
auto viewLayoutSampler = std::make_tuple(bitmapDataImageView, sampler, vk::ImageLayout::eShaderReadOnlyOptimal);
descSet->ModifyWriteDescImage(SHGraphicsConstants::DescriptorSetIndex::FONT_DATA, SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA, {&viewLayoutSampler, 1});
static constexpr uint32_t FONT_DATA_SET_INDEX = 0;
descSet->ModifyWriteDescImage(FONT_DATA_SET_INDEX, SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA, {&viewLayoutSampler, 1});
descSet->ModifyWriteDescBuffer(SHGraphicsConstants::DescriptorSetIndex::FONT_DATA,
descSet->ModifyWriteDescBuffer(FONT_DATA_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::FONT_MATRIX_DATA, { &matrixDataBuffer, 1 }, 0, fontAsset.glyphTransformations.size() * sizeof(SHMatrix));
// Bind image and buffer to desc set.
descSet->UpdateDescriptorSetImages(SHGraphicsConstants::DescriptorSetIndex::FONT_DATA, SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA);
descSet->UpdateDescriptorSetBuffer(SHGraphicsConstants::DescriptorSetIndex::FONT_DATA, SHGraphicsConstants::DescriptorSetBindings::FONT_MATRIX_DATA);
descSet->UpdateDescriptorSetImages(FONT_DATA_SET_INDEX, SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA);
descSet->UpdateDescriptorSetBuffer(FONT_DATA_SET_INDEX, SHGraphicsConstants::DescriptorSetBindings::FONT_MATRIX_DATA);
}
void SHFont::BindDescriptorSet(Handle<SHVkCommandBuffer> commandBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex) noexcept
{
commandBuffer->BindDescriptorSet(descSet, SH_PIPELINE_TYPE::GRAPHICS, setIndex, {});
}
std::unordered_map<msdfgen::unicode_t, uint32_t> SHFont::GetUnicodeIndexing(void) const noexcept
{
return unicodeIndexing;

View File

@ -3,6 +3,7 @@
#include "Resource/SHHandle.h"
#include "msdf-atlas-gen/msdf-atlas-gen.h"
#include "Assets/Asset Types/SHFontAsset.h"
#include "Graphics/Pipeline/SHPipelineType.h"
namespace SHADE
{
@ -57,6 +58,7 @@ namespace SHADE
SHFont (Handle<SHVkLogicalDevice> inLogicalDeviceHdl, SHFontAsset const& asset) noexcept;
void TransferToGPU (Handle<SHVkCommandBuffer> commandBuffer) noexcept;
void DoPostTransfer (Handle<SHVkDescriptorPool> descPool, Handle<SHVkDescriptorSetLayout> layout) noexcept;
void BindDescriptorSet (Handle<SHVkCommandBuffer> commandBuffer, SH_PIPELINE_TYPE pipelineType, uint32_t setIndex) noexcept;
/*-----------------------------------------------------------------------*/

View File

@ -6,11 +6,13 @@
#include "Graphics/Devices/SHVkLogicalDevice.h"
#include "Graphics/MiddleEnd/TextRendering/SHFont.h"
#include "Graphics/Buffers/SHVkBuffer.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Graphics/Pipeline/SHVkPipeline.h"
#include "Graphics/SHVkUtil.h"
#include "Graphics/RenderGraph/SHSubpass.h"
#include "Math/Transform/SHTransformComponent.h"
#include "Graphics/MiddleEnd/GlobalData/SHGlobalDescriptorSets.h"
#include "Graphics/MiddleEnd/Interface/SHRenderer.h"
namespace SHADE
{
@ -91,19 +93,17 @@ namespace SHADE
}
void SHTextRenderingSubSystem::Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS, std::function<void(Handle<SHVkCommandBuffer>, uint32_t)> const& bindFunction) noexcept
void SHTextRenderingSubSystem::Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS) noexcept
{
SHComponentManager::CreateComponentSparseSet<SHTextRenderableComponent>();
cameraDescSetBind = bindFunction;
logicalDevice = device;
// prepare pipeline layout params
SHPipelineLayoutParams plParams
{
.shaderModules = {textVS, textFS},
.globalDescSetLayouts = SHGraphicsGlobalData::GetDescSetLayouts()
.predefinedDescSetLayouts = SHGraphicsPredefinedData::GetSystemData(SHGraphicsPredefinedData::SystemType::TEXT_RENDERING).descSetLayouts
};
pipelineLayout = logicalDevice->CreatePipelineLayout(plParams);
@ -157,24 +157,6 @@ namespace SHADE
// Construct pipeline
pipeline->ConstructPipeline();
SHVkDescriptorSetLayout::Binding fontBitmapBinding
{
.Type = vk::DescriptorType::eCombinedImageSampler,
.Stage = vk::ShaderStageFlagBits::eFragment,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::FONT_BITMAP_DATA,
.DescriptorCount = 1,
};
SHVkDescriptorSetLayout::Binding fontMatrixBinding
{
.Type = vk::DescriptorType::eStorageBuffer,
.Stage = vk::ShaderStageFlagBits::eVertex,
.BindPoint = SHGraphicsConstants::DescriptorSetBindings::FONT_MATRIX_DATA,
.DescriptorCount = 1,
};
fontDataDescSetLayout = logicalDevice->CreateDescriptorSetLayout(SHGraphicsConstants::DescriptorSetIndex::FONT_DATA, { fontBitmapBinding, fontMatrixBinding });
}
void SHTextRenderingSubSystem::Run(uint32_t frameIndex) noexcept
@ -192,9 +174,14 @@ namespace SHADE
}
}
void SHTextRenderingSubSystem::Render(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept
void SHTextRenderingSubSystem::Render(Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex) noexcept
{
auto& textRendererComps = SHComponentManager::GetDense<SHTextRenderableComponent>();
auto const& mappings = SHGraphicsPredefinedData::GetMappings(SHGraphicsPredefinedData::SystemType::TEXT_RENDERING);
uint32_t fontSetIndex = mappings.at(SHPredefinedDescriptorTypes::FONT);
uint32_t staticGlobalSetIndex = mappings.at(SHPredefinedDescriptorTypes::STATIC_DATA);
uint32_t cameraSetIndex = mappings.at(SHPredefinedDescriptorTypes::CAMERA);
for (auto& comp : textRendererComps)
{
auto* transform = SHComponentManager::GetComponent<SHTransformComponent>(comp.GetEID());
@ -205,15 +192,19 @@ namespace SHADE
// bind the pipeline
cmdBuffer->BindPipeline(pipeline);
// Bind global data
SHGlobalDescriptorSets::BindStaticGlobalData(cmdBuffer, SH_PIPELINE_TYPE::GRAPHICS, staticGlobalSetIndex);
// Bind camera data
renderer->BindDescriptorSet(cmdBuffer, SH_PIPELINE_TYPE::GRAPHICS, cameraSetIndex, frameIndex);
// bind descriptors for font (matrices)
fontHandle->BindDescriptorSet(cmdBuffer, SH_PIPELINE_TYPE::GRAPHICS, fontSetIndex);
// bind VBO (position and indices)
cmdBuffer->BindVertexBuffer(SHGraphicsConstants::VertexBufferBindings::CALCULATED_GLYPH_POSITION, comp.charPositionDataBuffer, 0);
cmdBuffer->BindVertexBuffer(SHGraphicsConstants::VertexBufferBindings::GLYPH_INDEX, comp.indexingDataBuffer, 0);
cameraDescSetBind(cmdBuffer, frameIndex);
// bind descriptors for font (matrices)
cmdBuffer->BindDescriptorSet(fontHandle->GetDescriptorSet(), SH_PIPELINE_TYPE::GRAPHICS, SHGraphicsConstants::DescriptorSetIndex::FONT_DATA, {});
cmdBuffer->SetPushConstantVariable("TestPushConstant.worldTransform", transform->GetTRS(), SH_PIPELINE_TYPE::GRAPHICS);
cmdBuffer->SetPushConstantVariable("TestPushConstant.eid", comp.GetEID(), SH_PIPELINE_TYPE::GRAPHICS);
cmdBuffer->SetPushConstantVariable("TestPushConstant.textColor", SHVec3 (1.0f, 1.0f, 1.0f), SH_PIPELINE_TYPE::GRAPHICS);
@ -223,9 +214,7 @@ namespace SHADE
// call draw call
cmdBuffer->DrawArrays(4, comp.text.size(), 0, 0);
//glDrawArraysInstanced(GL_TRIANGLE_FAN, 0, 4, static_cast<GLsizei>(textComp.lastRenderedCharacterIndex) + 1);
}
}
}
@ -234,9 +223,9 @@ namespace SHADE
}
Handle<SHVkDescriptorSetLayout> SHTextRenderingSubSystem::GetFontDataDescSetLayout(void) const noexcept
{
return fontDataDescSetLayout;
}
//Handle<SHVkDescriptorSetLayout> SHTextRenderingSubSystem::GetFontDataDescSetLayout(void) const noexcept
//{
// return fontDataDescSetLayout;
//}
}

View File

@ -20,6 +20,7 @@ namespace SHADE
class SHVkRenderpass;
class SHSubpass;
class SHVkShaderModule;
class SHRenderer;
class SHTextRenderingSubSystem
{
@ -41,24 +42,20 @@ namespace SHADE
Handle<SHVkPipelineLayout> pipelineLayout;
//! Descriptor set for font data access in shaders
Handle<SHVkDescriptorSetLayout> fontDataDescSetLayout;
//! Super temporary. Global descriptor set needs to be revamped along with
//! entire graphics system.
std::function<void(Handle<SHVkCommandBuffer>, uint32_t)> cameraDescSetBind;
//Handle<SHVkDescriptorSetLayout> fontDataDescSetLayout;
private:
void RecomputePositions(SHTextRenderableComponent& textComp) noexcept;
public:
void Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS, std::function<void(Handle<SHVkCommandBuffer>, uint32_t)> const& bindFunction) noexcept;
void Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS) noexcept;
void Run(uint32_t frameIndex) noexcept;
void Render (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void Render (Handle<SHVkCommandBuffer> cmdBuffer, Handle<SHRenderer> renderer, uint32_t frameIndex) noexcept;
void Exit(void) noexcept;
Handle<SHVkDescriptorSetLayout> GetFontDataDescSetLayout (void) const noexcept;
//Handle<SHVkDescriptorSetLayout> GetFontDataDescSetLayout (void) const noexcept;
};

View File

@ -24,7 +24,7 @@ of DigiPen Institute of Technology is prohibited.
#include "Graphics/Descriptors/SHVkDescriptorSetGroup.h"
#include "Graphics/Images/SHVkImage.h"
#include "Graphics/Images/SHVkImageView.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsGlobalData.h"
#include "Graphics/MiddleEnd/GlobalData/SHGraphicsPredefinedData.h"
#include "Assets/Asset Types/SHTextureAsset.h"
namespace SHADE
@ -168,22 +168,23 @@ namespace SHADE
}
texDescriptors = descPool->Allocate
(
{ SHGraphicsGlobalData::GetDescSetLayouts()[SHGraphicsConstants::DescriptorSetIndex::STATIC_GLOBALS] },
{ SHGraphicsPredefinedData::GetPredefinedDescSetLayouts(SHGraphicsPredefinedData::PredefinedDescSetLayoutTypes::STATIC_DATA) },
{ static_cast<uint32_t>(texOrder.size()) }
);
#ifdef _DEBUG
for (auto set : texDescriptors->GetVkHandle())
SET_VK_OBJ_NAME(device, vk::ObjectType::eDescriptorSet, set, "[Descriptor Set] Static Globals");
#endif
static constexpr uint32_t TEX_DESCRIPTOR_SET_INDEX = 0;
texDescriptors->ModifyWriteDescImage
(
SHGraphicsConstants::DescriptorSetIndex::STATIC_GLOBALS,
TEX_DESCRIPTOR_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::IMAGE_AND_SAMPLERS_DATA,
combinedImageSamplers
);
texDescriptors->UpdateDescriptorSetImages
(
SHGraphicsConstants::DescriptorSetIndex::STATIC_GLOBALS,
TEX_DESCRIPTOR_SET_INDEX,
SHGraphicsConstants::DescriptorSetBindings::IMAGE_AND_SAMPLERS_DATA
);
}

View File

@ -25,7 +25,7 @@ namespace SHADE
//! used just for textures or lights for example). In that case, we still
//! want to use the layout to initialize the pipeline layout but we do not
//! want to use it for allocating descriptor sets.
std::vector<Handle<SHVkDescriptorSetLayout>> const& globalDescSetLayouts = {};
std::vector<Handle<SHVkDescriptorSetLayout>> const& predefinedDescSetLayouts = {};
//! Since both SPIRV-Reflect and GLSL don't provide ways to describe UBOs or
//! SSBOs as dynamic, we need to do it ourselves. This will store bindings

Some files were not shown because too many files have changed in this diff Show More