Tested adding text component to entities

This commit is contained in:
Brandon Mak 2022-11-18 16:35:49 +08:00
parent f991e7b227
commit 66f33554a3
19 changed files with 113 additions and 27 deletions

View File

@ -13,6 +13,7 @@
#include "Physics/Interface/SHRigidBodyComponent.h"
#include "Physics/Interface/SHColliderComponent.h"
#include "Graphics/MiddleEnd/Lights/SHLightComponent.h"
#include "Graphics/MiddleEnd/TextRendering/SHTextRendererComponent.h"
#include "Assets/SHAssetManager.h"
#include "Camera/SHCameraComponent.h"
@ -41,6 +42,19 @@ namespace Sandbox
void SBMainScene::Init()
{
sceneName = SHSerialization::DeserializeSceneFromFile(sceneAssetID);
/*-----------------------------------------------------------------------*/
/* TESTING CODE */
/*-----------------------------------------------------------------------*/
//testText = SHEntityManager::CreateEntity<SHTransformComponent, SHTextRendererComponent>(MAX_EID, "Test Text");
//auto gfxSystem =SHSystemManager::GetSystem<SHGraphicsSystem>();
//auto textComp = SHComponentManager::GetComponent<SHTextRendererComponent>(testText);
//textComp->SetFont(gfxSystem->GetFontLibrary().GetFonts()[0]);
/*-----------------------------------------------------------------------*/
/* TESTING CODE */
/*-----------------------------------------------------------------------*/
}
void SBMainScene::Update(float dt)

View File

@ -12,6 +12,8 @@ namespace Sandbox
EntityID testObj;
std::vector<EntityID> stressTestObjects;
EntityID testText;
public:
virtual void Load();
virtual void Init();

View File

@ -516,7 +516,7 @@ namespace SHADE
ImGui_ImplVulkan_DestroyFontUploadObjects();
renderGraph->GetNode("ImGui Node")->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer>& cmd)
renderGraph->GetNode("ImGui Node")->GetSubpass("ImGui Draw")->AddExteriorDrawCalls([](Handle<SHVkCommandBuffer>& cmd, uint32_t frameIndex)
{
cmd->BeginLabeledSegment("ImGui Draw");
ImGui_ImplVulkan_RenderDrawData(ImGui::GetDrawData(), cmd->GetVkCommandBuffer());

View File

@ -90,7 +90,7 @@ namespace SHADE
auto const& RENDERERS = GFX_SYSTEM->GetDefaultViewport()->GetRenderers();
auto renderGraph = RENDERERS[SHGraphicsConstants::RenderGraphIndices::WORLD]->GetRenderGraph();
auto subPass = renderGraph->GetNode("Debug Draw")->GetSubpass("Debug Draw");
subPass->AddExteriorDrawCalls([this, GFX_SYSTEM](Handle<SHVkCommandBuffer>& cmdBuffer)
subPass->AddExteriorDrawCalls([this, GFX_SYSTEM](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
{
// Get Current frame index
const uint32_t FRAME_IDX = GFX_SYSTEM->GetCurrentFrameIndex();
@ -106,7 +106,7 @@ namespace SHADE
}
});
auto subPassWithDepth = renderGraph->GetNode("Debug Draw with Depth")->GetSubpass("Debug Draw with Depth");
subPassWithDepth->AddExteriorDrawCalls([this, GFX_SYSTEM](Handle<SHVkCommandBuffer>& cmdBuffer)
subPassWithDepth->AddExteriorDrawCalls([this, GFX_SYSTEM](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
{
// Get Current frame index
const uint32_t FRAME_IDX = GFX_SYSTEM->GetCurrentFrameIndex();

View File

@ -288,6 +288,10 @@ namespace SHADE
auto uiSubpass = screenSpaceNode->AddSubpass("UI");
uiSubpass->AddColorOutput("Scene");
uiSubpass->AddColorOutput("Entity ID");
uiSubpass->AddExteriorDrawCalls([=](Handle<SHVkCommandBuffer>& cmdBuffer, uint32_t frameIndex)
{
textRenderingSubSystem->Render(cmdBuffer, frameIndex);
});
{
// Dummy Node to transition scene render graph resource
@ -363,7 +367,10 @@ namespace SHADE
// initialize the text renderer
auto uiNode = screenRenderGraph->GetNode("Screen Space Pass");
textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS);
textRenderingSubSystem->Init(device, uiNode->GetRenderpass(), uiNode->GetSubpass("UI"), descPool, textVS, textFS, [=](Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex)
{
screenRenderer->BindDescSet(cmdBuffer, frameIndex);
});
SHFreetypeInstance::Init();
}
@ -506,6 +513,8 @@ namespace SHADE
#endif
}
textRenderingSubSystem->Run(frameIndex);
// For every viewport
for (int vpIndex = 0; vpIndex < static_cast<int>(viewports.size()); ++vpIndex)
{
@ -810,7 +819,7 @@ namespace SHADE
/*---------------------------------------------------------------------------------*/
Handle<SHTexture> SHGraphicsSystem::AddTexture(const SHTextureAsset& texAsset)
{
const int MIPS = texAsset.mipOffsets.size();
const int MIPS = static_cast<int> (texAsset.mipOffsets.size());
auto sampler = samplerCache.GetSampler(device, SHVkSamplerParams { .maxLod = static_cast<float>(MIPS) });
SET_VK_OBJ_NAME(device, vk::ObjectType::eSampler, sampler->GetVkSampler(), "[Sampler] Mips " + std::to_string(MIPS));
return texLibrary.Add(texAsset, sampler);
@ -818,7 +827,7 @@ namespace SHADE
SHADE::Handle<SHADE::SHTexture> SHGraphicsSystem::AddTexture(uint32_t pixelCount, const SHTexture::PixelChannel* const pixelData, uint32_t width, uint32_t height, SHTexture::TextureFormat format, std::vector<uint32_t> mipOffsets)
{
const int MIPS = mipOffsets.size();
const int MIPS = static_cast<int> (mipOffsets.size());
auto sampler = samplerCache.GetSampler(device, SHVkSamplerParams{ .maxLod = static_cast<float>(MIPS) });
SET_VK_OBJ_NAME(device, vk::ObjectType::eSampler, sampler->GetVkSampler(), "[Sampler] Mips " + std::to_string(MIPS));
return texLibrary.Add(pixelCount, pixelData, width, height, format, mipOffsets, sampler);
@ -1008,6 +1017,11 @@ namespace SHADE
return worldRenderGraph->GetNode(G_BUFFER_RENDER_GRAPH_NODE_NAME.data());
}
SHADE::SHFontLibrary const& SHGraphicsSystem::GetFontLibrary(void) const noexcept
{
return fontLibrary;
}
Handle<SHVkPipeline> SHGraphicsSystem::createDebugDrawPipeline(Handle<SHVkRenderpass> renderPass, Handle<SHSubpass> subpass)
{
auto pipelineLayout = resourceManager.Create<SHVkPipelineLayout>

View File

@ -367,6 +367,7 @@ namespace SHADE
Handle<SHVkPipeline> GetDebugDrawPipeline(void) const noexcept { return debugDrawPipeline; }
Handle<SHVkPipeline> GetDebugDrawDepthPipeline(void) const noexcept { return debugDrawDepthPipeline; }
uint32_t GetCurrentFrameIndex(void) const noexcept { return renderContext.GetCurrentFrame(); }
SHFontLibrary const& GetFontLibrary (void) const noexcept;
/*-----------------------------------------------------------------------------*/
/* Getters */

View File

@ -101,6 +101,11 @@ namespace SHADE
//cpuCameraData.viewProjectionMatrix = camera->GetViewProjectionMatrix();
cameraBuffer->WriteToMemory(&cpuCameraData, sizeof(SHShaderCameraData), 0, cameraDataAlignedSize * frameIndex);
BindDescSet(cmdBuffer, frameIndex);
}
void SHRenderer::BindDescSet(Handle<SHVkCommandBuffer> cmdBuffer, 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 });

View File

@ -63,6 +63,7 @@ namespace SHADE
/***********************************************************************************/
class SHRenderer
{
public:
/*-----------------------------------------------------------------------------*/
/* Constructor/Destructors */
@ -82,6 +83,7 @@ namespace SHADE
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) noexcept;
void BindDescSet (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void UpdateCameraDataToBuffer (void) noexcept;
void SetViewProjectionMatrix (SHMatrix const& viewMatrix, SHMatrix const& projMatrix) noexcept;

View File

@ -423,9 +423,8 @@ namespace SHADE
/*!
\brief
Loops through every single light component and checks for dirty light
data. If light data is dirty, rewrite to the CPU container. We also want
to bind the descriptor set for the light data.
Loops through every single light component and writes light data to CPU
then GPU.
*/
/***************************************************************************/

View File

@ -43,7 +43,7 @@ namespace SHADE
.depth = 1,
.levels = 1,
.arrayLayers = 1,
.imageFormat = vk::Format::eR8G8B8A8Snorm,
.imageFormat = vk::Format::eR8G8B8A8Unorm,
//.imageFormat = vk::Format::eR32Sfloat,
//.imageFormat = vk::Format::eR32G32B32Sfloat,
.usageFlags = vk::ImageUsageFlagBits::eSampled | vk::ImageUsageFlagBits::eTransferDst,

View File

@ -100,4 +100,9 @@ namespace SHADE
postTransferBarriers.clear();
}
std::vector<Handle<SHFont>> const& SHFontLibrary::GetFonts(void) const noexcept
{
return fonts;
}
}

View File

@ -13,7 +13,7 @@ namespace SHADE
class SHVkQueue;
class SHVkDescriptorSetLayout;
class SHFontLibrary
class SH_API SHFontLibrary
{
private:
//! Handles to all the fonts usable in SHTextRendererComponents
@ -31,5 +31,6 @@ namespace SHADE
public:
Handle<SHFont> AddFont (Handle<SHVkLogicalDevice> logicalDevice, SHResourceHub& resourceHub, SHFontAsset const& asset) noexcept;
void BuildFonts (Handle<SHVkLogicalDevice> logicalDevice, Handle<SHVkQueue> queue, Handle<SHVkCommandPool> cmdPool, Handle<SHVkDescriptorPool> descPool, Handle<SHVkDescriptorSetLayout> layout, SHResourceHub& resourceHub) noexcept;
std::vector<Handle<SHFont>> const& GetFonts (void) const noexcept;
};
}

View File

@ -24,13 +24,18 @@ namespace SHADE
/***************************************************************************/
void SHTextRendererComponent::OnCreate(void)
{
text = "";
text = "Text";
requiresRecompute = true;
// Default white color.
color = SHColour::WHITE;
}
void SHTextRendererComponent::OnDestroy(void)
{
}
/***************************************************************************/
/*!
@ -50,6 +55,11 @@ namespace SHADE
MakeDirty();
}
void SHTextRendererComponent::SetFont(Handle<SHFont> font) noexcept
{
fontHandle = font;
}
/***************************************************************************/
/*!

View File

@ -12,7 +12,7 @@ namespace SHADE
class SHVkDescriptorSetGroup;
class SHVkBuffer;
class SHTextRendererComponent final : public SHComponent
class SH_API SHTextRendererComponent final : public SHComponent
{
public:
static constexpr uint32_t MAX_CHARACTERS = 500;
@ -44,11 +44,14 @@ namespace SHADE
public:
void OnCreate(void) override final;
void OnDestroy(void) override final;
/*-----------------------------------------------------------------------*/
/* SETTERS AND GETTERS */
/*-----------------------------------------------------------------------*/
void SetText (std::string_view newText) noexcept;
void SetFont (Handle<SHFont> font) noexcept;
std::string const& GetText (void) const noexcept;
friend class SHTextRenderingSubSystem;

View File

@ -10,6 +10,7 @@
#include "Graphics/Pipeline/SHVkPipeline.h"
#include "Graphics/SHVkUtil.h"
#include "Graphics/RenderGraph/SHSubpass.h"
#include "Math/Transform/SHTransformComponent.h"
namespace SHADE
{
@ -82,16 +83,20 @@ namespace SHADE
//}
}
textComp.indexingDataBuffer->WriteToMemory(indexingData.data(), indexingData.size() * sizeof (SHTextRendererComponent::TextIndexingType),0, 0);
textComp.charPositionDataBuffer->WriteToMemory(charPositionData.data(), charPositionData.size() * sizeof (SHVec4), 0, 0);
textComp.indexingDataBuffer->WriteToMemory(indexingData.data(), static_cast<uint32_t>(indexingData.size()) * sizeof (SHTextRendererComponent::TextIndexingType),0, 0);
textComp.charPositionDataBuffer->WriteToMemory(charPositionData.data(), static_cast<uint32_t>(charPositionData.size()) * sizeof (SHVec4), 0, 0);
indexingData.clear();
charPositionData.clear();
}
void SHTextRenderingSubSystem::Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS) noexcept
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
{
SHComponentManager::CreateComponentSparseSet<SHTextRendererComponent>();
cameraDescSetBind = bindFunction;
logicalDevice = device;
// prepare pipeline layout params
@ -121,7 +126,7 @@ namespace SHADE
colorBlendState.logic_op = vk::LogicOp::eCopy;
auto const& subpassColorReferences = subpass->GetColorAttachmentReferences();
colorBlendState.attachments.reserve(subpassColorReferences.size());
colorBlendState.attachments.reserve(static_cast<uint32_t>(subpassColorReferences.size()));
for (auto& att : subpassColorReferences)
{
@ -177,17 +182,18 @@ namespace SHADE
RecomputePositions(comp);
comp.Clean();
}
}
}
void SHTextRenderingSubSystem::Render(Handle<SHVkCommandBuffer> cmdBuffer) noexcept
void SHTextRenderingSubSystem::Render(Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept
{
auto& textRendererComps = SHComponentManager::GetDense<SHTextRendererComponent>();
for (auto& comp : textRendererComps)
{
auto* transform = SHComponentManager::GetComponent<SHTransformComponent>(comp.GetEID());
Handle<SHFont> fontHandle = comp.fontHandle;
if (fontHandle)
if (fontHandle && transform)
{
// bind the pipeline
cmdBuffer->BindPipeline(pipeline);
@ -196,10 +202,20 @@ namespace SHADE
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);
cmdBuffer->SubmitPushConstants(SH_PIPELINE_TYPE::GRAPHICS);
// call draw call
cmdBuffer->DrawArrays(4, comp.text.size(), 0, 0);
//glDrawArraysInstanced(GL_TRIANGLE_FAN, 0, 4, static_cast<GLsizei>(textComp.lastRenderedCharacterIndex) + 1);
}

View File

@ -2,6 +2,8 @@
#include "Resource/SHHandle.h"
#include "Graphics/Pipeline/SHPipelineState.h"
#include "Math/SHMatrix.h"
#include "Math/Vector/SHVec3.h"
namespace SHADE
{
@ -22,6 +24,12 @@ namespace SHADE
class SHTextRenderingSubSystem
{
private:
struct ShaderPushConstantData
{
SHMatrix worldTransform;
uint32_t eid;
SHVec3 textColor;
};
//! Logical device for creation and destruction
Handle<SHVkLogicalDevice> logicalDevice;
@ -35,15 +43,21 @@ namespace SHADE
//! 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;
private:
void RecomputePositions(SHTextRendererComponent& textComp) noexcept;
public:
void Init(Handle<SHVkLogicalDevice> device, Handle<SHVkRenderpass> compatibleRenderpass, Handle<SHSubpass> subpass, Handle<SHVkDescriptorPool> descPool, Handle<SHVkShaderModule> textVS, Handle<SHVkShaderModule> textFS) noexcept;
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 Run(uint32_t frameIndex) noexcept;
void Render (Handle<SHVkCommandBuffer> cmdBuffer) noexcept;
void Render (Handle<SHVkCommandBuffer> cmdBuffer, uint32_t frameIndex) noexcept;
void Exit(void) noexcept;
Handle<SHVkDescriptorSetLayout> GetFontDataDescSetLayout (void) const noexcept;

View File

@ -79,9 +79,9 @@ namespace SHADE
startOffset += pcInfo.size;
}
stageFlags |= shaderModule->GetShaderStageFlagBits();
}
stageFlags |= shaderModule->GetShaderStageFlagBits();
}
// After all the sizes of the push constant blocks have been added, record the size in the interface

View File

@ -211,7 +211,7 @@ namespace SHADE
// Draw all the exterior draw calls
for (auto& drawCall : exteriorDrawCalls)
{
drawCall(commandBuffer);
drawCall(commandBuffer, frameIndex);
}
commandBuffer->EndLabeledSegment();
}
@ -221,7 +221,7 @@ namespace SHADE
UpdateWriteDescriptors();
}
void SHSubpass::AddExteriorDrawCalls(std::function<void(Handle<SHVkCommandBuffer>&)> const& newDrawCall) noexcept
void SHSubpass::AddExteriorDrawCalls(std::function<void(Handle<SHVkCommandBuffer>&, uint32_t)> const& newDrawCall) noexcept
{
exteriorDrawCalls.push_back(newDrawCall);
}

View File

@ -76,7 +76,7 @@ namespace SHADE
//! after we draw everything from the batch. Because of this, these draw calls
//! are always the last things drawn, so DO NOT USE THIS FUNCTIONALITY FOR ANYTHING
//! COMPLEX.
std::vector<std::function<void(Handle<SHVkCommandBuffer>&)>> exteriorDrawCalls;
std::vector<std::function<void(Handle<SHVkCommandBuffer>&, uint32_t)>> exteriorDrawCalls;
/// For identifying subpasses
std::string name;
@ -99,7 +99,7 @@ namespace SHADE
void AddGeneralDepthOutput(std::string resourceToReference) noexcept;
void AddInput(std::string resourceToReference) noexcept;
void AddGeneralInput (std::string resourceToReference) noexcept;
void AddExteriorDrawCalls(std::function<void(Handle<SHVkCommandBuffer>&)> const& newDrawCall) noexcept;
void AddExteriorDrawCalls(std::function<void(Handle<SHVkCommandBuffer>&, uint32_t)> const& newDrawCall) noexcept;
// Runtime functions
void Execute(Handle<SHVkCommandBuffer>& commandBuffer, Handle<SHVkDescriptorPool> descPool, uint32_t frameIndex) noexcept;