From caf7997f36e4720736436fc720611b3358aa1e83 Mon Sep 17 00:00:00 2001 From: Sebastian Gaida <gaida@ca-digit.com> Date: Tue, 6 Jul 2021 12:58:13 +0200 Subject: [PATCH] [#87] add bunny into scene --- include/vkcv/DrawcallRecording.hpp | 11 +- projects/mesh_shader/CMakeLists.txt | 2 +- .../mesh_shader/resources/Bunny/Bunny.gltf | 3 + .../mesh_shader/resources/shaders/shader.frag | 4 +- .../mesh_shader/resources/shaders/shader.vert | 21 ++-- projects/mesh_shader/src/main.cpp | 111 +++++++++++++----- projects/mesh_shader/src/mesh.hpp | 5 + src/vkcv/DrawcallRecording.cpp | 13 +- 8 files changed, 124 insertions(+), 46 deletions(-) create mode 100644 projects/mesh_shader/resources/Bunny/Bunny.gltf create mode 100644 projects/mesh_shader/src/mesh.hpp diff --git a/include/vkcv/DrawcallRecording.hpp b/include/vkcv/DrawcallRecording.hpp index 50fb0846..c0ad2250 100644 --- a/include/vkcv/DrawcallRecording.hpp +++ b/include/vkcv/DrawcallRecording.hpp @@ -12,6 +12,11 @@ namespace vkcv { vk::Buffer buffer; }; + enum class IndexBitCount{ + Bit16, + Bit32 + }; + struct DescriptorSetUsage { inline DescriptorSetUsage(uint32_t setLocation, vk::DescriptorSet vulkanHandle) noexcept : setLocation(setLocation), vulkanHandle(vulkanHandle) {} @@ -21,12 +26,14 @@ namespace vkcv { }; struct Mesh { - inline Mesh(std::vector<VertexBufferBinding> vertexBufferBindings, vk::Buffer indexBuffer, size_t indexCount) noexcept - : vertexBufferBindings(vertexBufferBindings), indexBuffer(indexBuffer), indexCount(indexCount){} + inline Mesh(std::vector<VertexBufferBinding> vertexBufferBindings, vk::Buffer indexBuffer, size_t indexCount, IndexBitCount indexBitCount = IndexBitCount::Bit16) noexcept + : vertexBufferBindings(vertexBufferBindings), indexBuffer(indexBuffer), indexCount(indexCount), indexBitCount(indexBitCount){} std::vector<VertexBufferBinding> vertexBufferBindings; vk::Buffer indexBuffer; size_t indexCount; + IndexBitCount indexBitCount; + }; struct PushConstantData { diff --git a/projects/mesh_shader/CMakeLists.txt b/projects/mesh_shader/CMakeLists.txt index 0b2847cd..ba9ce472 100644 --- a/projects/mesh_shader/CMakeLists.txt +++ b/projects/mesh_shader/CMakeLists.txt @@ -25,4 +25,4 @@ endif() target_include_directories(mesh_shader SYSTEM BEFORE PRIVATE ${vkcv_include} ${vkcv_includes} ${vkcv_testing_include} ${vkcv_camera_include} ${vkcv_shader_compiler_include} ${vkcv_gui_include}) # linking with libraries from all dependencies and the VkCV framework -target_link_libraries(mesh_shader vkcv vkcv_testing vkcv_camera vkcv_shader_compiler vkcv_gui) +target_link_libraries(mesh_shader vkcv ${vkcv_libraries} vkcv_asset_loader ${vkcv_asset_loader_libraries} vkcv_testing vkcv_camera vkcv_shader_compiler vkcv_gui) \ No newline at end of file diff --git a/projects/mesh_shader/resources/Bunny/Bunny.gltf b/projects/mesh_shader/resources/Bunny/Bunny.gltf new file mode 100644 index 00000000..3b5eefbc --- /dev/null +++ b/projects/mesh_shader/resources/Bunny/Bunny.gltf @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:97970b941a690d4538c8d8989dd5a8bfae180bb117ba7e22c59e0a4d119e5a2f +size 5395743 diff --git a/projects/mesh_shader/resources/shaders/shader.frag b/projects/mesh_shader/resources/shaders/shader.frag index 37a98da8..11d4f36e 100644 --- a/projects/mesh_shader/resources/shaders/shader.frag +++ b/projects/mesh_shader/resources/shaders/shader.frag @@ -2,8 +2,10 @@ #extension GL_ARB_separate_shader_objects : enable layout(location = 0) in vec3 VertexColor; +layout(location = 1) in vec3 passNormal; layout(location = 0) out vec4 outColor; void main() { - outColor = vec4(VertexColor, 1); + vec3 vis = normalize(passNormal) * 0.5 +0.5; + outColor = vec4(vis , 1); } \ No newline at end of file diff --git a/projects/mesh_shader/resources/shaders/shader.vert b/projects/mesh_shader/resources/shaders/shader.vert index e129186a..425fc412 100644 --- a/projects/mesh_shader/resources/shaders/shader.vert +++ b/projects/mesh_shader/resources/shaders/shader.vert @@ -1,25 +1,18 @@ #version 450 #extension GL_ARB_separate_shader_objects : enable +layout(location = 0) in vec3 inPosition; +layout(location = 1) in vec3 inNormal; + layout(location = 0) out vec3 fragColor; +layout(location = 1) out vec3 passNormal; layout( push_constant ) uniform constants{ mat4 mvp; }; void main() { - vec3 positions[3] = { - vec3(-0.5, 0.5, -1), - vec3( 0.5, 0.5, -1), - vec3(0, -0.5, -1) - }; - - vec3 colors[3] = { - vec3(1, 0, 0), - vec3(0, 1, 0), - vec3(0, 0, 1) - }; - - gl_Position = mvp * vec4(positions[gl_VertexIndex], 1.0); - fragColor = colors[gl_VertexIndex]; + gl_Position = mvp * vec4(inPosition, 1.0); + passNormal = inNormal; + fragColor = vec3(1.f); } \ No newline at end of file diff --git a/projects/mesh_shader/src/main.cpp b/projects/mesh_shader/src/main.cpp index 8a423345..f1dffa05 100644 --- a/projects/mesh_shader/src/main.cpp +++ b/projects/mesh_shader/src/main.cpp @@ -6,6 +6,7 @@ #include <vkcv/shader/GLSLCompiler.hpp> #include <vkcv/gui/GUI.hpp> +#include <vkcv/asset/asset_loader.hpp> int main(int argc, const char** argv) { const char* applicationName = "Mesh shader"; @@ -27,20 +28,52 @@ int main(int argc, const char** argv) { {}, { "VK_KHR_swapchain", VK_NV_MESH_SHADER_EXTENSION_NAME } ); - - vkcv::gui::GUI gui (core, window); - const auto& context = core.getContext(); - const vk::Instance& instance = context.getInstance(); - const vk::PhysicalDevice& physicalDevice = context.getPhysicalDevice(); - const vk::Device& device = context.getDevice(); + vkcv::gui::GUI gui (core, window); + + const auto& context = core.getContext(); + const vk::Instance& instance = context.getInstance(); + const vk::PhysicalDevice& physicalDevice = context.getPhysicalDevice(); + const vk::Device& device = context.getDevice(); + + vkcv::asset::Scene mesh; + const char* path = argc > 1 ? argv[1] : "resources/Bunny/Bunny.gltf"; + vkcv::asset::loadScene(path, mesh); + + assert(!mesh.vertexGroups.empty()); + + auto vertexBuffer = core.createBuffer<uint8_t>( + vkcv::BufferType::VERTEX, + mesh.vertexGroups[0].vertexBuffer.data.size(), + vkcv::BufferMemoryType::DEVICE_LOCAL + ); + vertexBuffer.fill(mesh.vertexGroups[0].vertexBuffer.data); + + auto indexBuffer = core.createBuffer<uint8_t>( + vkcv::BufferType::INDEX, + mesh.vertexGroups[0].indexBuffer.data.size(), + vkcv::BufferMemoryType::DEVICE_LOCAL + ); + indexBuffer.fill(mesh.vertexGroups[0].indexBuffer.data); + + auto& attributes = mesh.vertexGroups[0].vertexBuffer.attributes; + + std::sort(attributes.begin(), attributes.end(), [](const vkcv::asset::VertexAttribute& x, const vkcv::asset::VertexAttribute& y) { + return static_cast<uint32_t>(x.type) < static_cast<uint32_t>(y.type); + }); const vkcv::AttachmentDescription present_color_attachment( vkcv::AttachmentOperation::STORE, vkcv::AttachmentOperation::CLEAR, core.getSwapchain().getFormat()); - vkcv::PassConfig trianglePassDefinition({ present_color_attachment }); + const vkcv::AttachmentDescription depth_attachment( + vkcv::AttachmentOperation::STORE, + vkcv::AttachmentOperation::CLEAR, + vk::Format::eD32Sfloat + ); + + vkcv::PassConfig trianglePassDefinition({ present_color_attachment, depth_attachment }); vkcv::PassHandle renderPass = core.createPass(trianglePassDefinition); if (!renderPass) @@ -49,30 +82,41 @@ int main(int argc, const char** argv) { return EXIT_FAILURE; } - vkcv::ShaderProgram triangleShaderProgram{}; + vkcv::ShaderProgram bunnyShaderProgram{}; vkcv::shader::GLSLCompiler compiler; compiler.compile(vkcv::ShaderStage::VERTEX, std::filesystem::path("resources/shaders/shader.vert"), - [&triangleShaderProgram](vkcv::ShaderStage shaderStage, const std::filesystem::path& path) { - triangleShaderProgram.addShader(shaderStage, path); + [&bunnyShaderProgram](vkcv::ShaderStage shaderStage, const std::filesystem::path& path) { + bunnyShaderProgram.addShader(shaderStage, path); }); compiler.compile(vkcv::ShaderStage::FRAGMENT, std::filesystem::path("resources/shaders/shader.frag"), - [&triangleShaderProgram](vkcv::ShaderStage shaderStage, const std::filesystem::path& path) { - triangleShaderProgram.addShader(shaderStage, path); + [&bunnyShaderProgram](vkcv::ShaderStage shaderStage, const std::filesystem::path& path) { + bunnyShaderProgram.addShader(shaderStage, path); }); - const vkcv::PipelineConfig trianglePipelineDefinition { - triangleShaderProgram, - (uint32_t)windowWidth, - (uint32_t)windowHeight, - renderPass, - {}, - {}, - false + const std::vector<vkcv::VertexAttachment> vertexAttachments = bunnyShaderProgram.getVertexAttachments(); + std::vector<vkcv::VertexBinding> bindings; + for (size_t i = 0; i < vertexAttachments.size(); i++) { + bindings.push_back(vkcv::VertexBinding(i, { vertexAttachments[i] })); + } + const vkcv::VertexLayout meshShaderLayout (bindings); + + uint32_t setID = 0; +// std::vector<vkcv::DescriptorBinding> descriptorBindings = {bunnyShaderProgram.getReflectedDescriptors()[setID] }; +// vkcv::DescriptorSetHandle descriptorSet = core.createDescriptorSet(descriptorBindings); + + const vkcv::PipelineConfig bunnyPipelineDefinition { + bunnyShaderProgram, + (uint32_t)windowWidth, + (uint32_t)windowHeight, + renderPass, + { meshShaderLayout }, + {}, + false }; - vkcv::PipelineHandle trianglePipeline = core.createGraphicsPipeline(trianglePipelineDefinition); + vkcv::PipelineHandle trianglePipeline = core.createGraphicsPipeline(bunnyPipelineDefinition); if (!trianglePipeline) { @@ -115,12 +159,23 @@ int main(int argc, const char** argv) { return EXIT_FAILURE; } - auto start = std::chrono::system_clock::now(); + const std::vector<vkcv::VertexBufferBinding> vertexBufferBindings = { + vkcv::VertexBufferBinding(static_cast<vk::DeviceSize>(attributes[0].offset), vertexBuffer.getVulkanHandle()), + vkcv::VertexBufferBinding(static_cast<vk::DeviceSize>(attributes[1].offset), vertexBuffer.getVulkanHandle()), + vkcv::VertexBufferBinding(static_cast<vk::DeviceSize>(attributes[2].offset), vertexBuffer.getVulkanHandle()) }; + + vkcv::DescriptorWrites setWrites; + + vkcv::ImageHandle depthBuffer = core.createImage(vk::Format::eD32Sfloat, windowWidth, windowHeight, 1, false).getHandle(); + + auto start = std::chrono::system_clock::now(); vkcv::ImageHandle swapchainImageHandle = vkcv::ImageHandle::createSwapchainImageHandle(); - const vkcv::Mesh renderMesh({}, nullptr, 3); - vkcv::DrawcallInfo drawcall(renderMesh, {}); + const vkcv::Mesh renderMesh(vertexBufferBindings, indexBuffer.getVulkanHandle(), mesh.vertexGroups[0].numIndices, vkcv::IndexBitCount::Bit32); + +// vkcv::DescriptorSetUsage descriptorUsage(0, core.getDescriptorSet(descriptorSet).vulkanHandle); + vkcv::DrawcallInfo drawcall(renderMesh, {}); const vkcv::ImageHandle swapchainInput = vkcv::ImageHandle::createSwapchainImageHandle(); @@ -146,8 +201,11 @@ int main(int argc, const char** argv) { glm::mat4 mvp = cameraManager.getActiveCamera().getMVP(); vkcv::PushConstantData pushConstantData((void*)&mvp, sizeof(glm::mat4)); + + const std::vector<vkcv::ImageHandle> renderTargets = { swapchainInput, depthBuffer }; auto cmdStream = core.createCommandStream(vkcv::QueueType::Graphics); + /* core.recordMeshShaderDrawcalls( cmdStream, renderPass, @@ -155,16 +213,15 @@ int main(int argc, const char** argv) { pushConstantData, { vkcv::MeshShaderDrawcall({}, 1) }, { swapchainInput }); + */ - /* core.recordDrawcallsToCmdStream( cmdStream, renderPass, trianglePipeline, pushConstantData, { drawcall }, - { swapchainInput }); - */ + { renderTargets }); core.prepareSwapchainImageForPresent(cmdStream); core.submitCommandStream(cmdStream); diff --git a/projects/mesh_shader/src/mesh.hpp b/projects/mesh_shader/src/mesh.hpp new file mode 100644 index 00000000..9a21bb4f --- /dev/null +++ b/projects/mesh_shader/src/mesh.hpp @@ -0,0 +1,5 @@ +#pragma once + +struct Mesh{ + +}; \ No newline at end of file diff --git a/src/vkcv/DrawcallRecording.cpp b/src/vkcv/DrawcallRecording.cpp index bfea043d..86eaa0a5 100644 --- a/src/vkcv/DrawcallRecording.cpp +++ b/src/vkcv/DrawcallRecording.cpp @@ -1,7 +1,18 @@ #include <vkcv/DrawcallRecording.hpp> +#include <vkcv/Logger.hpp> namespace vkcv { + vk::IndexType getIndexType(IndexBitCount indexByteCount){ + switch (indexByteCount) { + case IndexBitCount::Bit16: return vk::IndexType::eUint16; + case IndexBitCount::Bit32: return vk::IndexType::eUint32; + default: + vkcv_log(LogLevel::ERROR, "unknown Enum"); + return vk::IndexType::eUint16; + } + } + void recordDrawcall( const DrawcallInfo &drawcall, vk::CommandBuffer cmdBuffer, @@ -35,7 +46,7 @@ namespace vkcv { drawcallPushConstantData); if (drawcall.mesh.indexBuffer) { - cmdBuffer.bindIndexBuffer(drawcall.mesh.indexBuffer, 0, vk::IndexType::eUint16); //FIXME: choose proper size + cmdBuffer.bindIndexBuffer(drawcall.mesh.indexBuffer, 0, getIndexType(drawcall.mesh.indexBitCount)); cmdBuffer.drawIndexed(drawcall.mesh.indexCount, 1, 0, 0, {}); } else { -- GitLab