1
Fork 0
mirror of https://github.com/redstrate/Novus.git synced 2025-04-20 11:47:45 +00:00

Fix a crash in VulkanWindow when trying to close one

This commit is contained in:
Joshua Goins 2023-12-10 07:13:42 -05:00
parent 546ebfd0bd
commit 09e1d25d09
3 changed files with 32 additions and 10 deletions

View file

@ -20,16 +20,19 @@ VulkanWindow::VulkanWindow(MDLPart *part, Renderer *renderer, QVulkanInstance *i
void VulkanWindow::exposeEvent(QExposeEvent *) void VulkanWindow::exposeEvent(QExposeEvent *)
{ {
if (isExposed()) { if (isExposed() && !m_initialized) {
if (!m_initialized) { m_initialized = true;
m_initialized = true;
auto surface = m_instance->surfaceForWindow(this); auto surface = m_instance->surfaceForWindow(this);
if (!m_renderer->initSwapchain(surface, width() * screen()->devicePixelRatio(), height() * screen()->devicePixelRatio())) if (!m_renderer->initSwapchain(surface, width() * screen()->devicePixelRatio(), height() * screen()->devicePixelRatio()))
m_initialized = false; m_initialized = false;
else else
render(); render();
} }
if (!isExposed() && m_initialized) {
m_initialized = false;
m_renderer->destroySwapchain();
} }
} }
@ -42,8 +45,17 @@ bool VulkanWindow::event(QEvent *e)
case QEvent::Resize: { case QEvent::Resize: {
QResizeEvent *resizeEvent = (QResizeEvent *)e; QResizeEvent *resizeEvent = (QResizeEvent *)e;
auto surface = m_instance->surfaceForWindow(this); auto surface = m_instance->surfaceForWindow(this);
m_renderer->resize(surface, resizeEvent->size().width() * screen()->devicePixelRatio(), resizeEvent->size().height() * screen()->devicePixelRatio()); if (surface != nullptr) {
m_renderer->resize(surface,
resizeEvent->size().width() * screen()->devicePixelRatio(),
resizeEvent->size().height() * screen()->devicePixelRatio());
}
} break; } break;
case QEvent::PlatformSurface:
if (static_cast<QPlatformSurfaceEvent *>(e)->surfaceEventType() == QPlatformSurfaceEvent::SurfaceAboutToBeDestroyed && m_initialized) {
m_renderer->destroySwapchain();
}
break;
case QEvent::MouseButtonPress: { case QEvent::MouseButtonPress: {
auto mouseEvent = dynamic_cast<QMouseEvent *>(e); auto mouseEvent = dynamic_cast<QMouseEvent *>(e);

View file

@ -68,6 +68,8 @@ public:
bool initSwapchain(VkSurfaceKHR surface, int width, int height); bool initSwapchain(VkSurfaceKHR surface, int width, int height);
void resize(VkSurfaceKHR surface, int width, int height); void resize(VkSurfaceKHR surface, int width, int height);
void destroySwapchain();
RenderModel addModel(const physis_MDL &model, int lod); RenderModel addModel(const physis_MDL &model, int lod);
void reloadModel(RenderModel &model, uint32_t lod); void reloadModel(RenderModel &model, uint32_t lod);
RenderTexture addTexture(uint32_t width, uint32_t height, const uint8_t *data, uint32_t data_size); RenderTexture addTexture(uint32_t width, uint32_t height, const uint8_t *data, uint32_t data_size);

View file

@ -426,6 +426,14 @@ void Renderer::resize(VkSurfaceKHR surface, int width, int height)
initSwapchain(surface, width, height); initSwapchain(surface, width, height);
} }
void Renderer::destroySwapchain()
{
if (swapchain != VK_NULL_HANDLE) {
vkDestroySwapchainKHR(device, swapchain, nullptr);
swapchain = VK_NULL_HANDLE;
}
}
void Renderer::render(std::vector<RenderModel> models) void Renderer::render(std::vector<RenderModel> models)
{ {
vkWaitForFences(device, 1, &inFlightFences[currentFrame], VK_TRUE, std::numeric_limits<uint64_t>::max()); vkWaitForFences(device, 1, &inFlightFences[currentFrame], VK_TRUE, std::numeric_limits<uint64_t>::max());