From 6b70f604607caa7ef986720b795558faaba0badb Mon Sep 17 00:00:00 2001 From: bubnikv Date: Thu, 10 Jan 2019 18:08:38 +0100 Subject: [PATCH] Fix of SPE-753 Slicer crash when SLA printer is selected and printer profile is changed First, there was a bug in the preset Tabs, where a "printer_technology" was incorrectly queried on "print" and "filament" (or "sla_print" and "sla_material") profiles. Second, there was an unsafe "printer_technology" getter, which would add the missing key to the config container when queried for. --- src/slic3r/GUI/Preset.hpp | 14 +++++++++++--- src/slic3r/GUI/PresetBundle.cpp | 2 +- src/slic3r/GUI/Tab.cpp | 14 ++++++++------ 3 files changed, 20 insertions(+), 10 deletions(-) diff --git a/src/slic3r/GUI/Preset.hpp b/src/slic3r/GUI/Preset.hpp index 24112cf10..021fea22c 100644 --- a/src/slic3r/GUI/Preset.hpp +++ b/src/slic3r/GUI/Preset.hpp @@ -161,9 +161,17 @@ public: } const std::string& compatible_printers_condition() const { return const_cast(this)->compatible_printers_condition(); } - static PrinterTechnology& printer_technology(DynamicPrintConfig &cfg) { return cfg.option>("printer_technology", true)->value; } - PrinterTechnology& printer_technology() { return Preset::printer_technology(this->config); } - const PrinterTechnology& printer_technology() const { return Preset::printer_technology(const_cast(this)->config); } + // Return a printer technology, return ptFFF if the printer technology is not set. + static PrinterTechnology printer_technology(const DynamicPrintConfig &cfg) { + auto *opt = cfg.option>("printer_technology"); + // The following assert may trigger when importing some legacy profile, + // but it is safer to keep it here to capture the cases where the "printer_technology" key is queried, where it should not. + assert(opt != nullptr); + return (opt == nullptr) ? ptFFF : opt->value; + } + PrinterTechnology printer_technology() const { return Preset::printer_technology(this->config); } + // This call returns a reference, it may add a new entry into the DynamicPrintConfig. + PrinterTechnology& printer_technology_ref() { return this->config.option>("printer_technology", true)->value; } // Mark this preset as compatible if it is compatible with active_printer. bool update_compatible(const Preset &active_printer, const DynamicPrintConfig *extra_config, const Preset *active_print = nullptr); diff --git a/src/slic3r/GUI/PresetBundle.cpp b/src/slic3r/GUI/PresetBundle.cpp index 0021ce307..4c6c52763 100644 --- a/src/slic3r/GUI/PresetBundle.cpp +++ b/src/slic3r/GUI/PresetBundle.cpp @@ -81,7 +81,7 @@ PresetBundle::PresetBundle() : this->sla_prints.default_preset().inherits(); this->printers.add_default_preset(Preset::sla_printer_options(), static_cast(SLAFullPrintConfig::defaults()), "- default SLA -"); - this->printers.preset(1).printer_technology() = ptSLA; + this->printers.preset(1).printer_technology_ref() = ptSLA; for (size_t i = 0; i < 2; ++ i) { // The following ugly switch is to avoid printers.preset(0) to return the edited instance, as the 0th default is the current one. Preset &preset = this->printers.default_preset(i); diff --git a/src/slic3r/GUI/Tab.cpp b/src/slic3r/GUI/Tab.cpp index 53ead470e..4daaf5d63 100644 --- a/src/slic3r/GUI/Tab.cpp +++ b/src/slic3r/GUI/Tab.cpp @@ -2296,11 +2296,13 @@ void Tab::load_current_preset() (preset.is_default || preset.is_system) ? m_btn_delete_preset->Disable() : m_btn_delete_preset->Enable(true); update(); - // For the printer profile, generate the extruder pages. - if (preset.printer_technology() == ptFFF) - on_preset_loaded(); - else - wxGetApp().sidebar().update_objects_list_extruder_column(1); + if (m_name == "printer") { + // For the printer profile, generate the extruder pages. + if (preset.printer_technology() == ptFFF) + on_preset_loaded(); + else + wxGetApp().sidebar().update_objects_list_extruder_column(1); + } // Reload preset pages with the new configuration values. reload_config(); @@ -2325,7 +2327,7 @@ void Tab::load_current_preset() // update show/hide tabs if (m_name == "printer") { - PrinterTechnology& printer_technology = m_presets->get_edited_preset().printer_technology(); + const PrinterTechnology printer_technology = m_presets->get_edited_preset().printer_technology(); if (printer_technology != static_cast(this)->m_printer_technology) { for (auto tab : wxGetApp().tabs_list) {