mirror of
https://github.com/Drezil/imgui.git
synced 2024-11-15 09:27:00 +00:00
Examples: Vulkan: Moved main.cpp data structures to imgui_impl_vulkan.h as shared helpers for the benefit of both the example and the platform/viewport renderer interface.
This commit is contained in:
parent
e9fa17e1bf
commit
426930e028
@ -727,6 +727,34 @@ void ImGui_ImplVulkan_Render(VkCommandBuffer command_buffer)
|
|||||||
|
|
||||||
#include <stdlib.h> // malloc
|
#include <stdlib.h> // malloc
|
||||||
|
|
||||||
|
ImGui_ImplVulkan_FrameData::ImGui_ImplVulkan_FrameData()
|
||||||
|
{
|
||||||
|
BackbufferIndex = 0;
|
||||||
|
CommandPool = VK_NULL_HANDLE;
|
||||||
|
CommandBuffer = VK_NULL_HANDLE;
|
||||||
|
Fence = VK_NULL_HANDLE;
|
||||||
|
PresentCompleteSemaphore = VK_NULL_HANDLE;
|
||||||
|
RenderCompleteSemaphore = VK_NULL_HANDLE;
|
||||||
|
}
|
||||||
|
|
||||||
|
ImGui_ImplVulkan_WindowData::ImGui_ImplVulkan_WindowData()
|
||||||
|
{
|
||||||
|
Width = Height = 0;
|
||||||
|
Swapchain = VK_NULL_HANDLE;
|
||||||
|
Surface = VK_NULL_HANDLE;
|
||||||
|
memset(&SurfaceFormat, 0, sizeof(SurfaceFormat));
|
||||||
|
PresentMode = VK_PRESENT_MODE_MAX_ENUM_KHR;
|
||||||
|
RenderPass = VK_NULL_HANDLE;
|
||||||
|
memset(&ClearValue, 0, sizeof(ClearValue));
|
||||||
|
BackBufferCount = 0;
|
||||||
|
memset(&BackBuffer, 0, sizeof(BackBuffer));
|
||||||
|
memset(&BackBufferView, 0, sizeof(BackBufferView));
|
||||||
|
memset(&Framebuffer, 0, sizeof(Framebuffer));
|
||||||
|
FrameIndex = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
VkSurfaceFormatKHR ImGui_ImplVulkan_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space)
|
VkSurfaceFormatKHR ImGui_ImplVulkan_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space)
|
||||||
{
|
{
|
||||||
IM_ASSERT(request_formats != NULL);
|
IM_ASSERT(request_formats != NULL);
|
||||||
@ -790,9 +818,9 @@ VkPresentModeKHR ImGui_ImplVulkan_SelectPresentMode(VkPhysicalDevice physical_de
|
|||||||
return VK_PRESENT_MODE_FIFO_KHR; // Always available
|
return VK_PRESENT_MODE_FIFO_KHR; // Always available
|
||||||
}
|
}
|
||||||
|
|
||||||
// --------------------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------------------
|
||||||
// Platform Windows (OPTIONAL/EXPERIMENTAL)
|
// Platform Windows (OPTIONAL/EXPERIMENTAL)
|
||||||
// --------------------------------------------------------------------------------------------------------
|
//--------------------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
#include "imgui_internal.h" // ImGuiViewport
|
#include "imgui_internal.h" // ImGuiViewport
|
||||||
|
|
||||||
@ -868,4 +896,3 @@ void ImGui_ImplVulkan_ShutdownPlatformInterface()
|
|||||||
ImGuiIO& io = ImGui::GetIO();
|
ImGuiIO& io = ImGui::GetIO();
|
||||||
memset(&io.RendererInterface, 0, sizeof(io.RendererInterface));
|
memset(&io.RendererInterface, 0, sizeof(io.RendererInterface));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -36,6 +36,43 @@ IMGUI_API void ImGui_ImplVulkan_InvalidateDeviceObjects();
|
|||||||
IMGUI_API bool ImGui_ImplVulkan_CreateFontsTexture(VkCommandBuffer command_buffer);
|
IMGUI_API bool ImGui_ImplVulkan_CreateFontsTexture(VkCommandBuffer command_buffer);
|
||||||
IMGUI_API bool ImGui_ImplVulkan_CreateDeviceObjects();
|
IMGUI_API bool ImGui_ImplVulkan_CreateDeviceObjects();
|
||||||
|
|
||||||
|
//-------------------------------------------------------------------------
|
||||||
// Miscellaneous Vulkan Helpers
|
// Miscellaneous Vulkan Helpers
|
||||||
|
// Generally we try to NOT provide any kind of superfluous high-level helpers in the examples.
|
||||||
|
// But for the purpose of allowing multi-windows, we need those internally anyway. The code being not trivial are exposing it for the benefit of the example code.
|
||||||
|
// If your application/engine already has code to create all that data (swap chain, render pass, frame buffers, etc.) you can ignore all of this.
|
||||||
|
//-------------------------------------------------------------------------
|
||||||
|
|
||||||
IMGUI_API VkSurfaceFormatKHR ImGui_ImplVulkan_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space);
|
IMGUI_API VkSurfaceFormatKHR ImGui_ImplVulkan_SelectSurfaceFormat(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkFormat* request_formats, int request_formats_count, VkColorSpaceKHR request_color_space);
|
||||||
IMGUI_API VkPresentModeKHR ImGui_ImplVulkan_SelectPresentMode(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkPresentModeKHR* request_modes, int request_modes_count);
|
IMGUI_API VkPresentModeKHR ImGui_ImplVulkan_SelectPresentMode(VkPhysicalDevice physical_device, VkSurfaceKHR surface, const VkPresentModeKHR* request_modes, int request_modes_count);
|
||||||
|
|
||||||
|
struct ImGui_ImplVulkan_FrameData
|
||||||
|
{
|
||||||
|
uint32_t BackbufferIndex; // keep track of recently rendered swapchain frame indices
|
||||||
|
VkCommandPool CommandPool;
|
||||||
|
VkCommandBuffer CommandBuffer;
|
||||||
|
VkFence Fence;
|
||||||
|
VkSemaphore PresentCompleteSemaphore;
|
||||||
|
VkSemaphore RenderCompleteSemaphore;
|
||||||
|
|
||||||
|
IMGUI_API ImGui_ImplVulkan_FrameData();
|
||||||
|
};
|
||||||
|
|
||||||
|
struct ImGui_ImplVulkan_WindowData
|
||||||
|
{
|
||||||
|
int Width, Height;
|
||||||
|
VkSwapchainKHR Swapchain;
|
||||||
|
VkSurfaceKHR Surface;
|
||||||
|
VkSurfaceFormatKHR SurfaceFormat;
|
||||||
|
VkPresentModeKHR PresentMode;
|
||||||
|
VkRenderPass RenderPass;
|
||||||
|
VkClearValue ClearValue;
|
||||||
|
uint32_t BackBufferCount;
|
||||||
|
VkImage BackBuffer[16];
|
||||||
|
VkImageView BackBufferView[16];
|
||||||
|
VkFramebuffer Framebuffer[16];
|
||||||
|
uint32_t FrameIndex;
|
||||||
|
ImGui_ImplVulkan_FrameData Frames[IMGUI_VK_QUEUED_FRAMES];
|
||||||
|
|
||||||
|
IMGUI_API ImGui_ImplVulkan_WindowData();
|
||||||
|
};
|
||||||
|
@ -10,7 +10,6 @@
|
|||||||
#include <vulkan/vulkan.h>
|
#include <vulkan/vulkan.h>
|
||||||
|
|
||||||
// FIXME-VULKAN: Resizing with IMGUI_UNLIMITED_FRAME_RATE triggers errors from the validation layer.
|
// FIXME-VULKAN: Resizing with IMGUI_UNLIMITED_FRAME_RATE triggers errors from the validation layer.
|
||||||
#define IMGUI_MAX_POSSIBLE_BACK_BUFFERS 16
|
|
||||||
#define IMGUI_UNLIMITED_FRAME_RATE
|
#define IMGUI_UNLIMITED_FRAME_RATE
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
#define IMGUI_VULKAN_DEBUG_REPORT
|
#define IMGUI_VULKAN_DEBUG_REPORT
|
||||||
@ -26,59 +25,7 @@ static VkDebugReportCallbackEXT g_DebugReport = VK_NULL_HANDLE;
|
|||||||
static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE;
|
static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE;
|
||||||
static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE;
|
static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE;
|
||||||
|
|
||||||
struct FrameData
|
static ImGui_ImplVulkan_WindowData g_WindowData;
|
||||||
{
|
|
||||||
uint32_t BackbufferIndex; // keep track of recently rendered swapchain frame indices
|
|
||||||
VkCommandPool CommandPool;
|
|
||||||
VkCommandBuffer CommandBuffer;
|
|
||||||
VkFence Fence;
|
|
||||||
VkSemaphore PresentCompleteSemaphore;
|
|
||||||
VkSemaphore RenderCompleteSemaphore;
|
|
||||||
|
|
||||||
FrameData()
|
|
||||||
{
|
|
||||||
BackbufferIndex = 0;
|
|
||||||
CommandPool = VK_NULL_HANDLE;
|
|
||||||
CommandBuffer = VK_NULL_HANDLE;
|
|
||||||
Fence = VK_NULL_HANDLE;
|
|
||||||
PresentCompleteSemaphore = VK_NULL_HANDLE;
|
|
||||||
RenderCompleteSemaphore = VK_NULL_HANDLE;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct WindowData
|
|
||||||
{
|
|
||||||
int Width, Height;
|
|
||||||
VkSwapchainKHR Swapchain;
|
|
||||||
VkSurfaceKHR Surface;
|
|
||||||
VkSurfaceFormatKHR SurfaceFormat;
|
|
||||||
VkPresentModeKHR PresentMode;
|
|
||||||
VkRenderPass RenderPass;
|
|
||||||
VkClearValue ClearValue;
|
|
||||||
uint32_t BackBufferCount;
|
|
||||||
VkImage BackBuffer[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
VkImageView BackBufferView[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
VkFramebuffer Framebuffer[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
uint32_t FrameIndex;
|
|
||||||
FrameData Frames[IMGUI_VK_QUEUED_FRAMES];
|
|
||||||
|
|
||||||
WindowData()
|
|
||||||
{
|
|
||||||
Width = Height = 0;
|
|
||||||
Swapchain = VK_NULL_HANDLE;
|
|
||||||
Surface = VK_NULL_HANDLE;
|
|
||||||
memset(&SurfaceFormat, 0, sizeof(SurfaceFormat));
|
|
||||||
PresentMode = VK_PRESENT_MODE_MAX_ENUM_KHR;
|
|
||||||
RenderPass = VK_NULL_HANDLE;
|
|
||||||
memset(&ClearValue, 0, sizeof(ClearValue));
|
|
||||||
BackBufferCount = 0;
|
|
||||||
memset(&BackBuffer, 0, sizeof(BackBuffer));
|
|
||||||
memset(&BackBufferView, 0, sizeof(BackBufferView));
|
|
||||||
memset(&Framebuffer, 0, sizeof(Framebuffer));
|
|
||||||
FrameIndex = 0;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
static WindowData g_WindowData;
|
|
||||||
|
|
||||||
static void check_vk_result(VkResult err)
|
static void check_vk_result(VkResult err)
|
||||||
{
|
{
|
||||||
@ -88,7 +35,7 @@ static void check_vk_result(VkResult err)
|
|||||||
abort();
|
abort();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void CreateOrResizeSwapChainAndFrameBuffer(WindowData* wd, int w, int h)
|
static void CreateOrResizeSwapChainAndFrameBuffer(ImGui_ImplVulkan_WindowData* wd, int w, int h)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
VkSwapchainKHR old_swapchain = wd->Swapchain;
|
VkSwapchainKHR old_swapchain = wd->Swapchain;
|
||||||
@ -231,50 +178,49 @@ static void CreateVulkanInstance(const char** extensions, uint32_t extensions_co
|
|||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
|
|
||||||
|
VkInstanceCreateInfo create_info = {};
|
||||||
|
create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
|
||||||
|
create_info.enabledExtensionCount = extensions_count;
|
||||||
|
create_info.ppEnabledExtensionNames = extensions;
|
||||||
|
|
||||||
|
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
||||||
|
// Enabling multiple validation layers grouped as LunarG standard validation
|
||||||
|
const char* layers[] = { "VK_LAYER_LUNARG_standard_validation" };
|
||||||
|
create_info.enabledLayerCount = 1;
|
||||||
|
create_info.ppEnabledLayerNames = layers;
|
||||||
|
|
||||||
|
// Enable debug report extension (we need additional storage, so we duplicate the user array to add our new extension to it)
|
||||||
|
const char** extensions_ext = (const char**)malloc(sizeof(const char*) * (extensions_count + 1));
|
||||||
|
memcpy(extensions_ext, extensions, extensions_count * sizeof(const char*));
|
||||||
|
extensions_ext[extensions_count] = "VK_EXT_debug_report";
|
||||||
|
create_info.enabledExtensionCount = extensions_count + 1;
|
||||||
|
create_info.ppEnabledExtensionNames = extensions_ext;
|
||||||
|
|
||||||
// Create Vulkan Instance
|
// Create Vulkan Instance
|
||||||
{
|
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
||||||
VkInstanceCreateInfo create_info = {};
|
check_vk_result(err);
|
||||||
create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
|
free(extensions_ext);
|
||||||
create_info.enabledExtensionCount = extensions_count;
|
|
||||||
create_info.ppEnabledExtensionNames = extensions;
|
|
||||||
|
|
||||||
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
// Get the function pointer (required for any extensions)
|
||||||
// Enabling multiple validation layers grouped as LunarG standard validation
|
auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT");
|
||||||
const char* layers[] = { "VK_LAYER_LUNARG_standard_validation" };
|
IM_ASSERT(vkCreateDebugReportCallbackEXT != NULL);
|
||||||
create_info.enabledLayerCount = 1;
|
|
||||||
create_info.ppEnabledLayerNames = layers;
|
|
||||||
|
|
||||||
// Enable debug report extension (we need additional storage, so we duplicate the user array to add our new extension to it)
|
// Setup the debug report callback
|
||||||
const char** extensions_ext = (const char**)malloc(sizeof(const char*) * (extensions_count + 1));
|
VkDebugReportCallbackCreateInfoEXT debug_report_ci = {};
|
||||||
memcpy(extensions_ext, extensions, extensions_count * sizeof(const char*));
|
debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
|
||||||
extensions_ext[extensions_count] = "VK_EXT_debug_report";
|
debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT;
|
||||||
create_info.enabledExtensionCount = extensions_count + 1;
|
debug_report_ci.pfnCallback = debug_report;
|
||||||
create_info.ppEnabledExtensionNames = extensions_ext;
|
debug_report_ci.pUserData = NULL;
|
||||||
#endif // IMGUI_VULKAN_DEBUG_REPORT
|
err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport);
|
||||||
|
check_vk_result(err);
|
||||||
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
#else
|
||||||
check_vk_result(err);
|
// Create Vulkan Instance without any debug feature
|
||||||
|
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
||||||
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
check_vk_result(err);
|
||||||
free(extensions_ext);
|
#endif
|
||||||
|
|
||||||
// Get the function pointer (required for any extensions)
|
|
||||||
auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT");
|
|
||||||
IM_ASSERT(vkCreateDebugReportCallbackEXT != NULL);
|
|
||||||
|
|
||||||
// Setup the debug report callback
|
|
||||||
VkDebugReportCallbackCreateInfoEXT debug_report_ci = {};
|
|
||||||
debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
|
|
||||||
debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT;
|
|
||||||
debug_report_ci.pfnCallback = debug_report;
|
|
||||||
debug_report_ci.pUserData = NULL;
|
|
||||||
err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport);
|
|
||||||
check_vk_result(err);
|
|
||||||
#endif // IMGUI_VULKAN_DEBUG_REPORT
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetupVulkan(WindowData* wd)
|
static void SetupVulkan(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
|
|
||||||
@ -322,7 +268,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Get Surface Format
|
// Get Surface Format
|
||||||
{
|
{
|
||||||
const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
|
const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
|
||||||
@ -330,7 +275,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
wd->SurfaceFormat = ImGui_ImplVulkan_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace);
|
wd->SurfaceFormat = ImGui_ImplVulkan_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Get Present Mode
|
// Get Present Mode
|
||||||
{
|
{
|
||||||
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
||||||
@ -341,7 +285,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
wd->PresentMode = ImGui_ImplVulkan_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_mode, 1);
|
wd->PresentMode = ImGui_ImplVulkan_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_mode, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Create Logical Device (with 1 queue)
|
// Create Logical Device (with 1 queue)
|
||||||
{
|
{
|
||||||
int device_extension_count = 1;
|
int device_extension_count = 1;
|
||||||
@ -366,7 +309,7 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
// Create Command Buffers
|
// Create Command Buffers
|
||||||
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[i];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[i];
|
||||||
{
|
{
|
||||||
VkCommandPoolCreateInfo info = {};
|
VkCommandPoolCreateInfo info = {};
|
||||||
info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO;
|
info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO;
|
||||||
@ -430,11 +373,11 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
|
|
||||||
static void cleanup_vulkan()
|
static void cleanup_vulkan()
|
||||||
{
|
{
|
||||||
WindowData* wd = &g_WindowData;
|
ImGui_ImplVulkan_WindowData* wd = &g_WindowData;
|
||||||
vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);
|
vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);
|
||||||
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[i];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[i];
|
||||||
vkDestroyFence(g_Device, fd->Fence, g_Allocator);
|
vkDestroyFence(g_Device, fd->Fence, g_Allocator);
|
||||||
vkFreeCommandBuffers(g_Device, fd->CommandPool, 1, &fd->CommandBuffer);
|
vkFreeCommandBuffers(g_Device, fd->CommandPool, 1, &fd->CommandBuffer);
|
||||||
vkDestroyCommandPool(g_Device, fd->CommandPool, g_Allocator);
|
vkDestroyCommandPool(g_Device, fd->CommandPool, g_Allocator);
|
||||||
@ -460,9 +403,9 @@ static void cleanup_vulkan()
|
|||||||
vkDestroyInstance(g_Instance, g_Allocator);
|
vkDestroyInstance(g_Instance, g_Allocator);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_begin(WindowData* wd)
|
static void frame_begin(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[wd->FrameIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[wd->FrameIndex];
|
||||||
VkResult err;
|
VkResult err;
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
@ -497,9 +440,9 @@ static void frame_begin(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_end(WindowData* wd)
|
static void frame_end(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[wd->FrameIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[wd->FrameIndex];
|
||||||
VkResult err;
|
VkResult err;
|
||||||
vkCmdEndRenderPass(fd->CommandBuffer);
|
vkCmdEndRenderPass(fd->CommandBuffer);
|
||||||
{
|
{
|
||||||
@ -523,7 +466,7 @@ static void frame_end(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_present(WindowData* wd)
|
static void frame_present(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
// If IMGUI_UNLIMITED_FRAME_RATE is defined we present the latest but one frame. Otherwise we present the latest rendered frame
|
// If IMGUI_UNLIMITED_FRAME_RATE is defined we present the latest but one frame. Otherwise we present the latest rendered frame
|
||||||
@ -533,7 +476,7 @@ static void frame_present(WindowData* wd)
|
|||||||
uint32_t PresentIndex = g_FrameIndex;
|
uint32_t PresentIndex = g_FrameIndex;
|
||||||
#endif // IMGUI_UNLIMITED_FRAME_RATE
|
#endif // IMGUI_UNLIMITED_FRAME_RATE
|
||||||
|
|
||||||
FrameData* fd = &wd->Frames[PresentIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[PresentIndex];
|
||||||
VkPresentInfoKHR info = {};
|
VkPresentInfoKHR info = {};
|
||||||
info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
|
info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
|
||||||
info.waitSemaphoreCount = 1;
|
info.waitSemaphoreCount = 1;
|
||||||
@ -568,7 +511,7 @@ int main(int, char**)
|
|||||||
delete[] sdl_extensions;
|
delete[] sdl_extensions;
|
||||||
|
|
||||||
// Create Window Surface
|
// Create Window Surface
|
||||||
WindowData* wd = &g_WindowData;
|
ImGui_ImplVulkan_WindowData* wd = &g_WindowData;
|
||||||
SDL_bool result = SDL_Vulkan_CreateSurface(window, g_Instance, &wd->Surface);
|
SDL_bool result = SDL_Vulkan_CreateSurface(window, g_Instance, &wd->Surface);
|
||||||
if (result == 0)
|
if (result == 0)
|
||||||
{
|
{
|
||||||
@ -723,6 +666,8 @@ int main(int, char**)
|
|||||||
ImGui_ImplVulkan_Render(wd->Frames[wd->FrameIndex].CommandBuffer);
|
ImGui_ImplVulkan_Render(wd->Frames[wd->FrameIndex].CommandBuffer);
|
||||||
frame_end(wd);
|
frame_end(wd);
|
||||||
|
|
||||||
|
ImGui::RenderAdditionalViewports();
|
||||||
|
|
||||||
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
||||||
// When IMGUI_UNLIMITED_FRAME_RATE is defined we render into latest image acquired from the swapchain but we display the image which was rendered before.
|
// When IMGUI_UNLIMITED_FRAME_RATE is defined we render into latest image acquired from the swapchain but we display the image which was rendered before.
|
||||||
// Hence we must render once and increase the FrameIndex without presenting.
|
// Hence we must render once and increase the FrameIndex without presenting.
|
||||||
@ -733,7 +678,6 @@ int main(int, char**)
|
|||||||
#endif
|
#endif
|
||||||
swap_chain_has_at_least_one_image = true;
|
swap_chain_has_at_least_one_image = true;
|
||||||
wd->FrameIndex = (wd->FrameIndex + 1) % IMGUI_VK_QUEUED_FRAMES;
|
wd->FrameIndex = (wd->FrameIndex + 1) % IMGUI_VK_QUEUED_FRAMES;
|
||||||
ImGui::RenderAdditionalViewports();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cleanup
|
// Cleanup
|
||||||
|
@ -13,7 +13,6 @@
|
|||||||
#include <vulkan/vulkan.h>
|
#include <vulkan/vulkan.h>
|
||||||
|
|
||||||
// FIXME-VULKAN: Resizing with IMGUI_UNLIMITED_FRAME_RATE triggers errors from the validation layer.
|
// FIXME-VULKAN: Resizing with IMGUI_UNLIMITED_FRAME_RATE triggers errors from the validation layer.
|
||||||
#define IMGUI_MAX_POSSIBLE_BACK_BUFFERS 16
|
|
||||||
#define IMGUI_UNLIMITED_FRAME_RATE
|
#define IMGUI_UNLIMITED_FRAME_RATE
|
||||||
#ifdef _DEBUG
|
#ifdef _DEBUG
|
||||||
#define IMGUI_VULKAN_DEBUG_REPORT
|
#define IMGUI_VULKAN_DEBUG_REPORT
|
||||||
@ -29,59 +28,7 @@ static VkDebugReportCallbackEXT g_DebugReport = VK_NULL_HANDLE;
|
|||||||
static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE;
|
static VkPipelineCache g_PipelineCache = VK_NULL_HANDLE;
|
||||||
static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE;
|
static VkDescriptorPool g_DescriptorPool = VK_NULL_HANDLE;
|
||||||
|
|
||||||
struct FrameData
|
static ImGui_ImplVulkan_WindowData g_WindowData;
|
||||||
{
|
|
||||||
uint32_t BackbufferIndex; // keep track of recently rendered swapchain frame indices
|
|
||||||
VkCommandPool CommandPool;
|
|
||||||
VkCommandBuffer CommandBuffer;
|
|
||||||
VkFence Fence;
|
|
||||||
VkSemaphore PresentCompleteSemaphore;
|
|
||||||
VkSemaphore RenderCompleteSemaphore;
|
|
||||||
|
|
||||||
FrameData()
|
|
||||||
{
|
|
||||||
BackbufferIndex = 0;
|
|
||||||
CommandPool = VK_NULL_HANDLE;
|
|
||||||
CommandBuffer = VK_NULL_HANDLE;
|
|
||||||
Fence = VK_NULL_HANDLE;
|
|
||||||
PresentCompleteSemaphore = VK_NULL_HANDLE;
|
|
||||||
RenderCompleteSemaphore = VK_NULL_HANDLE;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct WindowData
|
|
||||||
{
|
|
||||||
int Width, Height;
|
|
||||||
VkSwapchainKHR Swapchain;
|
|
||||||
VkSurfaceKHR Surface;
|
|
||||||
VkSurfaceFormatKHR SurfaceFormat;
|
|
||||||
VkPresentModeKHR PresentMode;
|
|
||||||
VkRenderPass RenderPass;
|
|
||||||
VkClearValue ClearValue;
|
|
||||||
uint32_t BackBufferCount;
|
|
||||||
VkImage BackBuffer[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
VkImageView BackBufferView[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
VkFramebuffer Framebuffer[IMGUI_MAX_POSSIBLE_BACK_BUFFERS];
|
|
||||||
uint32_t FrameIndex;
|
|
||||||
FrameData Frames[IMGUI_VK_QUEUED_FRAMES];
|
|
||||||
|
|
||||||
WindowData()
|
|
||||||
{
|
|
||||||
Width = Height = 0;
|
|
||||||
Swapchain = VK_NULL_HANDLE;
|
|
||||||
Surface = VK_NULL_HANDLE;
|
|
||||||
memset(&SurfaceFormat, 0, sizeof(SurfaceFormat));
|
|
||||||
PresentMode = VK_PRESENT_MODE_MAX_ENUM_KHR;
|
|
||||||
RenderPass = VK_NULL_HANDLE;
|
|
||||||
memset(&ClearValue, 0, sizeof(ClearValue));
|
|
||||||
BackBufferCount = 0;
|
|
||||||
memset(&BackBuffer, 0, sizeof(BackBuffer));
|
|
||||||
memset(&BackBufferView, 0, sizeof(BackBufferView));
|
|
||||||
memset(&Framebuffer, 0, sizeof(Framebuffer));
|
|
||||||
FrameIndex = 0;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
static WindowData g_WindowData;
|
|
||||||
|
|
||||||
static void check_vk_result(VkResult err)
|
static void check_vk_result(VkResult err)
|
||||||
{
|
{
|
||||||
@ -91,7 +38,7 @@ static void check_vk_result(VkResult err)
|
|||||||
abort();
|
abort();
|
||||||
}
|
}
|
||||||
|
|
||||||
static void CreateOrResizeSwapChainAndFrameBuffer(WindowData* wd, int w, int h)
|
static void CreateOrResizeSwapChainAndFrameBuffer(ImGui_ImplVulkan_WindowData* wd, int w, int h)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
VkSwapchainKHR old_swapchain = wd->Swapchain;
|
VkSwapchainKHR old_swapchain = wd->Swapchain;
|
||||||
@ -147,6 +94,7 @@ static void CreateOrResizeSwapChainAndFrameBuffer(WindowData* wd, int w, int h)
|
|||||||
check_vk_result(err);
|
check_vk_result(err);
|
||||||
err = vkGetSwapchainImagesKHR(g_Device, wd->Swapchain, &wd->BackBufferCount, NULL);
|
err = vkGetSwapchainImagesKHR(g_Device, wd->Swapchain, &wd->BackBufferCount, NULL);
|
||||||
check_vk_result(err);
|
check_vk_result(err);
|
||||||
|
IM_ASSERT(wd->BackBufferCount < IM_ARRAYSIZE(wd->BackBuffer));
|
||||||
err = vkGetSwapchainImagesKHR(g_Device, wd->Swapchain, &wd->BackBufferCount, wd->BackBuffer);
|
err = vkGetSwapchainImagesKHR(g_Device, wd->Swapchain, &wd->BackBufferCount, wd->BackBuffer);
|
||||||
check_vk_result(err);
|
check_vk_result(err);
|
||||||
}
|
}
|
||||||
@ -234,50 +182,49 @@ static void CreateVulkanInstance(const char** extensions, uint32_t extensions_co
|
|||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
|
|
||||||
|
VkInstanceCreateInfo create_info = {};
|
||||||
|
create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
|
||||||
|
create_info.enabledExtensionCount = extensions_count;
|
||||||
|
create_info.ppEnabledExtensionNames = extensions;
|
||||||
|
|
||||||
|
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
||||||
|
// Enabling multiple validation layers grouped as LunarG standard validation
|
||||||
|
const char* layers[] = { "VK_LAYER_LUNARG_standard_validation" };
|
||||||
|
create_info.enabledLayerCount = 1;
|
||||||
|
create_info.ppEnabledLayerNames = layers;
|
||||||
|
|
||||||
|
// Enable debug report extension (we need additional storage, so we duplicate the user array to add our new extension to it)
|
||||||
|
const char** extensions_ext = (const char**)malloc(sizeof(const char*) * (extensions_count + 1));
|
||||||
|
memcpy(extensions_ext, extensions, extensions_count * sizeof(const char*));
|
||||||
|
extensions_ext[extensions_count] = "VK_EXT_debug_report";
|
||||||
|
create_info.enabledExtensionCount = extensions_count + 1;
|
||||||
|
create_info.ppEnabledExtensionNames = extensions_ext;
|
||||||
|
|
||||||
// Create Vulkan Instance
|
// Create Vulkan Instance
|
||||||
{
|
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
||||||
VkInstanceCreateInfo create_info = {};
|
check_vk_result(err);
|
||||||
create_info.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
|
free(extensions_ext);
|
||||||
create_info.enabledExtensionCount = extensions_count;
|
|
||||||
create_info.ppEnabledExtensionNames = extensions;
|
|
||||||
|
|
||||||
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
// Get the function pointer (required for any extensions)
|
||||||
// Enabling multiple validation layers grouped as LunarG standard validation
|
auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT");
|
||||||
const char* layers[] = { "VK_LAYER_LUNARG_standard_validation" };
|
IM_ASSERT(vkCreateDebugReportCallbackEXT != NULL);
|
||||||
create_info.enabledLayerCount = 1;
|
|
||||||
create_info.ppEnabledLayerNames = layers;
|
|
||||||
|
|
||||||
// Enable debug report extension (we need additional storage, so we duplicate the user array to add our new extension to it)
|
// Setup the debug report callback
|
||||||
const char** extensions_ext = (const char**)malloc(sizeof(const char*) * (extensions_count + 1));
|
VkDebugReportCallbackCreateInfoEXT debug_report_ci = {};
|
||||||
memcpy(extensions_ext, extensions, extensions_count * sizeof(const char*));
|
debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
|
||||||
extensions_ext[extensions_count] = "VK_EXT_debug_report";
|
debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT;
|
||||||
create_info.enabledExtensionCount = extensions_count + 1;
|
debug_report_ci.pfnCallback = debug_report;
|
||||||
create_info.ppEnabledExtensionNames = extensions_ext;
|
debug_report_ci.pUserData = NULL;
|
||||||
#endif // IMGUI_VULKAN_DEBUG_REPORT
|
err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport);
|
||||||
|
check_vk_result(err);
|
||||||
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
#else
|
||||||
check_vk_result(err);
|
// Create Vulkan Instance without any debug feature
|
||||||
|
err = vkCreateInstance(&create_info, g_Allocator, &g_Instance);
|
||||||
#ifdef IMGUI_VULKAN_DEBUG_REPORT
|
check_vk_result(err);
|
||||||
free(extensions_ext);
|
#endif
|
||||||
|
|
||||||
// Get the function pointer (required for any extensions)
|
|
||||||
auto vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)vkGetInstanceProcAddr(g_Instance, "vkCreateDebugReportCallbackEXT");
|
|
||||||
IM_ASSERT(vkCreateDebugReportCallbackEXT != NULL);
|
|
||||||
|
|
||||||
// Setup the debug report callback
|
|
||||||
VkDebugReportCallbackCreateInfoEXT debug_report_ci = {};
|
|
||||||
debug_report_ci.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
|
|
||||||
debug_report_ci.flags = VK_DEBUG_REPORT_ERROR_BIT_EXT | VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT;
|
|
||||||
debug_report_ci.pfnCallback = debug_report;
|
|
||||||
debug_report_ci.pUserData = NULL;
|
|
||||||
err = vkCreateDebugReportCallbackEXT(g_Instance, &debug_report_ci, g_Allocator, &g_DebugReport);
|
|
||||||
check_vk_result(err);
|
|
||||||
#endif // IMGUI_VULKAN_DEBUG_REPORT
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void SetupVulkan(WindowData* wd)
|
static void SetupVulkan(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
|
|
||||||
@ -325,7 +272,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Get Surface Format
|
// Get Surface Format
|
||||||
{
|
{
|
||||||
const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
|
const VkFormat requestSurfaceImageFormat[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
|
||||||
@ -333,7 +279,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
wd->SurfaceFormat = ImGui_ImplVulkan_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace);
|
wd->SurfaceFormat = ImGui_ImplVulkan_SelectSurfaceFormat(g_PhysicalDevice, wd->Surface, requestSurfaceImageFormat, (size_t)IM_ARRAYSIZE(requestSurfaceImageFormat), requestSurfaceColorSpace);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Get Present Mode
|
// Get Present Mode
|
||||||
{
|
{
|
||||||
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
||||||
@ -344,7 +289,6 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
wd->PresentMode = ImGui_ImplVulkan_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_mode, 1);
|
wd->PresentMode = ImGui_ImplVulkan_SelectPresentMode(g_PhysicalDevice, wd->Surface, &present_mode, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Create Logical Device (with 1 queue)
|
// Create Logical Device (with 1 queue)
|
||||||
{
|
{
|
||||||
int device_extension_count = 1;
|
int device_extension_count = 1;
|
||||||
@ -369,7 +313,7 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
// Create Command Buffers
|
// Create Command Buffers
|
||||||
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[i];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[i];
|
||||||
{
|
{
|
||||||
VkCommandPoolCreateInfo info = {};
|
VkCommandPoolCreateInfo info = {};
|
||||||
info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO;
|
info.sType = VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO;
|
||||||
@ -433,11 +377,11 @@ static void SetupVulkan(WindowData* wd)
|
|||||||
|
|
||||||
static void cleanup_vulkan()
|
static void cleanup_vulkan()
|
||||||
{
|
{
|
||||||
WindowData* wd = &g_WindowData;
|
ImGui_ImplVulkan_WindowData* wd = &g_WindowData;
|
||||||
vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);
|
vkDestroyDescriptorPool(g_Device, g_DescriptorPool, g_Allocator);
|
||||||
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
for (int i = 0; i < IMGUI_VK_QUEUED_FRAMES; i++)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[i];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[i];
|
||||||
vkDestroyFence(g_Device, fd->Fence, g_Allocator);
|
vkDestroyFence(g_Device, fd->Fence, g_Allocator);
|
||||||
vkFreeCommandBuffers(g_Device, fd->CommandPool, 1, &fd->CommandBuffer);
|
vkFreeCommandBuffers(g_Device, fd->CommandPool, 1, &fd->CommandBuffer);
|
||||||
vkDestroyCommandPool(g_Device, fd->CommandPool, g_Allocator);
|
vkDestroyCommandPool(g_Device, fd->CommandPool, g_Allocator);
|
||||||
@ -463,9 +407,9 @@ static void cleanup_vulkan()
|
|||||||
vkDestroyInstance(g_Instance, g_Allocator);
|
vkDestroyInstance(g_Instance, g_Allocator);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_begin(WindowData* wd)
|
static void frame_begin(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[wd->FrameIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[wd->FrameIndex];
|
||||||
VkResult err;
|
VkResult err;
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
@ -500,9 +444,9 @@ static void frame_begin(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_end(WindowData* wd)
|
static void frame_end(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
FrameData* fd = &wd->Frames[wd->FrameIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[wd->FrameIndex];
|
||||||
VkResult err;
|
VkResult err;
|
||||||
vkCmdEndRenderPass(fd->CommandBuffer);
|
vkCmdEndRenderPass(fd->CommandBuffer);
|
||||||
{
|
{
|
||||||
@ -526,7 +470,7 @@ static void frame_end(WindowData* wd)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void frame_present(WindowData* wd)
|
static void frame_present(ImGui_ImplVulkan_WindowData* wd)
|
||||||
{
|
{
|
||||||
VkResult err;
|
VkResult err;
|
||||||
// If IMGUI_UNLIMITED_FRAME_RATE is defined we present the latest but one frame. Otherwise we present the latest rendered frame
|
// If IMGUI_UNLIMITED_FRAME_RATE is defined we present the latest but one frame. Otherwise we present the latest rendered frame
|
||||||
@ -536,7 +480,7 @@ static void frame_present(WindowData* wd)
|
|||||||
uint32_t PresentIndex = g_FrameIndex;
|
uint32_t PresentIndex = g_FrameIndex;
|
||||||
#endif // IMGUI_UNLIMITED_FRAME_RATE
|
#endif // IMGUI_UNLIMITED_FRAME_RATE
|
||||||
|
|
||||||
FrameData* fd = &wd->Frames[PresentIndex];
|
ImGui_ImplVulkan_FrameData* fd = &wd->Frames[PresentIndex];
|
||||||
VkPresentInfoKHR info = {};
|
VkPresentInfoKHR info = {};
|
||||||
info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
|
info.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
|
||||||
info.waitSemaphoreCount = 1;
|
info.waitSemaphoreCount = 1;
|
||||||
@ -579,7 +523,7 @@ int main(int, char**)
|
|||||||
CreateVulkanInstance(glfw_extensions, glfw_extensions_count);
|
CreateVulkanInstance(glfw_extensions, glfw_extensions_count);
|
||||||
|
|
||||||
// Create Window Surface
|
// Create Window Surface
|
||||||
WindowData* wd = &g_WindowData;
|
ImGui_ImplVulkan_WindowData* wd = &g_WindowData;
|
||||||
{
|
{
|
||||||
VkResult err = glfwCreateWindowSurface(g_Instance, window, g_Allocator, &wd->Surface);
|
VkResult err = glfwCreateWindowSurface(g_Instance, window, g_Allocator, &wd->Surface);
|
||||||
check_vk_result(err);
|
check_vk_result(err);
|
||||||
@ -724,6 +668,8 @@ int main(int, char**)
|
|||||||
ImGui_ImplVulkan_Render(wd->Frames[wd->FrameIndex].CommandBuffer);
|
ImGui_ImplVulkan_Render(wd->Frames[wd->FrameIndex].CommandBuffer);
|
||||||
frame_end(wd);
|
frame_end(wd);
|
||||||
|
|
||||||
|
ImGui::RenderAdditionalViewports();
|
||||||
|
|
||||||
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
#ifdef IMGUI_UNLIMITED_FRAME_RATE
|
||||||
// When IMGUI_UNLIMITED_FRAME_RATE is defined we render into latest image acquired from the swapchain but we display the image which was rendered before.
|
// When IMGUI_UNLIMITED_FRAME_RATE is defined we render into latest image acquired from the swapchain but we display the image which was rendered before.
|
||||||
// Hence we must render once and increase the FrameIndex without presenting.
|
// Hence we must render once and increase the FrameIndex without presenting.
|
||||||
@ -734,8 +680,6 @@ int main(int, char**)
|
|||||||
#endif
|
#endif
|
||||||
swap_chain_has_at_least_one_image = true;
|
swap_chain_has_at_least_one_image = true;
|
||||||
wd->FrameIndex = (wd->FrameIndex + 1) % IMGUI_VK_QUEUED_FRAMES;
|
wd->FrameIndex = (wd->FrameIndex + 1) % IMGUI_VK_QUEUED_FRAMES;
|
||||||
|
|
||||||
//ImGui::RenderAdditionalViewports();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cleanup
|
// Cleanup
|
||||||
|
Loading…
Reference in New Issue
Block a user