From 84f651f85d3deca795443d1d3908c1ec71d2db7a Mon Sep 17 00:00:00 2001 From: YuSanka Date: Fri, 16 Sep 2022 17:25:00 +0200 Subject: [PATCH] DiffDialog: Save preset * Fixed a crash after save the preset with existing name * Added update of the PresetComboBoxes on SettingsTabs and Sidebar * Some code refactoring --- src/libslic3r/Preset.cpp | 19 +++++++-- src/libslic3r/PresetBundle.cpp | 9 ++--- src/slic3r/GUI/MainFrame.cpp | 9 ++++- src/slic3r/GUI/SavePresetDialog.cpp | 5 ++- src/slic3r/GUI/SavePresetDialog.hpp | 10 ++--- src/slic3r/GUI/Tab.cpp | 14 +------ src/slic3r/GUI/Tab.hpp | 1 - src/slic3r/GUI/UnsavedChangesDialog.cpp | 51 ++++++++++++++++++------- src/slic3r/GUI/UnsavedChangesDialog.hpp | 12 +++--- 9 files changed, 81 insertions(+), 49 deletions(-) diff --git a/src/libslic3r/Preset.cpp b/src/libslic3r/Preset.cpp index 5d152ea17c..aba428f8b0 100644 --- a/src/libslic3r/Preset.cpp +++ b/src/libslic3r/Preset.cpp @@ -932,8 +932,8 @@ Preset& PresetCollection::get_preset_with_name(const std::string& new_name, cons if (it != m_presets.end() && it->name == new_name) { // Preset with the same name found. Preset& preset = *it; - if (!preset.is_default && !preset.is_external && !preset.is_system) { - // Overwriting an existing preset if it isn't default/external/system + if (!preset.is_default && !preset.is_external && !preset.is_system && initial_preset->name != new_name) { + // Overwriting an existing preset if it isn't default/external/system or isn't an initial_preset preset.config = initial_preset->config; // The newly saved preset can be activated -> make it visible. preset.is_visible = true; @@ -941,10 +941,12 @@ Preset& PresetCollection::get_preset_with_name(const std::string& new_name, cons return preset; } + const std::string selected_preset_name = this->get_selected_preset_name(); + // Creating a new preset. Preset& preset = *m_presets.insert(it, *initial_preset); std::string& inherits = preset.inherits(); - std::string old_name = preset.name; + std::string old_name = preset.name; preset.name = new_name; preset.file = this->path_from_name(new_name); preset.vendor = nullptr; @@ -970,7 +972,16 @@ Preset& PresetCollection::get_preset_with_name(const std::string& new_name, cons // Just system presets have aliases preset.alias.clear(); - return preset; + // sort printers and get new it + std::sort(m_presets.begin(), m_presets.end()); + + // set initial preset selection + this->select_preset_by_name(selected_preset_name, true); + + it = this->find_preset_internal(new_name); + assert(it != m_presets.end()); + + return *it; } bool PresetCollection::delete_current_preset() diff --git a/src/libslic3r/PresetBundle.cpp b/src/libslic3r/PresetBundle.cpp index 176b098761..b783c8aebc 100644 --- a/src/libslic3r/PresetBundle.cpp +++ b/src/libslic3r/PresetBundle.cpp @@ -481,9 +481,8 @@ bool PresetBundle::transfer_and_save(Preset::Type type, const std::string& prese PresetCollection& presets = get_presets(type); - const Preset* preset_from = presets.find_preset(preset_from_name, false, false); const Preset* preset_to = presets.find_preset(preset_to_name, false, false); - if (!preset_from || !preset_to) + if (!preset_to) return false; // Find the preset with a new_name or create a new one, @@ -494,14 +493,14 @@ bool PresetBundle::transfer_and_save(Preset::Type type, const std::string& prese return false; // Apply options from the preset_from_name. + const Preset* preset_from = presets.find_preset(preset_from_name, false, false); + if (!preset_from) + return false; preset.config.apply_only(preset_from->config, options); // Store new_name preset to disk. preset.save(); - // update selection - presets.select_preset_by_name(preset_new_name, true); - // Mark the print & filament enabled if they are compatible with the currently selected preset. // If saving the preset changes compatibility with other presets, keep the now incompatible dependent presets selected, however with a "red flag" icon showing that they are no more compatible. update_compatible(PresetSelectCompatibleType::Never); diff --git a/src/slic3r/GUI/MainFrame.cpp b/src/slic3r/GUI/MainFrame.cpp index 0c83551769..df531c5629 100644 --- a/src/slic3r/GUI/MainFrame.cpp +++ b/src/slic3r/GUI/MainFrame.cpp @@ -299,6 +299,11 @@ void MainFrame::bind_diff_dialog() diff_dialog.get_selected_options(type)); }; + auto update_presets = [this, get_tab](Preset::Type type) { + get_tab(type)->update_preset_choice(); + m_plater->sidebar().update_presets(type); + }; + auto process_options = [this](std::function process) { const Preset::Type diff_dlg_type = diff_dialog.view_type(); if (diff_dlg_type == Preset::TYPE_INVALID) { @@ -311,7 +316,9 @@ void MainFrame::bind_diff_dialog() process(diff_dlg_type); }; - diff_dialog.Bind(EVT_DIFF_DIALOG_TRANSFER, [this, process_options, transfer](SimpleEvent&) { process_options(transfer); }); + diff_dialog.Bind(EVT_DIFF_DIALOG_TRANSFER, [this, process_options, transfer](SimpleEvent&) { process_options(transfer); }); + + diff_dialog.Bind(EVT_DIFF_DIALOG_UPDATE_PRESETS,[this, process_options, update_presets](SimpleEvent&) { process_options(update_presets); }); } diff --git a/src/slic3r/GUI/SavePresetDialog.cpp b/src/slic3r/GUI/SavePresetDialog.cpp index 89a5d7a8de..57aa5da983 100644 --- a/src/slic3r/GUI/SavePresetDialog.cpp +++ b/src/slic3r/GUI/SavePresetDialog.cpp @@ -163,8 +163,9 @@ void SavePresetDialog::Item::update() if (m_valid_type == ValidationType::Valid && existing) { if (m_preset_name == m_presets->get_selected_preset_name()) { - if (!rename && m_presets->get_edited_preset().is_dirty) - info_line = _L("Just save preset modifications"); + if (!rename && m_presets->get_edited_preset().is_dirty || + m_parent->get_preset_bundle()) // means that we save modifications from the DiffDialog + info_line = _L("Save preset modifications to existing user profile"); else info_line = _L("Nothing changed"); m_valid_type = ValidationType::Valid; diff --git a/src/slic3r/GUI/SavePresetDialog.hpp b/src/slic3r/GUI/SavePresetDialog.hpp index aec58ac7a3..c40a5896f2 100644 --- a/src/slic3r/GUI/SavePresetDialog.hpp +++ b/src/slic3r/GUI/SavePresetDialog.hpp @@ -86,15 +86,13 @@ public: SavePresetDialog(wxWindow* parent, Preset::Type type, std::string suffix = ""); SavePresetDialog(wxWindow* parent, std::vector types, std::string suffix = "", PresetBundle* preset_bundle = nullptr); SavePresetDialog(wxWindow* parent, Preset::Type type, bool rename, const wxString& info_line_extention); - ~SavePresetDialog(); + ~SavePresetDialog() override; void AddItem(Preset::Type type, const std::string& suffix); - void set_preset_bundle(PresetBundle* preset_bundle) { m_preset_bundle = preset_bundle; } - PresetBundle* get_preset_bundle() const { return m_preset_bundle; } - - std::string get_name(); - std::string get_name(Preset::Type type); + PresetBundle* get_preset_bundle() const { return m_preset_bundle; } + std::string get_name(); + std::string get_name(Preset::Type type); bool enable_ok_btn() const; void add_info_for_edit_ph_printer(wxBoxSizer *sizer); diff --git a/src/slic3r/GUI/Tab.cpp b/src/slic3r/GUI/Tab.cpp index ed73e5552d..d27bfc9315 100644 --- a/src/slic3r/GUI/Tab.cpp +++ b/src/slic3r/GUI/Tab.cpp @@ -47,14 +47,14 @@ #include "Notebook.hpp" #ifdef WIN32 - #include + #include #endif // WIN32 namespace Slic3r { namespace GUI { Tab::Tab(wxBookCtrlBase* parent, const wxString& title, Preset::Type type) : - m_parent(parent), m_title(title), m_type(type) + m_parent(parent), m_type(type), m_title(title) { Create(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxBK_LEFT | wxTAB_TRAVERSAL/*, name*/); this->SetFont(Slic3r::GUI::wxGetApp().normal_font()); @@ -3611,16 +3611,6 @@ void Tab::transfer_options(const std::string &name_from, const std::string &name load_current_preset(); } -void Tab::save_options(const std::string &name_from, const std::string &name_to, std::vector options) -{ - if (options.empty()) - return; - - Preset* preset_from = m_presets->find_preset(name_from); - Preset* preset_to = m_presets->find_preset(name_to); - -} - // Save the current preset into file. // This removes the "dirty" flag of the preset, possibly creates a new preset under a new name, // and activates the new preset. diff --git a/src/slic3r/GUI/Tab.hpp b/src/slic3r/GUI/Tab.hpp index 9c4b101407..448e4be050 100644 --- a/src/slic3r/GUI/Tab.hpp +++ b/src/slic3r/GUI/Tab.hpp @@ -323,7 +323,6 @@ public: void compare_preset(); void transfer_options(const std::string&name_from, const std::string&name_to, std::vector options); - void save_options(const std::string &name_from, const std::string &name_to, std::vector options); void save_preset(std::string name = std::string(), bool detach = false); void rename_preset(); void delete_preset(); diff --git a/src/slic3r/GUI/UnsavedChangesDialog.cpp b/src/slic3r/GUI/UnsavedChangesDialog.cpp index 7fdec251ce..c04a536efb 100644 --- a/src/slic3r/GUI/UnsavedChangesDialog.cpp +++ b/src/slic3r/GUI/UnsavedChangesDialog.cpp @@ -35,7 +35,8 @@ namespace Slic3r { namespace GUI { -wxDEFINE_EVENT(EVT_DIFF_DIALOG_TRANSFER, SimpleEvent); +wxDEFINE_EVENT(EVT_DIFF_DIALOG_TRANSFER, SimpleEvent); +wxDEFINE_EVENT(EVT_DIFF_DIALOG_UPDATE_PRESETS, SimpleEvent); // ---------------------------------------------------------------------------- @@ -1384,7 +1385,7 @@ FullCompareDialog::FullCompareDialog(const wxString& option_name, const wxString wxFlexGridSizer* grid_sizer = new wxFlexGridSizer(2, has_new_value_column ? 3 : 2, 1, 0); grid_sizer->SetFlexibleDirection(wxBOTH); - for (size_t col = 0 ; col < grid_sizer->GetCols(); col++) + for (int col = 0 ; col < grid_sizer->GetCols(); col++) grid_sizer->AddGrowableCol(col, 1); grid_sizer->AddGrowableRow(1,1); @@ -1750,9 +1751,10 @@ void DiffPresetDialog::show(Preset::Type type /* = Preset::TYPE_INVALID*/) Show(); } -void DiffPresetDialog::update_presets(Preset::Type type) +void DiffPresetDialog::update_presets(Preset::Type type, bool update_preset_bundles_from_app/* = true */) { - update_bundles_from_app(); + if (update_preset_bundles_from_app) + update_bundles_from_app(); update_controls_visibility(type); if (type == Preset::TYPE_INVALID) @@ -2010,7 +2012,7 @@ void DiffPresetDialog::update_compatibility(const std::string& preset_name, Pres bool DiffPresetDialog::save() { - presets_to_saves.clear(); + presets_to_save.clear(); std::vector types_for_save; @@ -2018,7 +2020,7 @@ bool DiffPresetDialog::save() std::initializer_list{Preset::TYPE_PRINTER, Preset::TYPE_SLA_PRINT, Preset::TYPE_SLA_MATERIAL }) if (!m_tree->options(type, true).empty()) { types_for_save.emplace_back(type); - presets_to_saves.emplace_back(PresetToSave{ type, get_left_preset_name(type), get_right_preset_name(type), get_right_preset_name(type) }); + presets_to_save.emplace_back(PresetToSave{ type, get_left_preset_name(type), get_right_preset_name(type), get_right_preset_name(type) }); } if (!types_for_save.empty()) { @@ -2026,7 +2028,7 @@ bool DiffPresetDialog::save() if (save_dlg.ShowModal() != wxID_OK) return false; - for (auto& preset : presets_to_saves) { + for (auto& preset : presets_to_save) { const std::string& name = save_dlg.get_name(preset.type); if (!name.empty()) preset.new_name = name; @@ -2035,25 +2037,48 @@ bool DiffPresetDialog::save() return true; } +std::vector DiffPresetDialog::get_options_to_save(Preset::Type type) +{ + auto options = m_tree->options(type, true); + + // erase "inherits" option from the list if it exists there + if (const auto it = std::find(options.begin(), options.end(), "inherits"); it != options.end()) + options.erase(it); + + if (type == Preset::TYPE_PRINTER) { + // erase "extruders_count" option from the list if it exists there + if (const auto it = std::find(options.begin(), options.end(), "extruders_count"); it != options.end()) + options.erase(it); + } + return options; +} + void DiffPresetDialog::button_event(Action act) { if (act == Action::Save) { if (save()) { size_t saved_cnt = 0; - for (const auto& preset : presets_to_saves) - if (wxGetApp().preset_bundle->transfer_and_save(preset.type, preset.from_name, preset.to_name, preset.new_name, m_tree->options(preset.type, true))) + for (const auto& preset : presets_to_save) + if (wxGetApp().preset_bundle->transfer_and_save(preset.type, preset.from_name, preset.to_name, preset.new_name, get_options_to_save(preset.type))) saved_cnt++; - if (saved_cnt > 0) - MessageDialog(nullptr, UnsavedChangesDialog::msg_success_saved_modifications(saved_cnt)).ShowModal(); - - update_presets(); + if (saved_cnt > 0) { + MessageDialog(this, UnsavedChangesDialog::msg_success_saved_modifications(saved_cnt)).ShowModal(); + update_bundles_from_app(); + for (const auto& preset : presets_to_save) { + m_preset_bundle_left->get_presets(preset.type).select_preset_by_name(preset.from_name, true); + m_preset_bundle_right->get_presets(preset.type).select_preset_by_name(preset.new_name, true); + } + update_presets(m_view_type, false); + } } } else { Hide(); if (act == Action::Transfer) wxPostEvent(this, SimpleEvent(EVT_DIFF_DIALOG_TRANSFER)); + else if (!presets_to_save.empty()) + wxPostEvent(this, SimpleEvent(EVT_DIFF_DIALOG_UPDATE_PRESETS)); } } diff --git a/src/slic3r/GUI/UnsavedChangesDialog.hpp b/src/slic3r/GUI/UnsavedChangesDialog.hpp index a303593ca8..1592914fce 100644 --- a/src/slic3r/GUI/UnsavedChangesDialog.hpp +++ b/src/slic3r/GUI/UnsavedChangesDialog.hpp @@ -15,7 +15,8 @@ class wxStaticText; namespace Slic3r { namespace GUI{ -wxDECLARE_EVENT(EVT_DIFF_DIALOG_TRANSFER, SimpleEvent); +wxDECLARE_EVENT(EVT_DIFF_DIALOG_TRANSFER, SimpleEvent); +wxDECLARE_EVENT(EVT_DIFF_DIALOG_UPDATE_PRESETS, SimpleEvent); // ---------------------------------------------------------------------------- // ModelNode: a node inside DiffModel @@ -376,8 +377,9 @@ class DiffPresetDialog : public DPIDialog void update_controls_visibility(Preset::Type type = Preset::TYPE_INVALID); void update_compatibility(const std::string& preset_name, Preset::Type type, PresetBundle* preset_bundle); - void button_event(Action act); - bool save(); + std::vector get_options_to_save(Preset::Type type); + void button_event(Action act); + bool save(); struct DiffPresets { @@ -397,14 +399,14 @@ class DiffPresetDialog : public DPIDialog std::string new_name; }; - std::vector presets_to_saves; + std::vector presets_to_save; public: DiffPresetDialog(MainFrame*mainframe); ~DiffPresetDialog() override = default; void show(Preset::Type type = Preset::TYPE_INVALID); - void update_presets(Preset::Type type = Preset::TYPE_INVALID); + void update_presets(Preset::Type type = Preset::TYPE_INVALID, bool update_preset_bundles_from_app = true); Preset::Type view_type() const { return m_view_type; } PrinterTechnology printer_technology() const { return m_pr_technology; }