diff --git a/gui/libui/include/ui/App.h b/gui/libui/include/ui/App.h index 8a0d45e0..ce1e2496 100644 --- a/gui/libui/include/ui/App.h +++ b/gui/libui/include/ui/App.h @@ -61,6 +61,7 @@ namespace ui HashMap> m_windows; bool m_should_close { false }; os::EventLoop m_loop; + Vector m_window_clear_queue; bool process_events(); diff --git a/gui/libui/include/ui/Window.h b/gui/libui/include/ui/Window.h index 83d4f00f..ef6d4025 100644 --- a/gui/libui/include/ui/Window.h +++ b/gui/libui/include/ui/Window.h @@ -80,6 +80,12 @@ namespace ui return m_id; } + void on_close(os::Action&& action) + { + m_on_close_action = move(action); + m_has_on_close_action = true; + } + ~Window(); private: @@ -93,6 +99,9 @@ namespace ui Option m_old_mouse_buttons; bool m_decorated { false }; + os::Action m_on_close_action; + bool m_has_on_close_action { false }; + struct ShortcutAction { bool intercept; diff --git a/gui/libui/src/App.cpp b/gui/libui/src/App.cpp index ee2717c6..d53b17b7 100644 --- a/gui/libui/src/App.cpp +++ b/gui/libui/src/App.cpp @@ -75,7 +75,7 @@ namespace ui void App::unregister_window(Window* window, Badge) { int id = window->id(); - check(m_windows.try_remove(id)); + m_window_clear_queue.try_append(id); } Window* App::find_window(int id) @@ -124,6 +124,15 @@ namespace ui { check(m_main_window); m_client->check_for_messages().release_value(); + for (int id : m_window_clear_queue) + { + check(m_windows.try_remove(id)); + + ui::CloseWindowRequest request; + request.window = id; + client().send_async(request); + } + m_window_clear_queue.clear_data(); return !m_should_close; } } diff --git a/gui/libui/src/Window.cpp b/gui/libui/src/Window.cpp index 44f240dd..3aa699c6 100644 --- a/gui/libui/src/Window.cpp +++ b/gui/libui/src/Window.cpp @@ -84,6 +84,8 @@ namespace ui Window::~Window() { if (m_canvas.ptr) munmap(m_canvas.ptr, ((usize)m_canvas.width) * ((usize)m_canvas.height) * 4); + + if (m_has_on_close_action) m_on_close_action(); } void Window::set_title(StringView title) @@ -108,10 +110,6 @@ namespace ui { App& app = App::the(); - ui::CloseWindowRequest request; - request.window = m_id; - app.client().send_async(request); - if (this == app.main_window()) app.set_should_close(true); app.unregister_window(this, {});