Cleaned up UI rects into UILayers which contain batches of rects to be drawn

main
noah metz 2024-10-13 15:44:33 -06:00
parent 4c2bade162
commit b2a8d283f6
5 changed files with 73 additions and 73 deletions

@ -11,14 +11,27 @@ typedef struct GraphicsPipelineStruct {
VkPipeline pipeline;
} GraphicsPipeline;
struct UIRect {
typedef struct ColoredRectStruct {
vec3 pos;
vec2 size;
vec4 color;
};
} ColoredRect;
struct UIUniform {
typedef struct UIUniformStruct {
mat4 screen;
} UIUniform;
typedef struct UILayerStruct {
VkBuffer colored_rects;
uint32_t colored_rect_count;
} UILayer;
struct RectBuffer {
VkBuffer vertex;
VkBuffer index;
VmaAllocation vertex_memory;
VmaAllocation index_memory;
};
VkResult create_ui_rect_pipeline(VkDevice device, VkRenderPass render_pass, VkDescriptorSetLayout descriptor_layout, GraphicsPipeline* pipeline);
@ -26,6 +39,6 @@ VkResult create_ui_rect_pipeline(VkDevice device, VkRenderPass render_pass, VkDe
VkResult create_ui_descriptor_set(VkDevice device, VmaAllocator allocator, VkExtent2D swapchain_extent, VkDescriptorSetLayout* ui_descriptor_layout, VkDescriptorPool* ui_descriptor_pool, VkDescriptorSet* ui_descriptor_set, VmaAllocation* ui_descriptor_memory, VkBuffer* ui_descriptor_buffer);
VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandPool transfer_pool, VmaAllocator allocator, VkBuffer* vertex_buffer, VkBuffer* index_buffer, VmaAllocation* vertex_memory, VmaAllocation* index_memory);
VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandPool transfer_pool, VmaAllocator allocator, struct RectBuffer* buf);
#endif

@ -84,6 +84,7 @@ typedef struct RenderContextStruct {
VkDescriptorPool ui_descriptor_pool;
VkDescriptorSet ui_descriptor_set;
struct RectBuffer ui_rect;
GraphicsPipeline ui_pipeline_rect;
GraphicsPipeline ui_pipeline_text;
@ -92,6 +93,6 @@ typedef struct RenderContextStruct {
GLFWwindow* init_window();
VkResult init_vulkan(GLFWwindow* window, RenderContext* context);
VkResult draw_frame(RenderContext* context, VkBuffer ui_rect_vertex, VkBuffer ui_rect_index, VkBuffer ui_rects, uint32_t rect_count);
VkResult draw_frame(RenderContext* context, UILayer* ui_layers, uint32_t ui_layer_count);
#endif

@ -3,78 +3,57 @@
#include "vk_mem_alloc.h"
#include "vulkan/vk_enum_string_helper.h"
ColoredRect colored_rect(float width, float height, float r, float g, float b, float a, float x, float y, float z) {
ColoredRect rect = {
.size = {width, height},
.pos = {x, y, z},
.color = {r, g, b, a},
};
return rect;
}
VkResult render_thread(GLFWwindow* window, RenderContext* render_context) {
VkBuffer test_ui_buffer;
VmaAllocation test_ui_memory;
VkBuffer colored_rect_buffer;
VmaAllocation colored_rect_memory;
VkBufferCreateInfo test_ui_buffer_info = {
VkBufferCreateInfo colored_rect_buffer_info = {
.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,
.usage = VK_BUFFER_USAGE_VERTEX_BUFFER_BIT,
.size = 3*sizeof(struct UIRect),
.size = 3*sizeof(ColoredRect),
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
};
VmaAllocationCreateInfo test_ui_memory_info = {
VmaAllocationCreateInfo colored_rect_memory_info = {
.usage = VMA_MEMORY_USAGE_CPU_TO_GPU,
};
VkResult result = vmaCreateBuffer(render_context->allocator, &test_ui_buffer_info, &test_ui_memory_info, &test_ui_buffer, &test_ui_memory, NULL);
VkResult result = vmaCreateBuffer(render_context->allocator, &colored_rect_buffer_info, &colored_rect_memory_info, &colored_rect_buffer, &colored_rect_memory, NULL);
if(result != VK_SUCCESS) {
return result;
}
struct UIRect* mapped;
ColoredRect* colored_rects;
result = vmaMapMemory(render_context->allocator, test_ui_memory, (void**)&mapped);
result = vmaMapMemory(render_context->allocator, colored_rect_memory, (void**)&colored_rects);
if(result != VK_SUCCESS) {
return result;
}
mapped[0].size[0] = 100;
mapped[0].size[1] = 100;
mapped[0].color[0] = 1.0;
mapped[0].color[1] = 0.0;
mapped[0].color[2] = 0.0;
mapped[0].color[3] = 1.0;
mapped[0].pos[0] = 0.0;
mapped[0].pos[1] = 0.0;
mapped[0].pos[2] = 0.5;
mapped[1].size[0] = 100;
mapped[1].size[1] = 100;
mapped[1].color[0] = 0.0;
mapped[1].color[1] = 1.0;
mapped[1].color[2] = 0.0;
mapped[1].color[3] = 1.0;
mapped[1].pos[0] = 100;
mapped[1].pos[1] = 0.0;
mapped[1].pos[2] = 0.5;
mapped[2].size[0] = 100;
mapped[2].size[1] = 100;
mapped[2].color[0] = 0.0;
mapped[2].color[1] = 0.0;
mapped[2].color[2] = 1.0;
mapped[2].color[3] = 1.0;
mapped[2].pos[0] = 0.0;
mapped[2].pos[1] = 100;
mapped[2].pos[2] = 0.5;
vmaUnmapMemory(render_context->allocator, test_ui_memory);
VmaAllocation rect_vertex_memory;
VmaAllocation rect_index_memory;
VkBuffer rect_vertex;
VkBuffer rect_index;
result = create_ui_rect_buffer(render_context->device, render_context->transfer_queue, render_context->transfer_pool, render_context->allocator, &rect_vertex, &rect_index, &rect_vertex_memory, &rect_index_memory);
if(result != VK_SUCCESS) {
return result;
}
colored_rects[0] = colored_rect(100.0, 100.0, 1.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.5);
colored_rects[1] = colored_rect(100.0, 100.0, 0.0, 1.0, 0.0, 1.0, 0.0, 100.0, 0.5);
colored_rects[2] = colored_rect(100.0, 100.0, 0.0, 0.0, 1.0, 1.0, 100.0, 0.0, 0.5);
vmaUnmapMemory(render_context->allocator, colored_rect_memory);
UILayer test_layer = {
.colored_rects = colored_rect_buffer,
.colored_rect_count = 3,
};
while(glfwWindowShouldClose(window) == 0) {
glfwPollEvents();
result = draw_frame(render_context, rect_vertex, rect_index, test_ui_buffer, 3);
result = draw_frame(render_context, &test_layer, 1);
if(result != VK_SUCCESS) {
fprintf(stderr, "draw_frame error: %s\n", string_VkResult(result));
return result;

@ -74,7 +74,7 @@ VkResult create_ui_rect_pipeline(VkDevice device, VkRenderPass render_pass, VkDe
},
{
.binding = 1,
.stride = sizeof(struct UIRect),
.stride = sizeof(ColoredRect),
.inputRate = VK_VERTEX_INPUT_RATE_INSTANCE,
},
};
@ -90,19 +90,19 @@ VkResult create_ui_rect_pipeline(VkDevice device, VkRenderPass render_pass, VkDe
.binding = 1,
.location = 1,
.format = VK_FORMAT_R32G32B32_SFLOAT,
.offset = offsetof(struct UIRect, pos),
.offset = offsetof(ColoredRect, pos),
},
{
.binding = 1,
.location = 2,
.format = VK_FORMAT_R32G32_SFLOAT,
.offset = offsetof(struct UIRect, size),
.offset = offsetof(ColoredRect, size),
},
{
.binding = 1,
.location = 3,
.format = VK_FORMAT_R32G32B32A32_SFLOAT,
.offset = offsetof(struct UIRect, color),
.offset = offsetof(ColoredRect, color),
},
};
@ -313,7 +313,7 @@ VkResult create_ui_descriptor_set(VkDevice device, VmaAllocator allocator, VkExt
VkBufferCreateInfo ui_uniform_buffer_info = {
.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO,
.usage = VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT,
.size = sizeof(struct UIUniform),
.size = sizeof(UIUniform),
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
};
@ -331,7 +331,7 @@ VkResult create_ui_descriptor_set(VkDevice device, VmaAllocator allocator, VkExt
if(result != VK_SUCCESS) {
return result;
}
struct UIUniform ui_uniform;
UIUniform ui_uniform;
vec3 screen_offset = {-1.0, -1.0, 0.0};
vec3 screen_scale = {1.0/(float)swapchain_extent.width, 1.0/(float)swapchain_extent.height, 1.0};
glm_mat4_identity(ui_uniform.screen);
@ -360,7 +360,7 @@ VkResult create_ui_descriptor_set(VkDevice device, VmaAllocator allocator, VkExt
return VK_SUCCESS;
}
VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandPool transfer_pool, VmaAllocator allocator, VkBuffer* vertex_buffer, VkBuffer* index_buffer, VmaAllocation* vertex_memory, VmaAllocation* index_memory) {
VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandPool transfer_pool, VmaAllocator allocator, struct RectBuffer* rect) {
uint32_t vertex_buffer_size = 4 * sizeof(vec2);
uint32_t index_buffer_size = 6 * sizeof(uint32_t);
@ -398,7 +398,7 @@ VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandP
.size = vertex_buffer_size,
};
result = vmaCreateBuffer(allocator, &vertex_buffer_info, &allocation_info, vertex_buffer, vertex_memory, NULL);
result = vmaCreateBuffer(allocator, &vertex_buffer_info, &allocation_info, &rect->vertex, &rect->vertex_memory, NULL);
if(result != VK_SUCCESS) {
return result;
}
@ -410,7 +410,7 @@ VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandP
.size = index_buffer_size,
};
result = vmaCreateBuffer(allocator, &index_buffer_info, &allocation_info, index_buffer, index_memory, NULL);
result = vmaCreateBuffer(allocator, &index_buffer_info, &allocation_info, &rect->index, &rect->index_memory, NULL);
if(result != VK_SUCCESS) {
return result;
}
@ -447,14 +447,14 @@ VkResult create_ui_rect_buffer(VkDevice device, Queue transfer_queue, VkCommandP
.dstOffset = 0,
.srcOffset = 0,
};
vkCmdCopyBuffer(copy_buffer, temp_buffer, *vertex_buffer, 1, &vertex_copy_region);
vkCmdCopyBuffer(copy_buffer, temp_buffer, rect->vertex, 1, &vertex_copy_region);
VkBufferCopy index_copy_region = {
.size = index_buffer_size,
.dstOffset = 0,
.srcOffset = vertex_buffer_size,
};
vkCmdCopyBuffer(copy_buffer, temp_buffer, *index_buffer, 1, &index_copy_region);
vkCmdCopyBuffer(copy_buffer, temp_buffer, rect->index, 1, &index_copy_region);
result = command_end_single(device, copy_buffer, transfer_pool, transfer_queue);
if(result != VK_SUCCESS) {

@ -954,11 +954,16 @@ VkResult init_vulkan(GLFWwindow* window, RenderContext* context) {
return result;
}
result = create_ui_rect_buffer(context->device, context->transfer_queue, context->transfer_pool, context->allocator, &context->ui_rect);
if(result != VK_SUCCESS) {
return result;
}
context->current_frame = 0;
return VK_SUCCESS;
}
VkResult draw_frame(RenderContext* context, VkBuffer ui_rect_vertex, VkBuffer ui_rect_index, VkBuffer ui_rects, uint32_t rect_count) {
VkResult draw_frame(RenderContext* context, UILayer* ui_layers, uint32_t ui_layer_count) {
VkResult result;
result = vkWaitForFences(context->device, 1, &context->in_flight_fences[context->current_frame], VK_TRUE, UINT64_MAX);
@ -992,6 +997,7 @@ VkResult draw_frame(RenderContext* context, VkBuffer ui_rect_vertex, VkBuffer ui
}
VkClearValue clear_values[2] = {{.color={{0.0f, 0.0f, 0.0f, 1.0f}}}, {.depthStencil={1.0f, 0.0f}}};
VkDeviceSize offset = 0;
// World Render Pass
VkRenderPassBeginInfo world_render_pass_begin = {
@ -1018,16 +1024,17 @@ VkResult draw_frame(RenderContext* context, VkBuffer ui_rect_vertex, VkBuffer ui
};
vkCmdBeginRenderPass(context->swapchain_command_buffers[context->current_frame], &ui_render_pass_begin, VK_SUBPASS_CONTENTS_INLINE);
// Draw UI rects //////////////////////////////
// Draw UI colored rects ////////////////////////////////
vkCmdBindPipeline(context->swapchain_command_buffers[context->current_frame], VK_PIPELINE_BIND_POINT_GRAPHICS, context->ui_pipeline_rect.pipeline);
vkCmdBindDescriptorSets(context->swapchain_command_buffers[context->current_frame], VK_PIPELINE_BIND_POINT_GRAPHICS, context->ui_pipeline_rect.layout, 0, 1, &context->ui_descriptor_set, 0, NULL);
VkDeviceSize offset = 0;
vkCmdBindVertexBuffers(context->swapchain_command_buffers[context->current_frame], 0, 1, &ui_rect_vertex, &offset);
vkCmdBindIndexBuffer(context->swapchain_command_buffers[context->current_frame], ui_rect_index, 0, VK_INDEX_TYPE_UINT32);
vkCmdBindVertexBuffers(context->swapchain_command_buffers[context->current_frame], 0, 1, &context->ui_rect.vertex, &offset);
vkCmdBindIndexBuffer(context->swapchain_command_buffers[context->current_frame], context->ui_rect.index, 0, VK_INDEX_TYPE_UINT32);
vkCmdBindVertexBuffers(context->swapchain_command_buffers[context->current_frame], 1, 1, &ui_rects, &offset);
vkCmdDrawIndexed(context->swapchain_command_buffers[context->current_frame], 6, rect_count, 0, 0, 0);
///////////////////////////////////////////////
for(uint32_t i = 0; i < ui_layer_count; i++) {
vkCmdBindVertexBuffers(context->swapchain_command_buffers[context->current_frame], 1, 1, &ui_layers[i].colored_rects, &offset);
vkCmdDrawIndexed(context->swapchain_command_buffers[context->current_frame], 6, ui_layers[i].colored_rect_count, 0, 0, 0);
}
/////////////////////////////////////////////////////////
vkCmdEndRenderPass(context->swapchain_command_buffers[context->current_frame]);