Browse Source

UI: Fix multithread-unsafe GetCurrentScene

The function `OBSBasic::GetCurrentScene()` is also called from the
graphics thread and access to a QListWidget object, which is not
multithread-safe.
Norihiro Kamae 3 years ago
parent
commit
1c4bc6e735
3 changed files with 10 additions and 2 deletions
  1. 1 0
      UI/window-basic-main-transitions.cpp
  2. 7 2
      UI/window-basic-main.cpp
  3. 2 0
      UI/window-basic-main.hpp

+ 1 - 0
UI/window-basic-main-transitions.cpp

@@ -735,6 +735,7 @@ void OBSBasic::SetCurrentScene(OBSSource scene, bool force)
 
 			if (source == scene) {
 				ui->scenes->blockSignals(true);
+				currentScene = itemScene.Get();
 				ui->scenes->setCurrentItem(item);
 				ui->scenes->blockSignals(false);
 				if (api)

+ 7 - 2
UI/window-basic-main.cpp

@@ -2769,8 +2769,7 @@ OBSSource OBSBasic::GetProgramSource()
 
 OBSScene OBSBasic::GetCurrentScene()
 {
-	QListWidgetItem *item = ui->scenes->currentItem();
-	return item ? GetOBSRef<OBSScene>(item) : nullptr;
+	return currentScene.load();
 }
 
 OBSSceneItem OBSBasic::GetSceneItem(QListWidgetItem *item)
@@ -3960,6 +3959,7 @@ void OBSBasic::RemoveSelectedScene()
 		QListWidgetItem *item = ui->scenes->takeItem(curIndex);
 		ui->scenes->insertItem(savedIndex, item);
 		ui->scenes->setCurrentRow(savedIndex);
+		currentScene = scene.Get();
 		ui->scenes->blockSignals(false);
 	};
 
@@ -4964,6 +4964,10 @@ void OBSBasic::on_scenes_currentItemChanged(QListWidgetItem *current,
 
 		scene = GetOBSRef<OBSScene>(current);
 		source = obs_scene_get_source(scene);
+
+		currentScene = scene;
+	} else {
+		currentScene = NULL;
 	}
 
 	SetCurrentScene(source);
@@ -5227,6 +5231,7 @@ void OBSBasic::ChangeSceneIndex(bool relative, int offset, int invalidIdx)
 	ui->scenes->insertItem(idx + offset, item);
 	ui->scenes->setCurrentRow(idx + offset);
 	item->setSelected(true);
+	currentScene = GetOBSRef<OBSScene>(item).Get();
 	ui->scenes->blockSignals(false);
 
 	OBSProjector::UpdateMultiviewProjectors();

+ 2 - 0
UI/window-basic-main.hpp

@@ -332,6 +332,8 @@ private:
 	QScopedPointer<QThread> patronJsonThread;
 	std::string patronJson;
 
+	std::atomic<obs_scene_t *> currentScene = nullptr;
+
 	void UpdateMultiviewProjectorMenu();
 
 	void DrawBackdrop(float cx, float cy);