From 828f43701a14af8e5b67c759bfaee363fb326d4a Mon Sep 17 00:00:00 2001 From: Danny Robson Date: Thu, 7 Sep 2017 12:52:03 +1000 Subject: [PATCH] hello-tool: build geometry in buffer rather than shader --- tools/hello.cpp | 87 +++++++++++++++++++++++++++++++++++++++-- tools/hello/shader.vert | 23 ++++------- 2 files changed, 90 insertions(+), 20 deletions(-) diff --git a/tools/hello.cpp b/tools/hello.cpp index 80936f6..b88fef9 100644 --- a/tools/hello.cpp +++ b/tools/hello.cpp @@ -8,6 +8,8 @@ #include #include +#include +#include #include #include @@ -59,6 +61,21 @@ create_shader (cruft::vk::device &dev, const std::experimental::filesystem::path } +/////////////////////////////////////////////////////////////////////////////// +struct vertex_t { + util::point2f position; + util::colour3f colour; +}; + + +//----------------------------------------------------------------------------- +static constexpr vertex_t VERTICES[] = { + { { 0.0f, -0.5f }, { 1.0f, 0.0f, 0.0f } }, + { { 0.5f, 0.5f }, { 0.0f, 1.0f, 0.0f } }, + { {-0.5f, 0.5f }, { 0.0f, 0.0f, 1.0f } }, +}; + + /////////////////////////////////////////////////////////////////////////////// int main (void) @@ -274,6 +291,48 @@ main (void) auto vert_module = create_shader (ldevice, "./hello/shader.vert"); auto frag_module = create_shader (ldevice, "./hello/shader.frag"); + VkBufferCreateInfo buffer_info {}; + buffer_info.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO; + buffer_info.size = sizeof (VERTICES); + buffer_info.usage = VK_BUFFER_USAGE_VERTEX_BUFFER_BIT; + buffer_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE; + + VkBuffer vertex_buffer = cruft::vk::error::try_query ( + vkCreateBuffer, ldevice.id (), &buffer_info, nullptr + ); + + auto memory_requirements = cruft::vk::error::try_query ( + vkGetBufferMemoryRequirements, ldevice.id (), vertex_buffer + ); + + auto memory_properties = pdevice.memory_properties (); + + VkMemoryAllocateInfo allocate_info {}; + allocate_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO; + allocate_info.allocationSize = memory_requirements.size; + allocate_info.memoryTypeIndex = [&] () { + for (uint32_t i = 0; i < memory_properties.memoryTypeCount; ++i) { + if ((memory_requirements.memoryTypeBits & (1u << i)) && memory_properties.memoryTypes[i].propertyFlags & (VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT)) + return i; + } + + throw std::runtime_error ("no suitable memory type"); + } (); + + auto vertex_memory = cruft::vk::error::try_query ( + vkAllocateMemory, ldevice.id (), &allocate_info, nullptr + ); + + cruft::vk::error::try_code ( + vkBindBufferMemory (ldevice.id (), vertex_buffer, vertex_memory, 0) + ); + + auto data = cruft::vk::error::try_query ( + vkMapMemory, ldevice.id (), vertex_memory, 0, buffer_info.size, 0 + ); + memcpy (data, std::data (VERTICES), sizeof (VERTICES)); + vkUnmapMemory (ldevice.id (), vertex_memory); + VkPipelineShaderStageCreateInfo vert_stage_info {}; vert_stage_info.sType = cruft::vk::structure_type_v; vert_stage_info.stage = VK_SHADER_STAGE_VERTEX_BIT; @@ -288,12 +347,28 @@ main (void) vert_stage_info, frag_stage_info }; + VkVertexInputBindingDescription vertex_binding {}; + vertex_binding.binding = 0; + vertex_binding.stride = sizeof (vertex_t); + vertex_binding.inputRate = VK_VERTEX_INPUT_RATE_VERTEX; + + std::array vertex_attribute {}; + vertex_attribute[0].binding = 0; + vertex_attribute[0].location = 0; + vertex_attribute[0].format = VK_FORMAT_R32G32_SFLOAT; + vertex_attribute[0].offset = offsetof(vertex_t, position); + + vertex_attribute[1].binding = 0; + vertex_attribute[1].location = 1; + vertex_attribute[1].format = VK_FORMAT_R32G32B32_SFLOAT; + vertex_attribute[1].offset = offsetof (vertex_t, colour); + VkPipelineVertexInputStateCreateInfo vertex_input {}; vertex_input.sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO; - vertex_input.vertexBindingDescriptionCount = 0; - vertex_input.pVertexBindingDescriptions = nullptr; - vertex_input.vertexAttributeDescriptionCount = 0; - vertex_input.pVertexBindingDescriptions = nullptr; + vertex_input.vertexBindingDescriptionCount = 1; + vertex_input.pVertexBindingDescriptions = &vertex_binding; + vertex_input.vertexAttributeDescriptionCount = 2; + vertex_input.pVertexAttributeDescriptions = std::data (vertex_attribute); VkPipelineInputAssemblyStateCreateInfo assembly_info {}; assembly_info.sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO; @@ -494,6 +569,10 @@ main (void) vkCmdBindPipeline (command_buffers[i], VK_PIPELINE_BIND_POINT_GRAPHICS, graphics_pipeline); + VkBuffer buffers[] = {vertex_buffer}; + VkDeviceSize offsets[] = {0}; + vkCmdBindVertexBuffers (command_buffers[i], 0, 1, buffers, offsets); + vkCmdDraw (command_buffers[i], 3, 1, 0, 0); vkCmdEndRenderPass (command_buffers[i]); diff --git a/tools/hello/shader.vert b/tools/hello/shader.vert index d38f815..f77bced 100644 --- a/tools/hello/shader.vert +++ b/tools/hello/shader.vert @@ -1,25 +1,16 @@ #version 450 #extension GL_ARB_separate_shader_objects : enable +layout(location = 0) in vec2 inPosition; +layout(location = 1) in vec3 inColor; + +layout(location = 0) out vec3 fragColor; + out gl_PerVertex { vec4 gl_Position; }; -layout(location = 0) out vec3 fragColor; - -vec2 positions[3] = vec2[]( - vec2(0.0, -0.5), - vec2(0.5, 0.5), - vec2(-0.5, 0.5) -); - -vec3 colors[3] = vec3[]( - vec3(1.0, 0.0, 0.0), - vec3(0.0, 1.0, 0.0), - vec3(0.0, 0.0, 1.0) -); - void main() { - gl_Position = vec4(positions[gl_VertexIndex], 0.0, 1.0); - fragColor = colors[gl_VertexIndex]; + gl_Position = vec4(inPosition, 0.0, 1.0); + fragColor = inColor; }