From 9f494b90e5d8b32a49ec033adc4cd7f5b754f2f6 Mon Sep 17 00:00:00 2001 From: Frederick Roy Date: Tue, 7 Jan 2025 08:47:39 +0100 Subject: [PATCH] [ImGui, GLFW] Fix crash when quitting (#142) * glfw:fix crash when quitting (with escape key) * imgui: avoid brutal exit when selecting exit in menu --- SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.cpp | 38 +++++++++++----------- SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.h | 1 + SofaGLFW/src/SofaGLFW/SofaGLFWWindow.cpp | 7 ++-- SofaImGui/src/SofaImGui/ImGuiGUIEngine.cpp | 6 ++-- 4 files changed, 27 insertions(+), 25 deletions(-) diff --git a/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.cpp b/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.cpp index b144b49a11..ec406dd61e 100644 --- a/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.cpp +++ b/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.cpp @@ -26,28 +26,27 @@ #include -#include -#include -#include -#include -#include #include -#include -#include - +#include +#include #include - -#include #include -#include - +#include +#include #include #include +#include +#include +#include +#include +#include #include #include #include -#include + +#include + using namespace sofa; using namespace sofa::gui::common; @@ -275,6 +274,7 @@ bool SofaGLFWBaseGUI::createWindow(int width, int height, const char* title, boo { glfwWindow = glfwCreateWindow(width > 0 ? width : 100, height > 0 ? height : 100, title, nullptr, m_firstWindow); } + s_numberOfActiveWindows++; setWindowIcon(glfwWindow); @@ -458,22 +458,22 @@ std::size_t SofaGLFWBaseGUI::runLoop(std::size_t targetNbIterations) bool running = true; std::size_t currentNbIterations = 0; std::stringstream tmpStr; - while (!s_mapWindows.empty() && running) + while (s_numberOfActiveWindows > 0 && running) { SIMULATION_LOOP_SCOPE // Keep running runStep(); - + for (auto& [glfwWindow, sofaGlfwWindow] : s_mapWindows) { - if (sofaGlfwWindow) + if (glfwWindow && sofaGlfwWindow) { // while user did not request to close this window (i.e press escape), draw if (!glfwWindowShouldClose(glfwWindow)) { makeCurrentContext(glfwWindow); - + m_guiEngine->beforeDraw(glfwWindow); sofaGlfwWindow->draw(m_groot, m_vparams); m_guiEngine->afterDraw(); @@ -486,7 +486,6 @@ std::size_t SofaGLFWBaseGUI::runLoop(std::size_t targetNbIterations) m_viewPortHeight = m_vparams->viewport()[3]; m_viewPortWidth = m_vparams->viewport()[2]; - } else { @@ -861,8 +860,9 @@ void SofaGLFWBaseGUI::close_callback(GLFWwindow* window) { glfwWindow->close(); delete glfwWindow; + glfwWindow = nullptr; + s_numberOfActiveWindows--; } - s_mapWindows.erase(window); } } diff --git a/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.h b/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.h index 8d03b65a39..aca128312f 100644 --- a/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.h +++ b/SofaGLFW/src/SofaGLFW/SofaGLFWBaseGUI.h @@ -127,6 +127,7 @@ class SOFAGLFW_API SofaGLFWBaseGUI : public BaseViewer inline static std::map s_mapWindows{}; inline static std::map s_mapGUIs{}; + inline static std::size_t s_numberOfActiveWindows = 0; bool m_bGlfwIsInitialized{ false }; bool m_bGlewIsInitialized{ false }; diff --git a/SofaGLFW/src/SofaGLFW/SofaGLFWWindow.cpp b/SofaGLFW/src/SofaGLFW/SofaGLFWWindow.cpp index f8e9459f61..9b505feeb9 100644 --- a/SofaGLFW/src/SofaGLFW/SofaGLFWWindow.cpp +++ b/SofaGLFW/src/SofaGLFW/SofaGLFWWindow.cpp @@ -50,7 +50,8 @@ void SofaGLFWWindow::close() } -void SofaGLFWWindow::draw(simulation::NodeSPtr groot, core::visual::VisualParams* vparams){ +void SofaGLFWWindow::draw(simulation::NodeSPtr groot, core::visual::VisualParams* vparams) +{ glClearColor(m_backgroundColor.r(), m_backgroundColor.g(), m_backgroundColor.b(), m_backgroundColor.a()); glClearDepth(1.0); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); @@ -65,9 +66,9 @@ void SofaGLFWWindow::draw(simulation::NodeSPtr groot, core::visual::VisualParams msg_error("SofaGLFWGUI") << "No camera defined."; return; } - + if (groot->f_bbox.getValue().isValid()) - { + { vparams->sceneBBox() = groot->f_bbox.getValue(); m_currentCamera->setBoundingBox(vparams->sceneBBox().minBBox(), vparams->sceneBBox().maxBBox()); } diff --git a/SofaImGui/src/SofaImGui/ImGuiGUIEngine.cpp b/SofaImGui/src/SofaImGui/ImGuiGUIEngine.cpp index a42dc1796d..33c1372e33 100644 --- a/SofaImGui/src/SofaImGui/ImGuiGUIEngine.cpp +++ b/SofaImGui/src/SofaImGui/ImGuiGUIEngine.cpp @@ -188,7 +188,7 @@ void ImGuiGUIEngine::loadFile(sofaglfw::SofaGLFWBaseGUI* baseGUI, sofa::core::sp if( !groot ) groot = sofa::simulation::getSimulation()->createNewGraph(""); baseGUI->setSimulation(groot, filePathName); - + sofa::simulation::node::initRoot(groot.get()); auto camera = baseGUI->findCamera(groot); if (camera) @@ -361,8 +361,8 @@ void ImGuiGUIEngine::startFrame(sofaglfw::SofaGLFWBaseGUI* baseGUI) ImGui::Separator(); if (ImGui::MenuItem("Exit")) { - //TODO: brutal exit, need to clean up everything (simulation, window, opengl, imgui etc) - exit(EXIT_SUCCESS); + this->terminate(); + return; } ImGui::EndMenu(); }