From 4330065d7d9dcfcbc578fc2222045e8e90683df3 Mon Sep 17 00:00:00 2001 From: jp9000 Date: Thu, 2 Jul 2015 16:12:47 -0700 Subject: [PATCH] UI: Add ClearSceneData to clean up all obs data Add a central function for clearing all data: scenes, sources, widgets such as lists that may contain source references in their sub-items, dialogs which may contain source references. In certain circumstances this data must be fully released and manually freed to ensure that there are no outstanding references to obs data (such as on shutdown, where all data should be properly freed). --- obs/window-basic-main.cpp | 70 +++++++++++++++++++++++++-------------- obs/window-basic-main.hpp | 3 ++ 2 files changed, 48 insertions(+), 25 deletions(-) diff --git a/obs/window-basic-main.cpp b/obs/window-basic-main.cpp index ff5063d8c..ee4815991 100644 --- a/obs/window-basic-main.cpp +++ b/obs/window-basic-main.cpp @@ -1919,6 +1919,48 @@ void OBSBasic::ResizePreview(uint32_t cx, uint32_t cy) } } +void OBSBasic::CloseDialogs() +{ + QList childDialogs = this->findChildren(); + if (!childDialogs.isEmpty()) { + for (int i = 0; i < childDialogs.size(); ++i) { + childDialogs.at(i)->close(); + } + } + + for (QPointer &projector : projectors) { + delete projector; + projector.clear(); + } +} + +void OBSBasic::ClearSceneData() +{ + CloseDialogs(); + + ClearVolumeControls(); + ClearListItems(ui->scenes); + ClearListItems(ui->sources); + + obs_set_output_source(0, nullptr); + obs_set_output_source(1, nullptr); + obs_set_output_source(2, nullptr); + obs_set_output_source(3, nullptr); + obs_set_output_source(4, nullptr); + obs_set_output_source(5, nullptr); + + auto cb = [](void *unused, obs_source_t *source) + { + obs_source_remove(source); + UNUSED_PARAMETER(unused); + return true; + }; + + obs_enum_sources(cb, nullptr); + + sourceSceneRefs.clear(); +} + void OBSBasic::closeEvent(QCloseEvent *event) { if (outputHandler && outputHandler->Active()) { @@ -1943,21 +1985,6 @@ void OBSBasic::closeEvent(QCloseEvent *event) signalHandlers.clear(); - /* Check all child dialogs and ensure they run their proper closeEvent - * methods before exiting the application. Otherwise Qt doesn't send - * the proper QCloseEvent messages. */ - QList childDialogs = this->findChildren(); - if (!childDialogs.isEmpty()) { - for (int i = 0; i < childDialogs.size(); ++i) { - childDialogs.at(i)->close(); - } - } - - for (QPointer &projector : projectors) { - delete projector; - projector.clear(); - } - // remove draw callback in case our drawable surfaces go away before // the destructor gets called obs_remove_draw_callback(OBSBasic::RenderMain, this); @@ -1967,16 +1994,9 @@ void OBSBasic::closeEvent(QCloseEvent *event) delete saveTimer; SaveProject(); - /* Clear the list boxes in ::closeEvent to ensure that we can process - * any ->deleteLater events in this window created by Qt in relation to - * their internal data */ - ClearVolumeControls(); - - QListWidgetItem *item = nullptr; - while ((item = ui->scenes->takeItem(0))) - delete item; - - ClearListItems(ui->sources); + /* Clear all scene data (dialogs, widgets, widget sub-items, scenes, + * sources, etc) so that all references are released before shutdown */ + ClearSceneData(); } void OBSBasic::changeEvent(QEvent *event) diff --git a/obs/window-basic-main.hpp b/obs/window-basic-main.hpp index 685e3aa49..3f872f271 100644 --- a/obs/window-basic-main.hpp +++ b/obs/window-basic-main.hpp @@ -161,6 +161,9 @@ private: void CreatePropertiesWindow(obs_source_t *source); void CreateFiltersWindow(obs_source_t *source); + void CloseDialogs(); + void ClearSceneData(); + void Nudge(int dist, MoveDir dir); void OpenProjector(obs_source_t *source, int monitor);