diff --git a/UI/context-bar-controls.cpp b/UI/context-bar-controls.cpp index 9ef850b6d..1af2599ab 100644 --- a/UI/context-bar-controls.cpp +++ b/UI/context-bar-controls.cpp @@ -1,3 +1,4 @@ +#include "window-basic-main.hpp" #include "context-bar-controls.hpp" #include "qt-wrappers.hpp" #include "obs-app.hpp" @@ -33,6 +34,63 @@ SourceToolbar::SourceToolbar(QWidget *parent, OBSSource source) { } +void SourceToolbar::SaveOldProperties(obs_source_t *source) +{ + if (oldData) + obs_data_release(oldData); + + oldData = obs_data_create(); + obs_data_t *oldSettings = obs_source_get_settings(source); + obs_data_apply(oldData, oldSettings); + obs_data_set_string(oldData, "undo_sname", obs_source_get_name(source)); + obs_data_release(oldSettings); + obs_data_release(oldData); +} + +void SourceToolbar::SetUndoProperties(obs_source_t *source) +{ + OBSBasic *main = reinterpret_cast(App()->GetMainWindow()); + + std::string scene_name = + obs_source_get_name(main->GetCurrentSceneSource()); + auto undo_redo = [scene_name, + main = std::move(main)](const std::string &data) { + obs_data_t *settings = obs_data_create_from_json(data.c_str()); + obs_source_t *source = obs_get_source_by_name( + obs_data_get_string(settings, "undo_sname")); + obs_source_update(source, settings); + + obs_source_t *scene_source = + obs_get_source_by_name(scene_name.c_str()); + main->SetCurrentScene(scene_source); + obs_source_release(scene_source); + + obs_data_release(settings); + obs_source_release(source); + + main->UpdateContextBar(); + }; + + OBSData new_settings = obs_data_create(); + OBSData curr_settings = obs_source_get_settings(source); + obs_data_apply(new_settings, curr_settings); + obs_data_set_string(new_settings, "undo_sname", + obs_source_get_name(source)); + + std::string undo_data(obs_data_get_json(oldData)); + std::string redo_data(obs_data_get_json(new_settings)); + + if (undo_data.compare(redo_data) != 0) + main->undo_s.add_action( + QTStr("Undo.Properties") + .arg(obs_source_get_name(source)), + undo_redo, undo_redo, undo_data, redo_data, nullptr); + + obs_data_release(new_settings); + obs_data_release(curr_settings); + obs_data_release(oldData); +} + /* ========================================================================= */ BrowserToolbar::BrowserToolbar(QWidget *parent, OBSSource source) @@ -163,8 +221,10 @@ void ComboSelectToolbar::on_device_currentIndexChanged(int idx) return; } + SaveOldProperties(source); UpdateSourceComboToolbarValue(ui->device, source, idx, prop_name, is_int); + SetUndoProperties(source); } AudioCaptureToolbar::AudioCaptureToolbar(QWidget *parent, OBSSource source) @@ -370,10 +430,12 @@ void GameCaptureToolbar::on_mode_currentIndexChanged(int idx) QString id = ui->mode->itemData(idx).toString(); + SaveOldProperties(source); obs_data_t *settings = obs_data_create(); obs_data_set_string(settings, "capture_mode", QT_TO_UTF8(id)); obs_source_update(source, settings); obs_data_release(settings); + SetUndoProperties(source); UpdateWindowVisibility(); } @@ -387,10 +449,12 @@ void GameCaptureToolbar::on_window_currentIndexChanged(int idx) QString id = ui->window->itemData(idx).toString(); + SaveOldProperties(source); obs_data_t *settings = obs_data_create(); obs_data_set_string(settings, "window", QT_TO_UTF8(id)); obs_source_update(source, settings); obs_data_release(settings); + SetUndoProperties(source); } /* ========================================================================= */ @@ -434,10 +498,12 @@ void ImageSourceToolbar::on_browse_clicked() ui->path->setText(path); + SaveOldProperties(source); obs_data_t *settings = obs_data_create(); obs_data_set_string(settings, "file", QT_TO_UTF8(path)); obs_source_update(source, settings); obs_data_release(settings); + SetUndoProperties(source); } /* ========================================================================= */ @@ -518,10 +584,14 @@ void ColorSourceToolbar::on_choose_clicked() color = newColor; UpdateColor(); + SaveOldProperties(source); + obs_data_t *settings = obs_data_create(); obs_data_set_int(settings, "color", color_to_int(color)); obs_source_update(source, settings); obs_data_release(settings); + + SetUndoProperties(source); } /* ========================================================================= */ @@ -596,6 +666,8 @@ void TextSourceToolbar::on_selectFont_clicked() flags |= font.strikeOut() ? OBS_FONT_STRIKEOUT : 0; obs_data_set_int(font_obj, "flags", flags); + SaveOldProperties(source); + obs_data_t *settings = obs_data_create(); obs_data_set_obj(settings, "font", font_obj); @@ -603,6 +675,8 @@ void TextSourceToolbar::on_selectFont_clicked() obs_source_update(source, settings); obs_data_release(settings); + + SetUndoProperties(source); } void TextSourceToolbar::on_selectColor_clicked() @@ -628,6 +702,8 @@ void TextSourceToolbar::on_selectColor_clicked() color = newColor; + SaveOldProperties(source); + obs_data_t *settings = obs_data_create(); if (!strncmp(obs_source_get_id(source), "text_ft2_source", 15)) { obs_data_set_int(settings, "color1", color_to_int(color)); @@ -637,6 +713,8 @@ void TextSourceToolbar::on_selectColor_clicked() } obs_source_update(source, settings); obs_data_release(settings); + + SetUndoProperties(source); } void TextSourceToolbar::on_text_textChanged() diff --git a/UI/context-bar-controls.hpp b/UI/context-bar-controls.hpp index 5848121fa..9671dd2f0 100644 --- a/UI/context-bar-controls.hpp +++ b/UI/context-bar-controls.hpp @@ -22,6 +22,10 @@ protected: std::unique_ptr; properties_t props; + OBSData oldData; + + void SaveOldProperties(obs_source_t *source); + void SetUndoProperties(obs_source_t *source); public: SourceToolbar(QWidget *parent, OBSSource source);