1
0
Fork 0
mirror of https://github.com/ocornut/imgui.git synced 2026-01-11 00:04:24 +00:00

Backends: Vulkan: Replaced InitInfo's PipelineInfo PipelineInfoForViewports by SecondaryViewportsInfo SecondaryViewportsInfo

- `PipelineInfoForViewports` was confusing (only one (or two) out of the five (or six) parameters was actually used).
- Add `struct ImGui_ImplVulkan_SecondaryViewportsInfo` for viewports specific informations (to be extended and re-used)
This commit is contained in:
Ronan Cailleau 2025-10-07 16:05:17 +02:00
parent 2289b6252a
commit ea33a483ba
2 changed files with 32 additions and 20 deletions

View file

@ -282,7 +282,6 @@ struct ImGui_ImplVulkan_Data
VkDescriptorSetLayout DescriptorSetLayout;
VkPipelineLayout PipelineLayout;
VkPipeline Pipeline; // pipeline for main render pass (created by app)
VkPipeline PipelineForViewports; // pipeline for secondary viewports (created by backend)
VkShaderModule ShaderModuleVert;
VkShaderModule ShaderModuleFrag;
VkDescriptorPool DescriptorPool;
@ -296,6 +295,12 @@ struct ImGui_ImplVulkan_Data
// Render buffers for main window
ImGui_ImplVulkan_WindowRenderBuffers MainWindowRenderBuffers;
// Viewports common data
// Filled during ImGui_ImplVulkan_PrepareViewportsRendering() based on ViewportsFormat and VulkanInitInfo->SecondaryViewportsInfo
ImGui_ImplVulkan_PipelineInfo PipelineInfoForViewports;
VkPipeline PipelineForViewports; // pipeline for secondary viewports (created by backend)
ImGui_ImplVulkan_Data()
{
memset((void*)this, 0, sizeof(*this));
@ -1321,7 +1326,7 @@ bool ImGui_ImplVulkan_Init(ImGui_ImplVulkan_InitInfo* info)
else
IM_ASSERT(info->DescriptorPoolSize > 0);
if (info->UseDynamicRendering)
IM_ASSERT(info->PipelineInfoMain.RenderPass == VK_NULL_HANDLE && info->PipelineInfoForViewports.RenderPass == VK_NULL_HANDLE);
IM_ASSERT(info->PipelineInfoMain.RenderPass == VK_NULL_HANDLE);
bd->VulkanInitInfo = *info;
@ -1978,18 +1983,18 @@ static void ImGui_ImplVulkan_CreateWindow(ImGuiViewport* viewport)
}
// Select Surface Format
ImGui_ImplVulkan_PipelineInfo* pipeline_info = &v->PipelineInfoForViewports;
ImVector<VkFormat> requestSurfaceImageFormats;
#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING
for (uint32_t n = 0; n < pipeline_info->PipelineRenderingCreateInfo.colorAttachmentCount; n++)
requestSurfaceImageFormats.push_back(pipeline_info->PipelineRenderingCreateInfo.pColorAttachmentFormats[n]);
#endif
const VkFormat defaultFormats[] = { VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
for (VkFormat format : defaultFormats)
requestSurfaceImageFormats.push_back(format);
ImGui_ImplVulkan_PipelineInfo* pipeline_info = &bd->PipelineInfoForViewports;
const VkFormat requestSurfaceImageFormats[] = { v->SecondaryViewportsInfo.DesiredFormat.format, VK_FORMAT_B8G8R8A8_UNORM, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_B8G8R8_UNORM, VK_FORMAT_R8G8B8_UNORM };
int requestSurfaceImageFormatsCount = IM_ARRAYSIZE(requestSurfaceImageFormats);
const VkFormat* pRequestSurfaceImageFormats = requestSurfaceImageFormats;
if (pRequestSurfaceImageFormats[0] == VK_FORMAT_UNDEFINED)
{
++pRequestSurfaceImageFormats;
--requestSurfaceImageFormatsCount;
}
const VkColorSpaceKHR requestSurfaceColorSpace = VK_COLORSPACE_SRGB_NONLINEAR_KHR;
wd->SurfaceFormat = ImGui_ImplVulkanH_SelectSurfaceFormat(v->PhysicalDevice, wd->Surface, requestSurfaceImageFormats.Data, (size_t)requestSurfaceImageFormats.Size, requestSurfaceColorSpace);
const VkColorSpaceKHR requestSurfaceColorSpace = v->SecondaryViewportsInfo.DesiredFormat.colorSpace;
wd->SurfaceFormat = ImGui_ImplVulkanH_SelectSurfaceFormat(v->PhysicalDevice, wd->Surface, pRequestSurfaceImageFormats, requestSurfaceImageFormatsCount, requestSurfaceColorSpace);
// Select Present Mode
// FIXME-VULKAN: Even thought mailbox seems to get us maximum framerate with a single window, it halves framerate with a second window etc. (w/ Nvidia and SDK 1.82.1)
@ -2000,7 +2005,7 @@ static void ImGui_ImplVulkan_CreateWindow(ImGuiViewport* viewport)
// Create SwapChain, RenderPass, Framebuffer, etc.
wd->ClearEnable = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? false : true;
wd->UseDynamicRendering = v->UseDynamicRendering;
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, wd, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount, pipeline_info->SwapChainImageUsage);
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, wd, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount, v->SecondaryViewportsInfo.SwapChainImageUsage);
vd->WindowOwned = true;
// Create pipeline (shared by all secondary viewports)
@ -2018,7 +2023,7 @@ static void ImGui_ImplVulkan_CreateWindow(ImGuiViewport* viewport)
pipeline_info->RenderPass = wd->RenderPass;
}
#endif
bd->PipelineForViewports = ImGui_ImplVulkan_CreatePipeline(v->Device, v->Allocator, VK_NULL_HANDLE, &v->PipelineInfoForViewports);
bd->PipelineForViewports = ImGui_ImplVulkan_CreatePipeline(v->Device, v->Allocator, VK_NULL_HANDLE, pipeline_info);
}
}
@ -2045,7 +2050,7 @@ static void ImGui_ImplVulkan_SetWindowSize(ImGuiViewport* viewport, ImVec2 size)
return;
ImGui_ImplVulkan_InitInfo* v = &bd->VulkanInitInfo;
vd->Window.ClearEnable = (viewport->Flags & ImGuiViewportFlags_NoRendererClear) ? false : true;
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, &vd->Window, v->QueueFamily, v->Allocator, (int)size.x, (int)size.y, v->MinImageCount, v->PipelineInfoForViewports.SwapChainImageUsage);
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, &vd->Window, v->QueueFamily, v->Allocator, (int)size.x, (int)size.y, v->MinImageCount, v->SecondaryViewportsInfo.SwapChainImageUsage);
}
static void ImGui_ImplVulkan_RenderWindow(ImGuiViewport* viewport, void*)
@ -2058,7 +2063,7 @@ static void ImGui_ImplVulkan_RenderWindow(ImGuiViewport* viewport, void*)
if (vd->SwapChainNeedRebuild || vd->SwapChainSuboptimal)
{
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, wd, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount, v->PipelineInfoForViewports.SwapChainImageUsage);
ImGui_ImplVulkanH_CreateOrResizeWindow(v->Instance, v->PhysicalDevice, v->Device, wd, v->QueueFamily, v->Allocator, (int)viewport->Size.x, (int)viewport->Size.y, v->MinImageCount, v->SecondaryViewportsInfo.SwapChainImageUsage);
vd->SwapChainNeedRebuild = vd->SwapChainSuboptimal = false;
}

View file

@ -66,7 +66,7 @@
// Backend uses a small number of descriptors per font atlas + as many as additional calls done to ImGui_ImplVulkan_AddTexture().
#define IMGUI_IMPL_VULKAN_MINIMUM_IMAGE_SAMPLER_POOL_SIZE (8) // Minimum per atlas
// Specify settings to create pipeline and swapchain
// Specify settings to create pipeline
struct ImGui_ImplVulkan_PipelineInfo
{
// For Main viewport only
@ -78,8 +78,13 @@ struct ImGui_ImplVulkan_PipelineInfo
#ifdef IMGUI_IMPL_VULKAN_HAS_DYNAMIC_RENDERING
VkPipelineRenderingCreateInfoKHR PipelineRenderingCreateInfo; // Optional, valid if .sType == VK_STRUCTURE_TYPE_PIPELINE_RENDERING_CREATE_INFO_KHR
#endif
};
struct ImGui_ImplVulkan_SecondaryViewportsInfo
{
// Ignored if .format == VK_FORMAT_UNDEFINED
VkSurfaceFormatKHR DesiredFormat;
// For Secondary viewports only (created/managed by backend)
VkImageUsageFlags SwapChainImageUsage; // Extra flags for vkCreateSwapchainKHR() calls for secondary viewports. We automatically add VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT. You can add e.g. VK_IMAGE_USAGE_TRANSFER_SRC_BIT if you need to capture from viewports.
};
@ -107,7 +112,6 @@ struct ImGui_ImplVulkan_InitInfo
// Pipeline
ImGui_ImplVulkan_PipelineInfo PipelineInfoMain; // Infos for Main Viewport (created by app/user)
ImGui_ImplVulkan_PipelineInfo PipelineInfoForViewports; // Infos for Secondary Viewports (created by backend)
//VkRenderPass RenderPass; // --> Since 2025/09/26: set 'PipelineInfoMain.RenderPass' instead
//uint32_t Subpass; // --> Since 2025/09/26: set 'PipelineInfoMain.Subpass' instead
//VkSampleCountFlagBits MSAASamples; // --> Since 2025/09/26: set 'PipelineInfoMain.MSAASamples' instead
@ -117,6 +121,9 @@ struct ImGui_ImplVulkan_InitInfo
// Need to explicitly enable VK_KHR_dynamic_rendering extension to use this, even for Vulkan 1.3 + setup PipelineInfoMain.PipelineRenderingCreateInfo and PipelineInfoViewports.PipelineRenderingCreateInfo.
bool UseDynamicRendering;
// Optional
ImGui_ImplVulkan_SecondaryViewportsInfo SecondaryViewportsInfo;
// (Optional) Allocation, Debugging
const VkAllocationCallbacks* Allocator;
void (*CheckVkResultFn)(VkResult err);