vulkan init done, more added to the platform layer for interfacing with window
This commit is contained in:
parent
7bf35d0031
commit
5f235694cd
17
src/main.c
17
src/main.c
@ -20,6 +20,23 @@ int main(int argc, char **argv)
|
|||||||
Assert(CreateWindow(), "Failed to initialize the window");
|
Assert(CreateWindow(), "Failed to initialize the window");
|
||||||
Assert(InitRenderer(renderer_arena), "Failed to initialize the renderer");
|
Assert(InitRenderer(renderer_arena), "Failed to initialize the renderer");
|
||||||
|
|
||||||
|
b32 quit = false;
|
||||||
|
WindowEvent e;
|
||||||
|
while (!quit)
|
||||||
|
{
|
||||||
|
while (GetWindowEvent(&e))
|
||||||
|
{
|
||||||
|
switch (e.type)
|
||||||
|
{
|
||||||
|
case EVENT_QUIT:
|
||||||
|
quit = true;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
DestroyRenderer();
|
DestroyRenderer();
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
@ -91,3 +91,13 @@ Window *GetWindow()
|
|||||||
{
|
{
|
||||||
return _GetWindow();
|
return _GetWindow();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
b32 GetWindowEvent(WindowEvent *event)
|
||||||
|
{
|
||||||
|
return _GetWindowEvent(event);
|
||||||
|
}
|
||||||
|
|
||||||
|
WindowSize GetWindowSize()
|
||||||
|
{
|
||||||
|
return _GetWindowSize();
|
||||||
|
}
|
||||||
|
|||||||
@ -1,5 +1,9 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
typedef enum Event_e Event_e;
|
||||||
|
typedef struct WindowEvent WindowEvent;
|
||||||
|
typedef struct WindowSize WindowSize;
|
||||||
|
|
||||||
#if __linux__
|
#if __linux__
|
||||||
#include "platform_linux.h"
|
#include "platform_linux.h"
|
||||||
#endif
|
#endif
|
||||||
@ -16,6 +20,28 @@
|
|||||||
#error Not yet implemented
|
#error Not yet implemented
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
enum Event_e
|
||||||
|
{
|
||||||
|
EVENT_NONE = 0,
|
||||||
|
EVENT_QUIT,
|
||||||
|
EVENT_RESIZE,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct WindowSize
|
||||||
|
{
|
||||||
|
u16 w;
|
||||||
|
u16 h;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct WindowEvent
|
||||||
|
{
|
||||||
|
union
|
||||||
|
{
|
||||||
|
WindowSize resize;
|
||||||
|
};
|
||||||
|
Event_e type;
|
||||||
|
};
|
||||||
|
|
||||||
// Init
|
// Init
|
||||||
b32 LoadLib(const char *name, Library *out_lib);
|
b32 LoadLib(const char *name, Library *out_lib);
|
||||||
b32 LoadFn(const char *name, Library *lib, Function *out_fn);
|
b32 LoadFn(const char *name, Library *lib, Function *out_fn);
|
||||||
@ -35,3 +61,5 @@ i32 EPrintf(const char *fmt, ...);
|
|||||||
// Window Functions
|
// Window Functions
|
||||||
b32 CreateWindow();
|
b32 CreateWindow();
|
||||||
Window *GetWindow();
|
Window *GetWindow();
|
||||||
|
b32 GetWindowEvent(WindowEvent *event);
|
||||||
|
WindowSize GetWindowSize();
|
||||||
|
|||||||
@ -227,4 +227,64 @@ Window *_GetWindow() {
|
|||||||
return &linux_window;
|
return &linux_window;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
WindowSize _GetWindowSize()
|
||||||
|
{
|
||||||
|
return (WindowSize) {
|
||||||
|
.w = linux_window.w,
|
||||||
|
.h = linux_window.h,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
b32 _GetWindowEvent(WindowEvent *event)
|
||||||
|
{
|
||||||
|
Assert(event != NULL, "GetWindowEvent received a null pointer");
|
||||||
|
|
||||||
|
b32 valid_event = false;
|
||||||
|
b32 no_event = false;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
xcb_generic_event_t *e = xcb_poll_for_event(linux_window.connection);
|
||||||
|
|
||||||
|
if (e != NULL)
|
||||||
|
{
|
||||||
|
switch (e->response_type & ~0x80)
|
||||||
|
{
|
||||||
|
case XCB_CLIENT_MESSAGE:
|
||||||
|
xcb_client_message_event_t *msg = (xcb_client_message_event_t *)e;
|
||||||
|
if (msg->data.data32[0] == linux_window.close_event)
|
||||||
|
{
|
||||||
|
event->type = EVENT_QUIT;
|
||||||
|
valid_event = true;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case XCB_RESIZE_REQUEST:
|
||||||
|
event->type = EVENT_RESIZE;
|
||||||
|
valid_event = true;
|
||||||
|
|
||||||
|
xcb_resize_request_event_t *resize = (xcb_resize_request_event_t *)e;
|
||||||
|
|
||||||
|
if (resize->width > 0)
|
||||||
|
{
|
||||||
|
linux_window.w = resize->width;
|
||||||
|
event->resize.w = resize->width;
|
||||||
|
}
|
||||||
|
if (resize->height > 0)
|
||||||
|
{
|
||||||
|
linux_window.h = resize->height;
|
||||||
|
event->resize.h = resize->height;
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} while(!valid_event);
|
||||||
|
|
||||||
|
return valid_event;
|
||||||
|
}
|
||||||
|
|
||||||
|
|||||||
@ -102,7 +102,8 @@ i32 _EPrintf(const char *fmt, va_list arg);
|
|||||||
// Window Functions
|
// Window Functions
|
||||||
b32 _CreateWindow();
|
b32 _CreateWindow();
|
||||||
Window *_GetWindow();
|
Window *_GetWindow();
|
||||||
|
b32 _GetWindowEvent(WindowEvent *event);
|
||||||
|
WindowSize _GetWindowSize();
|
||||||
|
|
||||||
// Platform API END
|
// Platform API END
|
||||||
|
|
||||||
|
|||||||
@ -6,7 +6,6 @@
|
|||||||
b32 _InitRenderer(Arena *arena)
|
b32 _InitRenderer(Arena *arena)
|
||||||
{
|
{
|
||||||
Assert(InitVulkan(arena), "InitVkLib failure");
|
Assert(InitVulkan(arena), "InitVkLib failure");
|
||||||
ArenaFree(arena);
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -27,7 +26,9 @@ void _DestroyRenderer()
|
|||||||
static b32 InitVulkan(Arena *arena)
|
static b32 InitVulkan(Arena *arena)
|
||||||
{
|
{
|
||||||
Assert(arena != NULL, "Vulkan memory is null");
|
Assert(arena != NULL, "Vulkan memory is null");
|
||||||
renderer.arena = arena;
|
renderer.perm_arena = arena;
|
||||||
|
void *mem = ArenaAlloc(arena, MB(4));
|
||||||
|
renderer.arena = CreateArena(mem, MB(4));
|
||||||
|
|
||||||
Assert(InitVkGlobalFunctions(), "Unable to load vulkan functions");
|
Assert(InitVkGlobalFunctions(), "Unable to load vulkan functions");
|
||||||
Assert(vkCreateInstance(&inst_info, NULL, &renderer.vk.inst) == VK_SUCCESS, "Error initializing instance");
|
Assert(vkCreateInstance(&inst_info, NULL, &renderer.vk.inst) == VK_SUCCESS, "Error initializing instance");
|
||||||
@ -43,9 +44,17 @@ static b32 InitVulkan(Arena *arena)
|
|||||||
|
|
||||||
Assert(CreateSurface(), "Unable to create surface");
|
Assert(CreateSurface(), "Unable to create surface");
|
||||||
Assert(CreateDevice(), "Unable to create device");
|
Assert(CreateDevice(), "Unable to create device");
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Assert(CreateVmaAllocator(), "Unable to create VMA allocator");
|
Assert(CreateVmaAllocator(), "Unable to create VMA allocator");
|
||||||
Assert(CreateFrameStructures(), "Unable to create frame structures");
|
Assert(CreateFrameStructures(), "Unable to create frame structures");
|
||||||
Assert(CreateImmediateStructures(), "Unable to create immediate structures");
|
Assert(CreateImmediateStructures(), "Unable to create immediate structures");
|
||||||
|
Assert(CreateSwapchain(), "Unable to initialize swapchain and draw images");
|
||||||
|
|
||||||
|
ArenaFree(renderer.arena);
|
||||||
|
|
||||||
|
Printfln("yeah");
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -84,7 +93,7 @@ static DeviceQueues CheckDeviceQueueSupport(VkPhysicalDevice device, VkSurfaceKH
|
|||||||
u32 queue_count;
|
u32 queue_count;
|
||||||
vkGetPhysicalDeviceQueueFamilyProperties(device, &queue_count, NULL);
|
vkGetPhysicalDeviceQueueFamilyProperties(device, &queue_count, NULL);
|
||||||
VkQueueFamilyProperties *families = ArenaAlloc(renderer.arena, sizeof(VkQueueFamilyProperties) * queue_count);
|
VkQueueFamilyProperties *families = ArenaAlloc(renderer.arena, sizeof(VkQueueFamilyProperties) * queue_count);
|
||||||
vkGetPhysicalDeviceQueueFamilyProperties(device, &queue_count, &families[0]);
|
vkGetPhysicalDeviceQueueFamilyProperties(device, &queue_count, families);
|
||||||
|
|
||||||
for (i32 i = 0; i < queue_count; i++)
|
for (i32 i = 0; i < queue_count; i++)
|
||||||
{
|
{
|
||||||
@ -115,7 +124,7 @@ static b32 CheckDevicePropertiesSupport(VkPhysicalDevice device, VkSurfaceKHR su
|
|||||||
u32 ext_count;
|
u32 ext_count;
|
||||||
vkEnumerateDeviceExtensionProperties(device, NULL, &ext_count, NULL);
|
vkEnumerateDeviceExtensionProperties(device, NULL, &ext_count, NULL);
|
||||||
VkExtensionProperties *ext_properties = ArenaAlloc(renderer.arena, sizeof(VkExtensionProperties) * ext_count);
|
VkExtensionProperties *ext_properties = ArenaAlloc(renderer.arena, sizeof(VkExtensionProperties) * ext_count);
|
||||||
vkEnumerateDeviceExtensionProperties(device, NULL, &ext_count, &ext_properties[0]);
|
vkEnumerateDeviceExtensionProperties(device, NULL, &ext_count, ext_properties);
|
||||||
|
|
||||||
i32 matched = 0;
|
i32 matched = 0;
|
||||||
for (u32 i = 0; i < ext_count; i++) {
|
for (u32 i = 0; i < ext_count; i++) {
|
||||||
@ -179,7 +188,7 @@ static b32 CreateDevice()
|
|||||||
u32 device_count;
|
u32 device_count;
|
||||||
vkEnumeratePhysicalDevices(inst, &device_count, NULL);
|
vkEnumeratePhysicalDevices(inst, &device_count, NULL);
|
||||||
VkPhysicalDevice *devices = ArenaAlloc(renderer.arena, sizeof(VkPhysicalDevice) * device_count);
|
VkPhysicalDevice *devices = ArenaAlloc(renderer.arena, sizeof(VkPhysicalDevice) * device_count);
|
||||||
vkEnumeratePhysicalDevices(inst, &device_count, &devices[0]);
|
vkEnumeratePhysicalDevices(inst, &device_count, devices);
|
||||||
|
|
||||||
b32 discrete_device = false;
|
b32 discrete_device = false;
|
||||||
DeviceQueues *queues = &renderer.vk.queues;
|
DeviceQueues *queues = &renderer.vk.queues;
|
||||||
@ -288,6 +297,8 @@ static b32 InitVkInstanceFunctions()
|
|||||||
INIT_INST_FN(vkGetDeviceProcAddr);
|
INIT_INST_FN(vkGetDeviceProcAddr);
|
||||||
INIT_INST_FN(vkDestroyInstance);
|
INIT_INST_FN(vkDestroyInstance);
|
||||||
INIT_INST_FN(vkDestroySurfaceKHR);
|
INIT_INST_FN(vkDestroySurfaceKHR);
|
||||||
|
INIT_INST_FN(vkGetPhysicalDeviceSurfaceCapabilitiesKHR);
|
||||||
|
INIT_INST_FN(vkGetPhysicalDeviceImageFormatProperties);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -364,6 +375,7 @@ static b32 CreateSurface()
|
|||||||
if (result != VK_SUCCESS) {
|
if (result != VK_SUCCESS) {
|
||||||
Printf("Unable to create surface: %d", result);
|
Printf("Unable to create surface: %d", result);
|
||||||
}
|
}
|
||||||
|
Printfln("surface: %d", renderer.vk.surface);
|
||||||
|
|
||||||
return result == VK_SUCCESS;
|
return result == VK_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -471,19 +483,185 @@ static b32 CreateImmediateStructures()
|
|||||||
|
|
||||||
static b32 CreateSwapchain()
|
static b32 CreateSwapchain()
|
||||||
{
|
{
|
||||||
|
Printfln("%d", __LINE__);
|
||||||
b32 success = true;
|
b32 success = true;
|
||||||
|
VkPhysicalDevice phys_device = renderer.vk.phys_device;
|
||||||
|
VkDevice device = renderer.vk.device;
|
||||||
|
VkSurfaceKHR surface = renderer.vk.surface;
|
||||||
|
|
||||||
VkSurfaceCapabilitiesKHR capabilities;
|
VkSurfaceCapabilitiesKHR capabilities;
|
||||||
|
vkGetPhysicalDeviceSurfaceCapabilitiesKHR(phys_device, surface, &capabilities);
|
||||||
|
Printfln("%d", __LINE__);
|
||||||
|
|
||||||
|
VkExtent2D extent;
|
||||||
|
WindowSize win_size = GetWindowSize();
|
||||||
|
|
||||||
|
extent.width = u32Clamp((u32)win_size.w, capabilities.minImageExtent.width, capabilities.maxImageExtent.width);
|
||||||
|
extent.height = u32Clamp((u32)win_size.h, capabilities.minImageExtent.height, capabilities.maxImageExtent.height);
|
||||||
|
|
||||||
|
u32 format_count;
|
||||||
|
vkGetPhysicalDeviceSurfaceFormatsKHR(phys_device, surface, &format_count, NULL);
|
||||||
|
VkSurfaceFormatKHR *formats = ArenaAlloc(renderer.arena, sizeof(VkSurfaceFormatKHR) * format_count);
|
||||||
|
vkGetPhysicalDeviceSurfaceFormatsKHR(phys_device, surface, &format_count, formats);
|
||||||
|
|
||||||
|
renderer.vk.sc_info.format = formats[0].format;
|
||||||
|
renderer.vk.sc_info.color_space = formats[0].colorSpace;
|
||||||
|
|
||||||
|
u32 present_count;
|
||||||
|
vkGetPhysicalDeviceSurfacePresentModesKHR(phys_device, surface, &present_count, NULL);
|
||||||
|
VkPresentModeKHR *present_modes = ArenaAlloc(renderer.arena, sizeof(VkSurfaceFormatKHR) * present_count);
|
||||||
|
vkGetPhysicalDeviceSurfacePresentModesKHR(phys_device, surface, &present_count, present_modes);
|
||||||
|
|
||||||
|
Printfln("%d", __LINE__);
|
||||||
|
|
||||||
|
VkPresentModeKHR present_mode;
|
||||||
|
for (u32 i = 0; i < present_count; i++)
|
||||||
|
{
|
||||||
|
if (present_modes[i] == VK_PRESENT_MODE_MAILBOX_KHR)
|
||||||
|
{
|
||||||
|
present_mode = VK_PRESENT_MODE_MAILBOX_KHR;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (present_mode != VK_PRESENT_MODE_MAILBOX_KHR)
|
||||||
|
present_mode = VK_PRESENT_MODE_FIFO_KHR;
|
||||||
|
|
||||||
|
swapchain_create_info.minImageCount = capabilities.minImageCount + 1;
|
||||||
|
swapchain_create_info.surface = surface;
|
||||||
|
swapchain_create_info.imageFormat = renderer.vk.sc_info.format;
|
||||||
|
swapchain_create_info.imageColorSpace = renderer.vk.sc_info.color_space;
|
||||||
|
swapchain_create_info.imageExtent = extent;
|
||||||
|
swapchain_create_info.preTransform = capabilities.currentTransform;
|
||||||
|
swapchain_create_info.presentMode = present_mode;
|
||||||
|
|
||||||
|
VkResult result;
|
||||||
|
result = vkCreateSwapchainKHR(device, &swapchain_create_info, NULL, &renderer.vk.swapchain);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
|
||||||
|
u32 image_count;
|
||||||
|
vkGetSwapchainImagesKHR(device, renderer.vk.swapchain, &image_count, NULL);
|
||||||
|
VkImage *sc_images = ArenaAlloc(renderer.perm_arena, sizeof(VkImage) * image_count);
|
||||||
|
VkImageView *sc_views = ArenaAlloc(renderer.perm_arena, sizeof(VkImage) * image_count);
|
||||||
|
vkGetSwapchainImagesKHR(device, renderer.vk.swapchain, &image_count, sc_images);
|
||||||
|
|
||||||
|
for (u32 i = 0; i < image_count; i++)
|
||||||
|
{
|
||||||
|
sc_image_view_create_info.image = sc_images[i];
|
||||||
|
sc_image_view_create_info.format = renderer.vk.sc_info.format;
|
||||||
|
|
||||||
|
result = vkCreateImageView(device, &sc_image_view_create_info, NULL, &sc_views[i]);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
renderer.vk.sc_info.imgs = sc_images;
|
||||||
|
renderer.vk.sc_info.views = sc_views;
|
||||||
|
renderer.vk.sc_info.img_count = image_count;
|
||||||
|
|
||||||
|
VkFormat image_format = GetImageFormat();
|
||||||
|
VkExtent3D extent_3d = {
|
||||||
|
.width = extent.width,
|
||||||
|
.height = extent.height,
|
||||||
|
.depth = 1,
|
||||||
|
};
|
||||||
|
|
||||||
|
renderer.vk.sc_info.extent = extent_3d;
|
||||||
|
|
||||||
|
VmaAllocationCreateInfo alloc_create_info = {
|
||||||
|
.usage = VMA_MEMORY_USAGE_GPU_ONLY,
|
||||||
|
.requiredFlags = VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT,
|
||||||
|
};
|
||||||
|
|
||||||
|
// Draw Image
|
||||||
|
draw_image_create_info.format = image_format;
|
||||||
|
draw_image_create_info.extent = extent_3d;
|
||||||
|
|
||||||
|
result = vmaCreateImage(renderer.vk.alloc, &draw_image_create_info,
|
||||||
|
&alloc_create_info, &renderer.vk.sc_info.draw_img.img, &renderer.vk.sc_info.draw_img.alloc, NULL);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
|
||||||
|
// Draw Image View
|
||||||
|
draw_image_view_create_info.image = renderer.vk.sc_info.draw_img.img;
|
||||||
|
draw_image_view_create_info.format = image_format;
|
||||||
|
|
||||||
|
result = vkCreateImageView(device, &draw_image_view_create_info, NULL, &renderer.vk.sc_info.draw_img.view);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
|
||||||
|
// Depth Image
|
||||||
|
depth_image_create_info.extent = extent_3d;
|
||||||
|
|
||||||
|
result = vmaCreateImage(renderer.vk.alloc, &depth_image_create_info,
|
||||||
|
&alloc_create_info, &renderer.vk.sc_info.depth_img.img, &renderer.vk.sc_info.depth_img.alloc, NULL);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
|
||||||
|
// Depth Image View
|
||||||
|
depth_image_view_create_info.image = renderer.vk.sc_info.depth_img.img;
|
||||||
|
result = vkCreateImageView(device, &depth_image_view_create_info, NULL, &renderer.vk.sc_info.depth_img.view);
|
||||||
|
if (result != VK_SUCCESS)
|
||||||
|
success = false;
|
||||||
|
|
||||||
return success;
|
return success;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static VkFormat GetImageFormat()
|
||||||
|
{
|
||||||
|
VkPhysicalDevice phys_device = renderer.vk.phys_device;
|
||||||
|
VkImageType image_type = VK_IMAGE_TYPE_2D;
|
||||||
|
VkImageTiling tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||||
|
VkImageUsageFlags usage_flags = VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
|
||||||
|
VK_IMAGE_USAGE_TRANSFER_DST_BIT |
|
||||||
|
VK_IMAGE_USAGE_STORAGE_BIT |
|
||||||
|
VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT;
|
||||||
|
|
||||||
|
VkFormat format = 0;
|
||||||
|
for (i32 i = 0; i < Len(VK_IMAGE_FORMATS); i++)
|
||||||
|
{
|
||||||
|
VkImageFormatProperties properties;
|
||||||
|
VkResult result;
|
||||||
|
result = vkGetPhysicalDeviceImageFormatProperties(phys_device, VK_IMAGE_FORMATS[i], image_type,
|
||||||
|
tiling, usage_flags, 0, &properties);
|
||||||
|
if (result == VK_ERROR_FORMAT_NOT_SUPPORTED)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (result == VK_SUCCESS)
|
||||||
|
{
|
||||||
|
format = VK_IMAGE_FORMATS[i];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Assert(format != 0, "[Error] unable to find appropriate image format");
|
||||||
|
|
||||||
|
return format;
|
||||||
|
}
|
||||||
|
|
||||||
static void DestroyVulkan()
|
static void DestroyVulkan()
|
||||||
{
|
{
|
||||||
VkDevice device = renderer.vk.device;
|
VkDevice device = renderer.vk.device;
|
||||||
VkInstance instance = renderer.vk.inst;
|
VkInstance instance = renderer.vk.inst;
|
||||||
FrameStructures data = renderer.vk.frame;
|
FrameStructures data = renderer.vk.frame;
|
||||||
ImmediateStructures imm = renderer.vk.imm;
|
ImmediateStructures imm = renderer.vk.imm;
|
||||||
|
SwapchainInfo sc_info = renderer.vk.sc_info;
|
||||||
|
VmaAllocator vma_alloc = renderer.vk.alloc;
|
||||||
|
VkSwapchainKHR swapchain = renderer.vk.swapchain;
|
||||||
|
|
||||||
|
vkDestroyImageView(device, sc_info.draw_img.view, NULL);
|
||||||
|
vmaDestroyImage(vma_alloc, sc_info.draw_img.img, sc_info.draw_img.alloc);
|
||||||
|
|
||||||
|
vkDestroyImageView(device, sc_info.depth_img.view, NULL);
|
||||||
|
vmaDestroyImage(vma_alloc, sc_info.depth_img.img, sc_info.depth_img.alloc);
|
||||||
|
|
||||||
|
for (u32 i = 0; i < sc_info.img_count; i++)
|
||||||
|
{
|
||||||
|
vkDestroyImageView(device, sc_info.views[i], NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
vkDestroySwapchainKHR(device, swapchain, NULL);
|
||||||
|
|
||||||
vkDestroyFence(device, imm.fence, NULL);
|
vkDestroyFence(device, imm.fence, NULL);
|
||||||
vkFreeCommandBuffers(device, imm.pool, 1, &imm.buffer);
|
vkFreeCommandBuffers(device, imm.pool, 1, &imm.buffer);
|
||||||
@ -511,6 +689,119 @@ static void DestroyVulkan()
|
|||||||
vkDestroyInstance(renderer.vk.inst, NULL);
|
vkDestroyInstance(renderer.vk.inst, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char *VkResultStr(VkResult result)
|
||||||
|
{
|
||||||
|
switch (result)
|
||||||
|
{
|
||||||
|
case VK_SUCCESS:
|
||||||
|
return "VK_SUCCESS";
|
||||||
|
case VK_NOT_READY:
|
||||||
|
return "VK_NOT_READY";
|
||||||
|
case VK_TIMEOUT:
|
||||||
|
return "VK_TIMEOUT";
|
||||||
|
case VK_EVENT_SET:
|
||||||
|
return "VK_EVENT_SET";
|
||||||
|
case VK_EVENT_RESET:
|
||||||
|
return "VK_EVENT_RESET";
|
||||||
|
case VK_INCOMPLETE:
|
||||||
|
return "VK_INCOMPLETE";
|
||||||
|
case VK_ERROR_OUT_OF_HOST_MEMORY:
|
||||||
|
return "VK_ERROR_OUT_OF_HOST_MEMORY";
|
||||||
|
case VK_ERROR_OUT_OF_DEVICE_MEMORY:
|
||||||
|
return "VK_ERROR_OUT_OF_DEVICE_MEMORY";
|
||||||
|
case VK_ERROR_INITIALIZATION_FAILED:
|
||||||
|
return "VK_ERROR_INITIALIZATION_FAILED";
|
||||||
|
case VK_ERROR_DEVICE_LOST:
|
||||||
|
return "VK_ERROR_DEVICE_LOST";
|
||||||
|
case VK_ERROR_MEMORY_MAP_FAILED:
|
||||||
|
return "VK_ERROR_MEMORY_MAP_FAILED";
|
||||||
|
case VK_ERROR_LAYER_NOT_PRESENT:
|
||||||
|
return "VK_ERROR_LAYER_NOT_PRESENT";
|
||||||
|
case VK_ERROR_EXTENSION_NOT_PRESENT:
|
||||||
|
return "VK_ERROR_EXTENSION_NOT_PRESENT";
|
||||||
|
case VK_ERROR_FEATURE_NOT_PRESENT:
|
||||||
|
return "VK_ERROR_FEATURE_NOT_PRESENT";
|
||||||
|
case VK_ERROR_INCOMPATIBLE_DRIVER:
|
||||||
|
return "VK_ERROR_INCOMPATIBLE_DRIVER";
|
||||||
|
case VK_ERROR_TOO_MANY_OBJECTS:
|
||||||
|
return "VK_ERROR_TOO_MANY_OBJECTS";
|
||||||
|
case VK_ERROR_FORMAT_NOT_SUPPORTED:
|
||||||
|
return "VK_ERROR_FORMAT_NOT_SUPPORTED";
|
||||||
|
case VK_ERROR_FRAGMENTED_POOL:
|
||||||
|
return "VK_ERROR_FRAGMENTED_POOL";
|
||||||
|
case VK_ERROR_UNKNOWN:
|
||||||
|
return "VK_ERROR_UNKNOWN";
|
||||||
|
case VK_ERROR_OUT_OF_POOL_MEMORY:
|
||||||
|
return "VK_ERROR_OUT_OF_POOL_MEMORY";
|
||||||
|
case VK_ERROR_INVALID_EXTERNAL_HANDLE:
|
||||||
|
return "VK_ERROR_INVALID_EXTERNAL_HANDLE";
|
||||||
|
case VK_ERROR_FRAGMENTATION:
|
||||||
|
return "VK_ERROR_FRAGMENTATION";
|
||||||
|
case VK_ERROR_INVALID_OPAQUE_CAPTURE_ADDRESS:
|
||||||
|
return "VK_ERROR_INVALID_OPAQUE_CAPTURE_ADDRESS";
|
||||||
|
case VK_PIPELINE_COMPILE_REQUIRED:
|
||||||
|
return "VK_PIPELINE_COMPILE_REQUIRED";
|
||||||
|
case VK_ERROR_SURFACE_LOST_KHR:
|
||||||
|
return "VK_ERROR_SURFACE_LOST_KHR";
|
||||||
|
case VK_ERROR_NATIVE_WINDOW_IN_USE_KHR:
|
||||||
|
return "VK_ERROR_NATIVE_WINDOW_IN_USE_KHR";
|
||||||
|
case VK_SUBOPTIMAL_KHR:
|
||||||
|
return "VK_SUBOPTIMAL_KHR";
|
||||||
|
case VK_ERROR_OUT_OF_DATE_KHR:
|
||||||
|
return "VK_ERROR_OUT_OF_DATE_KHR";
|
||||||
|
case VK_ERROR_INCOMPATIBLE_DISPLAY_KHR:
|
||||||
|
return "VK_ERROR_INCOMPATIBLE_DISPLAY_KHR";
|
||||||
|
case VK_ERROR_VALIDATION_FAILED_EXT:
|
||||||
|
return "VK_ERROR_VALIDATION_FAILED_EXT";
|
||||||
|
case VK_ERROR_INVALID_SHADER_NV:
|
||||||
|
return "VK_ERROR_INVALID_SHADER_NV";
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_IMAGE_USAGE_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_IMAGE_USAGE_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_VIDEO_PICTURE_LAYOUT_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_VIDEO_PICTURE_LAYOUT_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_VIDEO_PROFILE_OPERATION_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_VIDEO_PROFILE_OPERATION_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_VIDEO_PROFILE_FORMAT_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_VIDEO_PROFILE_FORMAT_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_VIDEO_PROFILE_CODEC_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_VIDEO_PROFILE_CODEC_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
#ifdef VK_ENABLE_BETA_EXTENSIONS
|
||||||
|
case VK_ERROR_VIDEO_STD_VERSION_NOT_SUPPORTED_KHR:
|
||||||
|
return "VK_ERROR_VIDEO_STD_VERSION_NOT_SUPPORTED_KHR";
|
||||||
|
#endif
|
||||||
|
case VK_ERROR_INVALID_DRM_FORMAT_MODIFIER_PLANE_LAYOUT_EXT:
|
||||||
|
return "VK_ERROR_INVALID_DRM_FORMAT_MODIFIER_PLANE_LAYOUT_EXT";
|
||||||
|
case VK_ERROR_NOT_PERMITTED_KHR:
|
||||||
|
return "VK_ERROR_NOT_PERMITTED_KHR";
|
||||||
|
case VK_ERROR_FULL_SCREEN_EXCLUSIVE_MODE_LOST_EXT:
|
||||||
|
return "VK_ERROR_FULL_SCREEN_EXCLUSIVE_MODE_LOST_EXT";
|
||||||
|
case VK_THREAD_IDLE_KHR:
|
||||||
|
return "VK_THREAD_IDLE_KHR";
|
||||||
|
case VK_THREAD_DONE_KHR:
|
||||||
|
return "VK_THREAD_DONE_KHR";
|
||||||
|
case VK_OPERATION_DEFERRED_KHR:
|
||||||
|
return "VK_OPERATION_DEFERRED_KHR";
|
||||||
|
case VK_OPERATION_NOT_DEFERRED_KHR:
|
||||||
|
return "VK_OPERATION_NOT_DEFERRED_KHR";
|
||||||
|
case VK_ERROR_COMPRESSION_EXHAUSTED_EXT:
|
||||||
|
return "VK_ERROR_COMPRESSION_EXHAUSTED_EXT";
|
||||||
|
case VK_RESULT_MAX_ENUM:
|
||||||
|
return "VK_RESULT_MAX_ENUM";
|
||||||
|
default:
|
||||||
|
return "??????";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static VkBool32 DebugCallback(
|
static VkBool32 DebugCallback(
|
||||||
VkDebugUtilsMessageSeverityFlagBitsEXT message_severity,
|
VkDebugUtilsMessageSeverityFlagBitsEXT message_severity,
|
||||||
VkDebugUtilsMessageTypeFlagsEXT message_type,
|
VkDebugUtilsMessageTypeFlagsEXT message_type,
|
||||||
|
|||||||
@ -47,6 +47,7 @@ VK_DECLARE(vkEnumerateDeviceExtensionProperties);
|
|||||||
VK_DECLARE(vkGetPhysicalDeviceSurfacePresentModesKHR);
|
VK_DECLARE(vkGetPhysicalDeviceSurfacePresentModesKHR);
|
||||||
VK_DECLARE(vkGetPhysicalDeviceSurfaceFormatsKHR);
|
VK_DECLARE(vkGetPhysicalDeviceSurfaceFormatsKHR);
|
||||||
VK_DECLARE(vkGetPhysicalDeviceSurfaceCapabilitiesKHR);
|
VK_DECLARE(vkGetPhysicalDeviceSurfaceCapabilitiesKHR);
|
||||||
|
VK_DECLARE(vkGetPhysicalDeviceImageFormatProperties);
|
||||||
|
|
||||||
#ifdef __linux__
|
#ifdef __linux__
|
||||||
VK_DECLARE(vkCreateXcbSurfaceKHR);
|
VK_DECLARE(vkCreateXcbSurfaceKHR);
|
||||||
@ -137,16 +138,36 @@ typedef struct {
|
|||||||
VkQueue graphics_queue, transfer_queue;
|
VkQueue graphics_queue, transfer_queue;
|
||||||
} DeviceQueues;
|
} DeviceQueues;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
VkImage img;
|
||||||
|
VkImageView view;
|
||||||
|
VmaAllocation alloc;
|
||||||
|
VkFormat fmt;
|
||||||
|
} Image;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
VkFormat format;
|
||||||
|
VkColorSpaceKHR color_space;
|
||||||
|
VkExtent3D extent;
|
||||||
|
VkImage *imgs;
|
||||||
|
VkImageView *views;
|
||||||
|
u32 img_count;
|
||||||
|
Image draw_img;
|
||||||
|
Image depth_img;
|
||||||
|
} SwapchainInfo;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
Library lib;
|
Library lib;
|
||||||
VkInstance inst;
|
VkInstance inst;
|
||||||
VkSurfaceKHR surface;
|
VkSurfaceKHR surface;
|
||||||
VkDevice device;
|
VkDevice device;
|
||||||
|
VkSwapchainKHR swapchain;
|
||||||
VkPhysicalDevice phys_device;
|
VkPhysicalDevice phys_device;
|
||||||
DeviceQueues queues;
|
DeviceQueues queues;
|
||||||
VmaAllocator alloc;
|
VmaAllocator alloc;
|
||||||
FrameStructures frame;
|
FrameStructures frame;
|
||||||
ImmediateStructures imm;
|
ImmediateStructures imm;
|
||||||
|
SwapchainInfo sc_info;
|
||||||
#ifdef BUILD_DEBUG
|
#ifdef BUILD_DEBUG
|
||||||
VkDebugUtilsMessengerEXT debug;
|
VkDebugUtilsMessengerEXT debug;
|
||||||
#endif
|
#endif
|
||||||
@ -155,6 +176,7 @@ typedef struct {
|
|||||||
typedef struct {
|
typedef struct {
|
||||||
Vulkan_t vk;
|
Vulkan_t vk;
|
||||||
Arena *arena;
|
Arena *arena;
|
||||||
|
Arena *perm_arena;
|
||||||
} Renderer_t;
|
} Renderer_t;
|
||||||
|
|
||||||
// Renderer Function Declarations
|
// Renderer Function Declarations
|
||||||
@ -167,6 +189,7 @@ static VkBool32 DebugCallback(
|
|||||||
const VkDebugUtilsMessengerCallbackDataEXT *pCallbackData,
|
const VkDebugUtilsMessengerCallbackDataEXT *pCallbackData,
|
||||||
void *pUserData
|
void *pUserData
|
||||||
);
|
);
|
||||||
|
const char *VkResultStr(VkResult result);
|
||||||
|
|
||||||
// Init
|
// Init
|
||||||
static b32 LoadVulkanLib();
|
static b32 LoadVulkanLib();
|
||||||
@ -184,6 +207,7 @@ static b32 CreateVmaAllocator();
|
|||||||
static b32 CreateFrameStructures();
|
static b32 CreateFrameStructures();
|
||||||
static b32 CreateImmediateStructures();
|
static b32 CreateImmediateStructures();
|
||||||
static b32 CreateSwapchain();
|
static b32 CreateSwapchain();
|
||||||
|
static VkFormat GetImageFormat();
|
||||||
|
|
||||||
// Destroy
|
// Destroy
|
||||||
static void DestroyVulkan();
|
static void DestroyVulkan();
|
||||||
|
|||||||
30
src/util.c
30
src/util.c
@ -78,3 +78,33 @@ void MemZero(void *ptr, isize size)
|
|||||||
assert(test_ptr[i] == 0);
|
assert(test_ptr[i] == 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u32 u32Min(u32 l, u32 r)
|
||||||
|
{
|
||||||
|
return l >= r ? r : l;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 i32Min(i32 l, i32 r)
|
||||||
|
{
|
||||||
|
return l >= r ? r : l;
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 u32Max(u32 l, u32 r)
|
||||||
|
{
|
||||||
|
return l >= r ? l : r;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 i32Max(i32 l, i32 r)
|
||||||
|
{
|
||||||
|
return l >= r ? l : r;
|
||||||
|
}
|
||||||
|
|
||||||
|
i32 i32Clamp(i32 v, i32 min, i32 max)
|
||||||
|
{
|
||||||
|
return i32Min(max, i32Max(v, min));
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 u32Clamp(u32 v, u32 min, u32 max)
|
||||||
|
{
|
||||||
|
return i32Min(max, i32Max(v, min));
|
||||||
|
}
|
||||||
|
|||||||
@ -17,3 +17,11 @@ i32 SPrintf(char *buf, rawptr fmt, ...);
|
|||||||
|
|
||||||
// Memory Functions
|
// Memory Functions
|
||||||
void MemZero(void *ptr, isize size);
|
void MemZero(void *ptr, isize size);
|
||||||
|
|
||||||
|
// Math Functions
|
||||||
|
u32 u32Min(u32 l, u32 r);
|
||||||
|
i32 i32Min(i32 l, i32 r);
|
||||||
|
u32 u32Max(u32 l, u32 r);
|
||||||
|
i32 i32Max(i32 l, i32 r);
|
||||||
|
i32 i32Clamp(i32 v, i32 min, i32 max);
|
||||||
|
u32 u32Clamp(u32 v, u32 min, u32 max);
|
||||||
|
|||||||
@ -1,5 +1,11 @@
|
|||||||
|
|
||||||
// VULKAN CONFIG
|
// VULKAN CONFIG
|
||||||
|
|
||||||
|
static const VkFormat VK_IMAGE_FORMATS[] = {
|
||||||
|
VK_FORMAT_R16G16B16A16_UNORM,
|
||||||
|
VK_FORMAT_R8G8B8A8_UNORM,
|
||||||
|
};
|
||||||
|
|
||||||
static VkApplicationInfo app_info = {
|
static VkApplicationInfo app_info = {
|
||||||
.sType = STYPE(APPLICATION_INFO),
|
.sType = STYPE(APPLICATION_INFO),
|
||||||
.pApplicationName = "Video Game",
|
.pApplicationName = "Video Game",
|
||||||
@ -110,3 +116,76 @@ static VkCommandBufferAllocateInfo cmd_buf_info = {
|
|||||||
.commandBufferCount = 1,
|
.commandBufferCount = 1,
|
||||||
.level = VK_COMMAND_BUFFER_LEVEL_PRIMARY,
|
.level = VK_COMMAND_BUFFER_LEVEL_PRIMARY,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static VkSwapchainCreateInfoKHR swapchain_create_info = {
|
||||||
|
.sType = STYPE(SWAPCHAIN_CREATE_INFO_KHR),
|
||||||
|
.imageArrayLayers = 1,
|
||||||
|
.imageUsage = VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT,
|
||||||
|
.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR,
|
||||||
|
.clipped = VK_TRUE,
|
||||||
|
.imageSharingMode = VK_SHARING_MODE_EXCLUSIVE,
|
||||||
|
};
|
||||||
|
|
||||||
|
static VkImageViewCreateInfo sc_image_view_create_info = {
|
||||||
|
.sType = STYPE(IMAGE_VIEW_CREATE_INFO),
|
||||||
|
.viewType = VK_IMAGE_VIEW_TYPE_2D,
|
||||||
|
.components = {
|
||||||
|
.r = VK_COMPONENT_SWIZZLE_IDENTITY,
|
||||||
|
.g = VK_COMPONENT_SWIZZLE_IDENTITY,
|
||||||
|
.b = VK_COMPONENT_SWIZZLE_IDENTITY,
|
||||||
|
.a = VK_COMPONENT_SWIZZLE_IDENTITY,
|
||||||
|
},
|
||||||
|
.subresourceRange = {
|
||||||
|
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||||
|
.baseMipLevel = 0,
|
||||||
|
.levelCount = 1,
|
||||||
|
.baseArrayLayer = 0,
|
||||||
|
.layerCount = 1,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static VkImageCreateInfo draw_image_create_info = {
|
||||||
|
.sType = STYPE(IMAGE_CREATE_INFO),
|
||||||
|
.imageType = VK_IMAGE_TYPE_2D,
|
||||||
|
.mipLevels = 1,
|
||||||
|
.arrayLayers = 1,
|
||||||
|
.samples = VK_SAMPLE_COUNT_1_BIT,
|
||||||
|
.tiling = VK_IMAGE_TILING_OPTIMAL,
|
||||||
|
.usage = VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_STORAGE_BIT | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT,
|
||||||
|
};
|
||||||
|
|
||||||
|
static VkImageViewCreateInfo draw_image_view_create_info = {
|
||||||
|
.sType = STYPE(IMAGE_VIEW_CREATE_INFO),
|
||||||
|
.viewType = VK_IMAGE_VIEW_TYPE_2D,
|
||||||
|
.subresourceRange = {
|
||||||
|
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT,
|
||||||
|
.baseMipLevel = 0,
|
||||||
|
.levelCount = 1,
|
||||||
|
.baseArrayLayer = 0,
|
||||||
|
.layerCount = 1,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
static VkImageCreateInfo depth_image_create_info = {
|
||||||
|
.sType = STYPE(IMAGE_CREATE_INFO),
|
||||||
|
.imageType = VK_IMAGE_TYPE_2D,
|
||||||
|
.mipLevels = 1,
|
||||||
|
.arrayLayers = 1,
|
||||||
|
.samples = VK_SAMPLE_COUNT_1_BIT,
|
||||||
|
.tiling = VK_IMAGE_TILING_OPTIMAL,
|
||||||
|
.format = VK_FORMAT_D32_SFLOAT,
|
||||||
|
.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT,
|
||||||
|
};
|
||||||
|
|
||||||
|
static VkImageViewCreateInfo depth_image_view_create_info = {
|
||||||
|
.sType = STYPE(IMAGE_VIEW_CREATE_INFO),
|
||||||
|
.viewType = VK_IMAGE_VIEW_TYPE_2D,
|
||||||
|
.format = VK_FORMAT_D32_SFLOAT,
|
||||||
|
.subresourceRange = {
|
||||||
|
.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT,
|
||||||
|
.baseMipLevel = 0,
|
||||||
|
.levelCount = 1,
|
||||||
|
.baseArrayLayer = 0,
|
||||||
|
.layerCount = 1,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user