diff --git a/engine/include/XCEngine/RHI/D3D12/D3D12CommandList.h b/engine/include/XCEngine/RHI/D3D12/D3D12CommandList.h index 69ac5d83..37d5bd06 100644 --- a/engine/include/XCEngine/RHI/D3D12/D3D12CommandList.h +++ b/engine/include/XCEngine/RHI/D3D12/D3D12CommandList.h @@ -37,12 +37,6 @@ public: void SetShader(RHIShader* shader) override; - void SetUniformInt(const char* name, int value) override; - void SetUniformFloat(const char* name, float value) override; - void SetUniformVec3(const char* name, float x, float y, float z) override; - void SetUniformVec4(const char* name, float x, float y, float z, float w) override; - void SetUniformMat4(const char* name, const float* value) override; - void TransitionBarrier(RHIResourceView* resource, ResourceStates stateBefore, ResourceStates stateAfter) override; void TransitionBarrier(ID3D12Resource* resource, ResourceStates stateBefore, ResourceStates stateAfter); void TransitionBarrierInternal(ID3D12Resource* resource, ResourceStates stateBefore, ResourceStates stateAfter, uint32_t subresource = D3D12_RESOURCE_BARRIER_ALL_SUBRESOURCES); diff --git a/engine/include/XCEngine/RHI/D3D12/D3D12DescriptorSet.h b/engine/include/XCEngine/RHI/D3D12/D3D12DescriptorSet.h index 620bacae..5a5a8e4b 100644 --- a/engine/include/XCEngine/RHI/D3D12/D3D12DescriptorSet.h +++ b/engine/include/XCEngine/RHI/D3D12/D3D12DescriptorSet.h @@ -2,6 +2,7 @@ #include #include +#include #include "../RHIEnums.h" #include "../RHITypes.h" @@ -21,13 +22,21 @@ public: bool Initialize(D3D12DescriptorHeap* heap, uint32_t offset, uint32_t count, const DescriptorSetLayoutDesc& layout); void Shutdown() override; + void Bind() override; + void Unbind() override; + void Update(uint32_t offset, RHIResourceView* view) override; void UpdateSampler(uint32_t offset, RHISampler* sampler) override; - void* GetNativeHandle() override; + void WriteConstant(uint32_t binding, const void* data, size_t size, size_t offset = 0) override; uint32_t GetBindingCount() const override { return m_bindingCount; } const DescriptorSetLayoutBinding* GetBindings() const override { return m_bindings; } + void* GetConstantBufferData() override { return m_constantBufferData.data(); } + size_t GetConstantBufferSize() const override { return m_constantBufferData.size(); } + bool IsConstantDirty() const override { return m_constantBufferDirty; } + void MarkConstantClean() override { m_constantBufferDirty = false; } + D3D12_GPU_DESCRIPTOR_HANDLE GetGPUHandle(uint32_t index = 0) const; uint32_t GetOffset() const { return m_offset; } uint32_t GetCount() const { return m_count; } @@ -39,6 +48,8 @@ private: uint32_t m_count; uint32_t m_bindingCount; DescriptorSetLayoutBinding* m_bindings; + std::vector m_constantBufferData; + bool m_constantBufferDirty = false; }; } // namespace RHI diff --git a/engine/include/XCEngine/RHI/OpenGL/OpenGLCommandList.h b/engine/include/XCEngine/RHI/OpenGL/OpenGLCommandList.h index 8fb1449b..1ff4ef98 100644 --- a/engine/include/XCEngine/RHI/OpenGL/OpenGLCommandList.h +++ b/engine/include/XCEngine/RHI/OpenGL/OpenGLCommandList.h @@ -54,11 +54,11 @@ public: void SetShader(RHIShader* shader) override; - void SetUniformInt(const char* name, int value) override; - void SetUniformFloat(const char* name, float value) override; - void SetUniformVec3(const char* name, float x, float y, float z) override; - void SetUniformVec4(const char* name, float x, float y, float z, float w) override; - void SetUniformMat4(const char* name, const float* value) override; + void SetUniformInt(const char* name, int value); + void SetUniformFloat(const char* name, float value); + void SetUniformVec3(const char* name, float x, float y, float z); + void SetUniformVec4(const char* name, float x, float y, float z, float w); + void SetUniformMat4(const char* name, const float* value); void SetPipelineState(RHIPipelineState* pipelineState) override; void SetGraphicsDescriptorSets( diff --git a/engine/include/XCEngine/RHI/OpenGL/OpenGLDescriptorSet.h b/engine/include/XCEngine/RHI/OpenGL/OpenGLDescriptorSet.h index 6bcb7093..e7dcdb63 100644 --- a/engine/include/XCEngine/RHI/OpenGL/OpenGLDescriptorSet.h +++ b/engine/include/XCEngine/RHI/OpenGL/OpenGLDescriptorSet.h @@ -28,14 +28,21 @@ public: bool Initialize(OpenGLTextureUnitAllocator* allocator, uint32_t count, const DescriptorSetLayoutDesc& layout); void Shutdown() override; + void Bind() override; + void Unbind() override; + void Update(uint32_t offset, RHIResourceView* view) override; void UpdateSampler(uint32_t offset, RHISampler* sampler) override; - void* GetNativeHandle() override { return this; } + void WriteConstant(uint32_t binding, const void* data, size_t size, size_t offset = 0) override; uint32_t GetBindingCount() const override { return static_cast(m_bindings.size()); } const DescriptorSetLayoutBinding* GetBindings() const override { return m_layoutBindings; } - void Bind(); + void* GetConstantBufferData() override { return m_constantBufferData.data(); } + size_t GetConstantBufferSize() const override { return m_constantBufferData.size(); } + bool IsConstantDirty() const override { return m_constantBufferDirty; } + void MarkConstantClean() override { m_constantBufferDirty = false; } + uint32_t GetBindingPoint(uint32_t binding) const; private: @@ -44,6 +51,9 @@ private: DescriptorSetLayoutBinding* m_layoutBindings; uint32_t m_bindingCount; bool m_bound; + std::vector m_constantBufferData; + bool m_constantBufferDirty = false; + uint32_t m_constantBuffer = 0; }; } // namespace RHI diff --git a/engine/include/XCEngine/RHI/RHICommandList.h b/engine/include/XCEngine/RHI/RHICommandList.h index c887f341..ff0eb63e 100644 --- a/engine/include/XCEngine/RHI/RHICommandList.h +++ b/engine/include/XCEngine/RHI/RHICommandList.h @@ -64,12 +64,6 @@ public: virtual void SetShader(RHIShader* shader) = 0; - virtual void SetUniformInt(const char* name, int value) = 0; - virtual void SetUniformFloat(const char* name, float value) = 0; - virtual void SetUniformVec3(const char* name, float x, float y, float z) = 0; - virtual void SetUniformVec4(const char* name, float x, float y, float z, float w) = 0; - virtual void SetUniformMat4(const char* name, const float* value) = 0; - virtual void SetPipelineState(RHIPipelineState* pso) = 0; virtual void SetGraphicsDescriptorSets( uint32_t firstSet, diff --git a/engine/include/XCEngine/RHI/RHIDescriptorPool.h b/engine/include/XCEngine/RHI/RHIDescriptorPool.h index 1c8394a8..e9905140 100644 --- a/engine/include/XCEngine/RHI/RHIDescriptorPool.h +++ b/engine/include/XCEngine/RHI/RHIDescriptorPool.h @@ -1,20 +1,12 @@ #pragma once #include "RHIEnums.h" -#include +#include "RHITypes.h" namespace XCEngine { namespace RHI { class RHIDescriptorSet; -struct DescriptorSetLayoutDesc; - -struct DescriptorPoolDesc { - void* device; - DescriptorHeapType type; - uint32_t descriptorCount; - bool shaderVisible; -}; class RHIDescriptorPool { public: diff --git a/engine/include/XCEngine/RHI/RHIDescriptorSet.h b/engine/include/XCEngine/RHI/RHIDescriptorSet.h index f6242166..190b9357 100644 --- a/engine/include/XCEngine/RHI/RHIDescriptorSet.h +++ b/engine/include/XCEngine/RHI/RHIDescriptorSet.h @@ -10,34 +10,30 @@ class RHIDescriptorPool; class RHIResourceView; class RHISampler; -struct DescriptorSetLayoutBinding { - uint32_t binding; - DescriptorType type; - uint32_t count; - ShaderVisibility visibility = ShaderVisibility::All; -}; - -struct DescriptorSetLayoutDesc { - DescriptorSetLayoutBinding* bindings = nullptr; - uint32_t bindingCount = 0; -}; - class RHIDescriptorSet { public: virtual ~RHIDescriptorSet() = default; virtual void Shutdown() = 0; + virtual void Bind() = 0; + virtual void Unbind() = 0; + virtual void Update(uint32_t offset, RHIResourceView* view) = 0; virtual void UpdateSampler(uint32_t offset, RHISampler* sampler) = 0; - virtual void* GetNativeHandle() = 0; + virtual void WriteConstant(uint32_t binding, const void* data, size_t size, size_t offset = 0) = 0; virtual uint32_t GetBindingCount() const = 0; virtual const DescriptorSetLayoutBinding* GetBindings() const = 0; + virtual void* GetConstantBufferData() = 0; + virtual size_t GetConstantBufferSize() const = 0; + virtual bool IsConstantDirty() const = 0; + virtual void MarkConstantClean() = 0; + protected: RHIDescriptorSet() = default; }; } // namespace RHI -} // namespace XCEngine \ No newline at end of file +} // namespace XCEngine diff --git a/engine/include/XCEngine/RHI/RHITypes.h b/engine/include/XCEngine/RHI/RHITypes.h index 4da31637..0cd2f930 100644 --- a/engine/include/XCEngine/RHI/RHITypes.h +++ b/engine/include/XCEngine/RHI/RHITypes.h @@ -377,5 +377,24 @@ struct ResourceViewDesc { uint32_t structureByteStride = 0; }; +struct DescriptorSetLayoutBinding { + uint32_t binding = 0; + uint32_t type = 0; + uint32_t count = 0; + uint32_t visibility = 0; +}; + +struct DescriptorSetLayoutDesc { + DescriptorSetLayoutBinding* bindings = nullptr; + uint32_t bindingCount = 0; +}; + +struct DescriptorPoolDesc { + void* device = nullptr; + DescriptorHeapType type = DescriptorHeapType::CBV_SRV_UAV; + uint32_t descriptorCount = 0; + bool shaderVisible = false; +}; + } // namespace RHI } // namespace XCEngine diff --git a/engine/src/RHI/D3D12/D3D12CommandList.cpp b/engine/src/RHI/D3D12/D3D12CommandList.cpp index 478e5d80..eb810b71 100644 --- a/engine/src/RHI/D3D12/D3D12CommandList.cpp +++ b/engine/src/RHI/D3D12/D3D12CommandList.cpp @@ -101,68 +101,6 @@ void D3D12CommandList::SetPipelineLayout(D3D12PipelineLayout* layout) { } } -void D3D12CommandList::SetUniformInt(const char* name, int value) { - if (m_currentShader && m_currentPipelineLayout) { - const RHIShader::UniformInfo* info = m_currentShader->GetUniformInfo(name); - if (info) { - uint32_t rootIndex = m_currentPipelineLayout->GetRootParameterIndex(info->bindPoint); - if (rootIndex != UINT32_MAX) { - m_commandList->SetGraphicsRoot32BitConstants(rootIndex, 1, &value, 0); - } - } - } -} - -void D3D12CommandList::SetUniformFloat(const char* name, float value) { - if (m_currentShader && m_currentPipelineLayout) { - const RHIShader::UniformInfo* info = m_currentShader->GetUniformInfo(name); - if (info) { - uint32_t rootIndex = m_currentPipelineLayout->GetRootParameterIndex(info->bindPoint); - if (rootIndex != UINT32_MAX) { - m_commandList->SetGraphicsRoot32BitConstants(rootIndex, 1, &value, 0); - } - } - } -} - -void D3D12CommandList::SetUniformVec3(const char* name, float x, float y, float z) { - if (m_currentShader && m_currentPipelineLayout) { - const RHIShader::UniformInfo* info = m_currentShader->GetUniformInfo(name); - if (info) { - uint32_t rootIndex = m_currentPipelineLayout->GetRootParameterIndex(info->bindPoint); - if (rootIndex != UINT32_MAX) { - float values[3] = { x, y, z }; - m_commandList->SetGraphicsRoot32BitConstants(rootIndex, 3, values, 0); - } - } - } -} - -void D3D12CommandList::SetUniformVec4(const char* name, float x, float y, float z, float w) { - if (m_currentShader && m_currentPipelineLayout) { - const RHIShader::UniformInfo* info = m_currentShader->GetUniformInfo(name); - if (info) { - uint32_t rootIndex = m_currentPipelineLayout->GetRootParameterIndex(info->bindPoint); - if (rootIndex != UINT32_MAX) { - float values[4] = { x, y, z, w }; - m_commandList->SetGraphicsRoot32BitConstants(rootIndex, 4, values, 0); - } - } - } -} - -void D3D12CommandList::SetUniformMat4(const char* name, const float* value) { - if (m_currentShader && m_currentPipelineLayout) { - const RHIShader::UniformInfo* info = m_currentShader->GetUniformInfo(name); - if (info) { - uint32_t rootIndex = m_currentPipelineLayout->GetRootParameterIndex(info->bindPoint); - if (rootIndex != UINT32_MAX) { - m_commandList->SetGraphicsRoot32BitConstants(rootIndex, 16, value, 0); - } - } - } -} - void D3D12CommandList::TransitionBarrier(RHIResourceView* resource, ResourceStates stateBefore, ResourceStates stateAfter) { if (!resource || !resource->IsValid()) return; D3D12ResourceView* d3d12View = static_cast(resource); @@ -584,7 +522,20 @@ void D3D12CommandList::ClearRenderTargetView(D3D12_CPU_DESCRIPTOR_HANDLE renderT } void D3D12CommandList::Clear(float r, float g, float b, float a, uint32_t buffers) { - (void)r; (void)g; (void)b; (void)a; (void)buffers; + float color[4] = { r, g, b, a }; + if (buffers & 1) { + for (const auto& rtvHandle : m_boundRenderTargets) { + m_commandList->ClearRenderTargetView(rtvHandle, color, 0, nullptr); + } + } + if (buffers & 2 || buffers & 4) { + if (m_depthStencilBound) { + uint32_t clearFlags = 0; + if (buffers & 2) clearFlags |= D3D12_CLEAR_FLAG_DEPTH; + if (buffers & 4) clearFlags |= D3D12_CLEAR_FLAG_STENCIL; + m_commandList->ClearDepthStencilView(m_boundDepthStencil, static_cast(clearFlags), 1.0f, 0, 0, nullptr); + } + } } void D3D12CommandList::ClearRenderTarget(RHIResourceView* renderTarget, const float color[4]) { diff --git a/engine/src/RHI/D3D12/D3D12DescriptorSet.cpp b/engine/src/RHI/D3D12/D3D12DescriptorSet.cpp index 608f34be..cb454253 100644 --- a/engine/src/RHI/D3D12/D3D12DescriptorSet.cpp +++ b/engine/src/RHI/D3D12/D3D12DescriptorSet.cpp @@ -43,6 +43,12 @@ void D3D12DescriptorSet::Shutdown() { } } +void D3D12DescriptorSet::Bind() { +} + +void D3D12DescriptorSet::Unbind() { +} + void D3D12DescriptorSet::Update(uint32_t offset, RHIResourceView* view) { (void)offset; (void)view; @@ -53,10 +59,6 @@ void D3D12DescriptorSet::UpdateSampler(uint32_t offset, RHISampler* sampler) { (void)sampler; } -void* D3D12DescriptorSet::GetNativeHandle() { - return this; -} - D3D12_GPU_DESCRIPTOR_HANDLE D3D12DescriptorSet::GetGPUHandle(uint32_t index) const { if (m_heap == nullptr) { return D3D12_GPU_DESCRIPTOR_HANDLE{0}; @@ -65,5 +67,14 @@ D3D12_GPU_DESCRIPTOR_HANDLE D3D12DescriptorSet::GetGPUHandle(uint32_t index) con return D3D12_GPU_DESCRIPTOR_HANDLE{ handle.ptr }; } +void D3D12DescriptorSet::WriteConstant(uint32_t binding, const void* data, size_t size, size_t offset) { + size_t requiredSize = offset + size; + if (m_constantBufferData.size() < requiredSize) { + m_constantBufferData.resize(requiredSize); + } + memcpy(m_constantBufferData.data() + offset, data, size); + m_constantBufferDirty = true; +} + } // namespace RHI } // namespace XCEngine \ No newline at end of file diff --git a/engine/src/RHI/OpenGL/OpenGLCommandList.cpp b/engine/src/RHI/OpenGL/OpenGLCommandList.cpp index e566fdda..1d00776e 100644 --- a/engine/src/RHI/OpenGL/OpenGLCommandList.cpp +++ b/engine/src/RHI/OpenGL/OpenGLCommandList.cpp @@ -612,8 +612,7 @@ void OpenGLCommandList::SetGraphicsDescriptorSets( for (uint32_t i = 0; i < count; ++i) { if (descriptorSets[i] != nullptr) { - OpenGLDescriptorSet* glSet = static_cast(descriptorSets[i]); - glSet->Bind(); + descriptorSets[i]->Bind(); } } } @@ -628,8 +627,7 @@ void OpenGLCommandList::SetComputeDescriptorSets( for (uint32_t i = 0; i < count; ++i) { if (descriptorSets[i] != nullptr) { - OpenGLDescriptorSet* glSet = static_cast(descriptorSets[i]); - glSet->Bind(); + descriptorSets[i]->Bind(); } } } diff --git a/engine/src/RHI/OpenGL/OpenGLDescriptorSet.cpp b/engine/src/RHI/OpenGL/OpenGLDescriptorSet.cpp index 0a4c8606..a856f160 100644 --- a/engine/src/RHI/OpenGL/OpenGLDescriptorSet.cpp +++ b/engine/src/RHI/OpenGL/OpenGLDescriptorSet.cpp @@ -32,7 +32,7 @@ bool OpenGLDescriptorSet::Initialize(OpenGLTextureUnitAllocator* allocator, uint m_bindings.resize(layout.bindingCount); for (uint32_t i = 0; i < layout.bindingCount; ++i) { m_bindings[i].binding = layout.bindings[i].binding; - m_bindings[i].type = layout.bindings[i].type; + m_bindings[i].type = static_cast(layout.bindings[i].type); m_bindings[i].count = layout.bindings[i].count; m_bindings[i].textureUnits.resize(layout.bindings[i].count); m_bindings[i].textureIds.resize(layout.bindings[i].count, 0); @@ -52,6 +52,11 @@ bool OpenGLDescriptorSet::Initialize(OpenGLTextureUnitAllocator* allocator, uint } void OpenGLDescriptorSet::Shutdown() { + if (m_constantBuffer != 0) { + glDeleteBuffers(1, reinterpret_cast(&m_constantBuffer)); + m_constantBuffer = 0; + } + if (m_allocator != nullptr) { for (auto& binding : m_bindings) { for (uint32_t i = 0; i < binding.textureUnits.size(); ++i) { @@ -107,9 +112,19 @@ void OpenGLDescriptorSet::UpdateSampler(uint32_t offset, RHISampler* sampler) { } void OpenGLDescriptorSet::Bind() { + if (m_constantBufferDirty && !m_constantBufferData.empty()) { + if (m_constantBuffer == 0) { + glGenBuffers(1, reinterpret_cast(&m_constantBuffer)); + } + glBindBuffer(GL_UNIFORM_BUFFER, m_constantBuffer); + glBufferData(GL_UNIFORM_BUFFER, m_constantBufferData.size(), m_constantBufferData.data(), GL_DYNAMIC_DRAW); + glBindBufferBase(GL_UNIFORM_BUFFER, 0, m_constantBuffer); + m_constantBufferDirty = false; + } + for (size_t i = 0; i < m_bindings.size(); ++i) { const auto& binding = m_bindings[i]; - + for (size_t j = 0; j < binding.textureUnits.size(); ++j) { uint32_t unit = binding.textureUnits[j]; uint32_t textureId = binding.textureIds[j]; @@ -133,6 +148,22 @@ void OpenGLDescriptorSet::Bind() { m_bound = true; } +void OpenGLDescriptorSet::Unbind() { + for (size_t i = 0; i < m_bindings.size(); ++i) { + const auto& binding = m_bindings[i]; + + for (size_t j = 0; j < binding.textureUnits.size(); ++j) { + uint32_t unit = binding.textureUnits[j]; + + glActiveTexture(GL_TEXTURE0 + unit); + glBindTexture(GL_TEXTURE_2D, 0); + glBindSampler(unit, 0); + } + } + + m_bound = false; +} + uint32_t OpenGLDescriptorSet::GetBindingPoint(uint32_t binding) const { for (size_t i = 0; i < m_bindings.size(); ++i) { if (m_bindings[i].binding == binding && !m_bindings[i].textureUnits.empty()) { @@ -142,5 +173,14 @@ uint32_t OpenGLDescriptorSet::GetBindingPoint(uint32_t binding) const { return 0; } +void OpenGLDescriptorSet::WriteConstant(uint32_t binding, const void* data, size_t size, size_t offset) { + size_t requiredSize = offset + size; + if (m_constantBufferData.size() < requiredSize) { + m_constantBufferData.resize(requiredSize); + } + memcpy(m_constantBufferData.data() + offset, data, size); + m_constantBufferDirty = true; +} + } // namespace RHI } // namespace XCEngine \ No newline at end of file