From 4a40ed5d9034a75db31d4425c25e7e65f7ee15f0 Mon Sep 17 00:00:00 2001 From: Warwick New Date: Mon, 16 Dec 2024 15:48:25 +0000 Subject: [PATCH] Added presentation support check --- src/main.c | 57 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 38 insertions(+), 19 deletions(-) diff --git a/src/main.c b/src/main.c index 09cc797..5749c26 100644 --- a/src/main.c +++ b/src/main.c @@ -223,11 +223,18 @@ void DestroyDebugUtilsMessengerEXT(VkInstance instance, struct QueueFamilyIndices_s { bool graphicsFamilyExists; uint32_t graphicsFamily; -} QueueFamilyIndices_default = {.graphicsFamilyExists = false, - .graphicsFamily = 0}; + bool presentFamilyExists; + uint32_t presentFamily; +} QueueFamilyIndices_default = { + .graphicsFamilyExists = false, + .graphicsFamily = 0, + .presentFamilyExists = false, + .presentFamily = 0, +}; typedef struct QueueFamilyIndices_s QueueFamilyIndices; -QueueFamilyIndices findQueueFamilies(VkPhysicalDevice device) { +QueueFamilyIndices findQueueFamilies(VkPhysicalDevice device, + VkSurfaceKHR *surface) { QueueFamilyIndices indices = QueueFamilyIndices_default; uint32_t queueFamilyCount = 0; @@ -235,22 +242,34 @@ QueueFamilyIndices findQueueFamilies(VkPhysicalDevice device) { VkQueueFamilyProperties queueFamilies[queueFamilyCount]; vkGetPhysicalDeviceQueueFamilyProperties(device, &queueFamilyCount, queueFamilies); - - for (uint32_t i = 0; i < queueFamilyCount; i++) { + uint32_t i; + for (i = 0; i < queueFamilyCount; i++) { + // Graphics support if (queueFamilies[i].queueFlags & VK_QUEUE_GRAPHICS_BIT) { indices.graphicsFamily = i; indices.graphicsFamilyExists = true; - break; // remove if we need additional checks in future + } + // Surface support + VkBool32 presentSupport = false; + vkGetPhysicalDeviceSurfaceSupportKHR(device, i, *surface, &presentSupport); + if (presentSupport) { + indices.presentFamilyExists = true; + indices.presentFamily = i; + } + + // Early break if we've found everything + if (indices.presentFamilyExists && indices.graphicsFamilyExists) { + break; } } return indices; } -bool isDeviceSuitable(VkPhysicalDevice device) { - QueueFamilyIndices indices = findQueueFamilies(device); +bool isDeviceSuitable(VkPhysicalDevice device, VkSurfaceKHR *surface) { + QueueFamilyIndices indices = findQueueFamilies(device, surface); - return indices.graphicsFamilyExists; + return indices.graphicsFamilyExists && indices.graphicsFamilyExists; } void pickPhysicalDevice(Application *app) { @@ -268,7 +287,7 @@ void pickPhysicalDevice(Application *app) { // TODO: pick device off of more than if it's just suitable for (int i = 0; i < physicalDeviceCount; i++) { - if (isDeviceSuitable(physicalDevices[i])) { + if (isDeviceSuitable(physicalDevices[i], &app->surface)) { physicalDevice = physicalDevices[i]; break; } @@ -284,7 +303,7 @@ void pickPhysicalDevice(Application *app) { void createLogicalDevice(Application *app) { // Specify Queues - QueueFamilyIndices indeces = findQueueFamilies(app->physicalDevice); + QueueFamilyIndices indeces = findQueueFamilies(app->physicalDevice, &app->surface); VkDeviceQueueCreateInfo queueCreateInfo = {}; queueCreateInfo.sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO; queueCreateInfo.queueFamilyIndex = indeces.graphicsFamily; @@ -320,13 +339,6 @@ void createLogicalDevice(Application *app) { vkGetDeviceQueue(app->device, indeces.graphicsFamily, 0, &app->graphicsQueue); } -void initVulkan(Application *app) { - createInstance(app); - setupDebugMessenger(app); - pickPhysicalDevice(app); - createLogicalDevice(app); -} - void createSurface(Application *app) { if (glfwCreateWindowSurface(app->instance, app->window, NULL, &app->surface) != VK_SUCCESS) { @@ -335,6 +347,14 @@ void createSurface(Application *app) { } } +void initVulkan(Application *app) { + createInstance(app); + setupDebugMessenger(app); + createSurface(app); + pickPhysicalDevice(app); + createLogicalDevice(app); +} + void mainLoop(Application *app) { while (!glfwWindowShouldClose(app->window)) { glfwPollEvents(); @@ -357,7 +377,6 @@ int main(void) { initWindow(&app); initVulkan(&app); - createSurface(&app); mainLoop(&app); cleanup(&app);