@@ -50,10 +50,12 @@ namespace ZEngine::Hardwares
5050
5151 ImageInFlights.init (&Arena, SwapchainImageCount, SwapchainImageCount);
5252 RenderCompletes.init (&Arena, SwapchainImageCount, SwapchainImageCount);
53+ PresentCompletes.init (&Arena, SwapchainImageCount, SwapchainImageCount);
5354 for (uint32_t i = 0 ; i < SwapchainImageCount; ++i)
5455 {
55- ImageInFlights[i] = nullptr ;
56- RenderCompletes[i] = ZPushStructCtorArgs (&Arena, Primitives::Semaphore, Device);
56+ ImageInFlights[i] = nullptr ;
57+ RenderCompletes[i] = ZPushStructCtorArgs (&Arena, Primitives::Semaphore, Device);
58+ PresentCompletes[i] = ZPushStructCtorArgs (&Arena, Primitives::Fence, Device);
5759 }
5860 }
5961
@@ -67,6 +69,7 @@ namespace ZEngine::Hardwares
6769 SwapchainImageHeight = capabilities.currentExtent .height ;
6870 }
6971
72+ VkSwapchainKHR old_swapchain = (SwapchainHandle != VK_NULL_HANDLE) ? SwapchainHandle : VK_NULL_HANDLE;
7073 auto min_image_count = std::clamp (capabilities.minImageCount , capabilities.minImageCount , capabilities.maxImageCount == 0 ? capabilities.minImageCount + 1 : capabilities.maxImageCount );
7174 VkSwapchainCreateInfoKHR swapchain_create_info = {
7275 .sType = VK_STRUCTURE_TYPE_SWAPCHAIN_CREATE_INFO_KHR,
@@ -82,7 +85,7 @@ namespace ZEngine::Hardwares
8285 .compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR,
8386 .presentMode = Device->PresentMode ,
8487 .clipped = VK_TRUE,
85- .oldSwapchain = (SwapchainHandle != VK_NULL_HANDLE) ? SwapchainHandle : VK_NULL_HANDLE
88+ .oldSwapchain = old_swapchain,
8689 };
8790
8891 auto scratch = ZGetScratch (&Arena);
@@ -129,6 +132,11 @@ namespace ZEngine::Hardwares
129132 }
130133
131134 ZReleaseScratch (scratch);
135+
136+ if (old_swapchain != VK_NULL_HANDLE)
137+ {
138+ ZENGINE_DESTROY_VULKAN_HANDLE (Device->LogicalDevice , vkDestroySwapchainKHR, old_swapchain, nullptr )
139+ }
132140 }
133141
134142 void DeviceSwapchain::Clear ()
@@ -183,13 +191,23 @@ namespace ZEngine::Hardwares
183191 }
184192 }
185193
194+ for (uint32_t i = 0 ; i < PresentCompletes.size (); ++i)
195+ {
196+ if (PresentCompletes[i]->GetState () == Rendering::Primitives::FenceState::Submitted)
197+ {
198+ PresentCompletes[i]->Wait (UINT64_MAX);
199+ PresentCompletes[i]->Reset ();
200+ }
201+ }
202+
186203 for (int i = 0 ; i < FrameContextPoolSizeFactor; ++i)
187204 {
188205 FrameContext& frame = FrameContexts[i + FrameContextOffset];
189206 frame.Acquired ->SetState (Primitives::SemaphoreState::Idle);
190207 }
191208
192209 Device->AsyncResLoader ->ClearAsyncJobs ();
210+ Device->AsyncResLoader ->Reset ();
193211
194212 uint64_t timeline_value = 0 ;
195213 vkGetSemaphoreCounterValue (Device->LogicalDevice , RenderTimeline->GetHandle (), &timeline_value);
@@ -198,7 +216,9 @@ namespace ZEngine::Hardwares
198216 ZENGINE_VALIDATE_ASSERT (timeline_value < UINT64_MAX, " Render Timeline value is corrupted, this should never happen." )
199217 RenderTimelineNextValue = timeline_value;
200218
201- FrameContextOffset = (FrameContextOffset + FrameContextPoolSizeFactor) % FrameContextPoolSize;
219+ FrameContextOffset = (FrameContextOffset + FrameContextPoolSizeFactor) % FrameContextPoolSize;
220+ // CurrentFrame = nullptr;
221+
202222 Clear ();
203223 Create ();
204224
@@ -207,17 +227,22 @@ namespace ZEngine::Hardwares
207227 }
208228
209229 FrameContext& frame = FrameContexts[frame_context_idx + FrameContextOffset];
210-
230+ if (frame.Fence ->GetState () == Rendering::Primitives::FenceState::Submitted)
231+ {
232+ frame.Fence ->Wait (UINT64_MAX);
233+ }
211234 frame.Fence ->Reset ();
212235 frame.Acquired ->SetState (Rendering::Primitives::SemaphoreState::Idle);
213- Device->AsyncResLoader ->ResetCommandBuffers (frame.Index , 0 );
214-
215- ZENGINE_VALIDATE_ASSERT (frame.Acquired ->GetState () != Primitives::SemaphoreState::Submitted, " " )
216236
217237 uint32_t image_idx = 0 ;
218238 VkResult acquire_image_result = vkAcquireNextImageKHR (Device->LogicalDevice , SwapchainHandle, UINT64_MAX, frame.Acquired ->GetHandle (), VK_NULL_HANDLE, &(image_idx));
219239 frame.Acquired ->SetState (Primitives::SemaphoreState::Submitted);
220- RenderCompletes[image_idx]->SetState (Rendering::Primitives::SemaphoreState::Idle);
240+
241+ if (PresentCompletes[image_idx]->GetState () == Rendering::Primitives::FenceState::Submitted)
242+ {
243+ PresentCompletes[image_idx]->Wait (UINT64_MAX);
244+ PresentCompletes[image_idx]->Reset ();
245+ }
221246
222247 if (ImageInFlights[image_idx] != nullptr )
223248 {
@@ -226,6 +251,7 @@ namespace ZEngine::Hardwares
226251 ImageInFlights[image_idx]->Wait (UINT64_MAX);
227252 }
228253 }
254+ RenderCompletes[image_idx]->SetState (Rendering::Primitives::SemaphoreState::Idle);
229255
230256 ImageInFlights[image_idx] = frame.Fence ;
231257 frame.ImageIndex = image_idx;
@@ -243,7 +269,6 @@ namespace ZEngine::Hardwares
243269 if (HasRecreationPending)
244270 {
245271 IdleFrameCount.fetch_add (1 );
246- Device->CommandBufferMgr ->EndEnqueuedBuffers ();
247272 Device->CommandBufferMgr ->ResetEnqueuedBufferIndex ();
248273 return ;
249274 }
@@ -302,9 +327,6 @@ namespace ZEngine::Hardwares
302327 }
303328 }
304329
305- Device->CommandBufferMgr ->EndEnqueuedBuffers ();
306- Device->AsyncResLoader ->SubmitAsyncJobs ();
307-
308330 auto scratch = ZGetScratch (&Arena);
309331
310332 Array<VkCommandBuffer> buffer = {};
@@ -314,7 +336,8 @@ namespace ZEngine::Hardwares
314336 buffer[i] = Device->CommandBufferMgr ->EnqueuedCommandBuffers [i]->GetHandle ();
315337 }
316338
317- auto render_complete = RenderCompletes[CurrentFrame->ImageIndex ];
339+ auto render_complete = RenderCompletes[CurrentFrame->ImageIndex ];
340+ auto present_complete = PresentCompletes[CurrentFrame->ImageIndex ];
318341
319342 ZENGINE_VALIDATE_ASSERT (render_complete->GetState () != Rendering::Primitives::SemaphoreState::Submitted, " Signal semaphore is already in a signaled state." )
320343 ZENGINE_VALIDATE_ASSERT (CurrentFrame->Fence ->GetState () != Rendering::Primitives::FenceState::Submitted, " Signal fence is already in a signaled state." )
@@ -450,9 +473,12 @@ namespace ZEngine::Hardwares
450473 .pSignalSemaphores = present_signal_semaphores,
451474 };
452475
453- VkResult r2 = vkQueueSubmit (queue.Handle , 1 , &submit2, VK_NULL_HANDLE );
476+ VkResult r2 = vkQueueSubmit (queue.Handle , 1 , &submit2, present_complete-> GetHandle () );
454477 ZENGINE_VALIDATE_ASSERT (r2 == VK_SUCCESS, " Failed to submit present bridge" )
455478
479+ render_complete->SetState (Rendering::Primitives::SemaphoreState::Submitted);
480+ present_complete->SetState (Rendering::Primitives::FenceState::Submitted);
481+
456482 VkSwapchainKHR swapchains[] = {SwapchainHandle};
457483 uint32_t frames[] = {CurrentFrame->ImageIndex };
458484 VkSemaphore semaphores[] = {render_complete->GetHandle ()};
@@ -466,7 +492,6 @@ namespace ZEngine::Hardwares
466492 .pImageIndices = frames,
467493 };
468494 VkResult present_result = vkQueuePresentKHR (queue.Handle , &present_info);
469- render_complete->SetState (Rendering::Primitives::SemaphoreState::Submitted);
470495
471496 IdleFrameCount.fetch_add (1 );
472497
0 commit comments