diff --git a/CopiumEngine/CopiumEngine.vcxproj b/CopiumEngine/CopiumEngine.vcxproj index e000edb..ddb9bb3 100644 --- a/CopiumEngine/CopiumEngine.vcxproj +++ b/CopiumEngine/CopiumEngine.vcxproj @@ -201,8 +201,11 @@ + + + @@ -283,6 +286,7 @@ + diff --git a/CopiumEngine/CopiumEngine.vcxproj.filters b/CopiumEngine/CopiumEngine.vcxproj.filters index 5257914..8da5e80 100644 --- a/CopiumEngine/CopiumEngine.vcxproj.filters +++ b/CopiumEngine/CopiumEngine.vcxproj.filters @@ -216,6 +216,15 @@ Source Files + + Header Files + + + Source Files + + + Source Files + @@ -467,5 +476,8 @@ Header Files + + Header Files + \ No newline at end of file diff --git a/CopiumEngine/src/copium/pipeline/Pipeline.cpp b/CopiumEngine/src/copium/pipeline/Pipeline.cpp index 619913f..f2cd628 100644 --- a/CopiumEngine/src/copium/pipeline/Pipeline.cpp +++ b/CopiumEngine/src/copium/pipeline/Pipeline.cpp @@ -7,6 +7,7 @@ #include "copium/renderer/RendererVertex.h" #include "copium/mesh/VertexPassthrough.h" #include "copium/mesh/Vertex.h" +#include "copium/renderer/LineVertex.h" #include "copium/util/FileSystem.h" namespace Copium @@ -44,6 +45,11 @@ namespace Copium creator.SetVertexDescriptor(Vertex::GetDescriptor()); creator.SetBlending(metaFileClass.GetValue("alpha-blending", "false") == "true" ? true : false); } + else if (type == "LineRenderer") + { + creator.SetVertexDescriptor(LineVertex::GetDescriptor()); + creator.SetPrimitiveTopology(VK_PRIMITIVE_TOPOLOGY_LINE_LIST); + } InitializeDescriptorSetLayout(creator); InitializePipeline(creator); } diff --git a/CopiumEngine/src/copium/pipeline/PipelineCreator.h b/CopiumEngine/src/copium/pipeline/PipelineCreator.h index 8c11ee0..f2a66f9 100644 --- a/CopiumEngine/src/copium/pipeline/PipelineCreator.h +++ b/CopiumEngine/src/copium/pipeline/PipelineCreator.h @@ -28,12 +28,12 @@ namespace Copium ShaderReflector shaderReflector; VertexDescriptor vertexDescriptor{}; - VkPrimitiveTopology topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST; - VkCullModeFlags cullMode = VK_CULL_MODE_FRONT_BIT; - VkFrontFace frontFace = VK_FRONT_FACE_CLOCKWISE; - VkRenderPass renderPass = VK_NULL_HANDLE; - bool depthTest = true; - bool blending = false; + VkPrimitiveTopology topology{VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST}; + VkCullModeFlags cullMode{VK_CULL_MODE_FRONT_BIT}; + VkFrontFace frontFace{VK_FRONT_FACE_CLOCKWISE}; + VkRenderPass renderPass{VK_NULL_HANDLE}; + bool depthTest{true}; + bool blending{false}; public: PipelineCreator(VkRenderPass renderPass, const std::string& vertexShader, const std::string& fragmentShader); diff --git a/CopiumEngine/src/copium/renderer/LineRenderer.cpp b/CopiumEngine/src/copium/renderer/LineRenderer.cpp new file mode 100644 index 0000000..f3c3ea2 --- /dev/null +++ b/CopiumEngine/src/copium/renderer/LineRenderer.cpp @@ -0,0 +1,90 @@ +#include "copium/renderer/LineRenderer.h" + +#include "copium/asset/AssetManager.h" +#include "copium/core/Vulkan.h" +#include "copium/pipeline/PipelineCreator.h" + +namespace Copium +{ + static constexpr int MAX_NUM_LINES = 30000; + static constexpr int MAX_NUM_VERTICES = 2 * MAX_NUM_LINES; + + LineRenderer::LineRenderer(const AssetRef& pipeline) + : descriptorPool{}, + ibo{MAX_NUM_VERTICES}, + pipeline{pipeline}, + vertexBuffer{LineVertex::GetDescriptor(), MAX_NUM_VERTICES} + { + InitializeIndexBuffer(); + } + + LineRenderer::~LineRenderer() = default; + + void LineRenderer::Draw(const glm::vec3& from, const glm::vec3& to, const glm::vec3& color) + { + AllocateLine(); + AddVertex(from, color); + AddVertex(to, color); + } + + void LineRenderer::AddVertex(const glm::vec3& position, const glm::vec3& color) + { + LineVertex* vertex = (LineVertex*)mappedVertexBuffer; + vertex->pos = position; + vertex->color = color; + mappedVertexBuffer = (LineVertex*)mappedVertexBuffer + 1; + } + + void LineRenderer::Begin(CommandBuffer& commandBuffer) + { + Pipeline& pl = pipeline.GetAsset(); + pl.Bind(commandBuffer); + ibo.Bind(commandBuffer); + mappedVertexBuffer = (char*)vertexBuffer.Map() + vertexBuffer.GetPosition(Vulkan::GetSwapChain().GetFlightIndex()); + lineCount = 0; + currentCommandBuffer = &commandBuffer; + } + + void LineRenderer::End() + { + Flush(); + } + + Pipeline& LineRenderer::GetGraphicsPipeline() + { + return pipeline.GetAsset(); + } + + void LineRenderer::SetDescriptorSet(const DescriptorSet& descriptorSet) + { + pipeline.GetAsset().SetDescriptorSet(descriptorSet); + } + + void LineRenderer::InitializeIndexBuffer() + { + CP_ASSERT(MAX_NUM_VERTICES < std::numeric_limits::max(), "Maximum number of indices too big"); + + std::vector indices; + indices.resize(MAX_NUM_VERTICES); + for (int i = 0; i < MAX_NUM_VERTICES; i++) + { + indices[i] = i; + } + ibo.UpdateStaging(indices.data()); + } + + void LineRenderer::AllocateLine() + { + CP_ASSERT(lineCount + 1 <= MAX_NUM_LINES, "Max number of lines reached in LineRenderer"); + lineCount++; + } + + void LineRenderer::Flush() + { + vertexBuffer.Unmap(); + vertexBuffer.Bind(*currentCommandBuffer); + Pipeline& pl = pipeline.GetAsset(); + pl.BindDescriptorSets(*currentCommandBuffer); + ibo.Draw(*currentCommandBuffer, lineCount * 2); + } +} \ No newline at end of file diff --git a/CopiumEngine/src/copium/renderer/LineRenderer.h b/CopiumEngine/src/copium/renderer/LineRenderer.h new file mode 100644 index 0000000..b269280 --- /dev/null +++ b/CopiumEngine/src/copium/renderer/LineRenderer.h @@ -0,0 +1,49 @@ +#pragma once + +#include "copium/buffer/CommandBuffer.h" +#include "copium/buffer/IndexBuffer.h" +#include "copium/buffer/RendererVertexBuffer.h" +#include "copium/renderer/LineVertex.h" +#include "copium/pipeline/Pipeline.h" +#include "copium/util/Common.h" + +#include +#include + +namespace Copium +{ + class LineRenderer + { + CP_DELETE_COPY_AND_MOVE_CTOR(LineRenderer); + public: + LineRenderer(const AssetRef& pipeline); + ~LineRenderer(); + + void Draw(const glm::vec3& from, const glm::vec3& to, const glm::vec3& color = glm::vec3{1, 1, 1}); + + void Begin(CommandBuffer& commandBuffer); + void End(); + + Pipeline& GetGraphicsPipeline(); + void SetDescriptorSet(const DescriptorSet& descriptorSet); + + private: + DescriptorPool descriptorPool; + IndexBuffer ibo; + AssetRef pipeline; + + RendererVertexBuffer vertexBuffer; + + // Temporary data during a render + CommandBuffer* currentCommandBuffer; + int lineCount; + void* mappedVertexBuffer; + private: + void InitializeIndexBuffer(); + + void AllocateLine(); + void Flush(); + + void AddVertex(const glm::vec3& position, const glm::vec3& color); + }; +} diff --git a/CopiumEngine/src/copium/renderer/LineVertex.cpp b/CopiumEngine/src/copium/renderer/LineVertex.cpp new file mode 100644 index 0000000..2767aba --- /dev/null +++ b/CopiumEngine/src/copium/renderer/LineVertex.cpp @@ -0,0 +1,12 @@ +#include "copium/renderer/LineVertex.h" + +namespace Copium +{ + VertexDescriptor LineVertex::GetDescriptor() + { + VertexDescriptor descriptor{}; + descriptor.AddAttribute(0, 0, VK_FORMAT_R32G32B32_SFLOAT, offsetof(LineVertex, pos), sizeof(LineVertex)); + descriptor.AddAttribute(0, 1, VK_FORMAT_R32G32B32_SFLOAT, offsetof(LineVertex, color), sizeof(LineVertex)); + return descriptor; + } +} \ No newline at end of file diff --git a/CopiumEngine/src/copium/renderer/LineVertex.h b/CopiumEngine/src/copium/renderer/LineVertex.h new file mode 100644 index 0000000..7f451bf --- /dev/null +++ b/CopiumEngine/src/copium/renderer/LineVertex.h @@ -0,0 +1,16 @@ +#pragma once + +#include "copium/pipeline/VertexDescriptor.h" + +#include + +namespace Copium +{ + struct LineVertex + { + glm::vec3 pos; + glm::vec3 color; + + static VertexDescriptor GetDescriptor(); + }; +}