#265 fix crash on adding extruder

This commit is contained in:
supermerill 2020-06-04 20:36:10 +02:00
parent f8c41fe6e7
commit 6a33909e79

View File

@ -918,7 +918,7 @@ void Tab::on_value_change(const std::string& opt_key, const boost::any& value)
update_wiping_button_visibility(); update_wiping_button_visibility();
if (opt_key == "extruders_count") if (opt_key == "extruders_count")
wxGetApp().plater()->on_extruders_change(boost::any_cast<size_t>(value)); wxGetApp().plater()->on_extruders_change(boost::any_cast<int>(value));
update(); update();
} }
@ -1117,8 +1117,15 @@ t_change set_or_add(t_change previous, t_change toadd) {
return toadd; return toadd;
else else
return [previous, toadd](t_config_option_key opt_key, boost::any value) { return [previous, toadd](t_config_option_key opt_key, boost::any value) {
previous(opt_key, value); try {
toadd(opt_key, value); toadd(opt_key, value);
previous(opt_key, value);
}
catch (const std::exception & ex) {
std::cout << "Exception while calling group event about "<<opt_key<<": " << ex.what();
throw ex;
}
}; };
} }
@ -1245,48 +1252,43 @@ bool Tab::create_pages(std::string setting_type_name, int idx_page)
// optgroup->get_value() return int for def.type == coInt, // optgroup->get_value() return int for def.type == coInt,
// Thus, there should be boost::any_cast<int> ! // Thus, there should be boost::any_cast<int> !
// Otherwise, boost::any_cast<size_t> causes an "unhandled unknown exception" // Otherwise, boost::any_cast<size_t> causes an "unhandled unknown exception"
size_t extruders_count = size_t(boost::any_cast<int>(current_group->get_value("extruders_count"))); if (opt_key == "extruders_count" || opt_key == "single_extruder_multi_material") {
wxTheApp->CallAfter([this, tab, opt_key, value, extruders_count]() { size_t extruders_count = size_t(boost::any_cast<int>(current_group->get_value("extruders_count")));
if (opt_key == "extruders_count" || opt_key == "single_extruder_multi_material") { tab->extruders_count_changed(extruders_count);
tab->extruders_count_changed(extruders_count); init_options_list(); // m_options_list should be updated before UI updating
init_options_list(); // m_options_list should be updated before UI updating update_dirty();
update_dirty(); if (opt_key == "single_extruder_multi_material") { // the single_extruder_multimaterial was added to force pages
if (opt_key == "single_extruder_multi_material") { // the single_extruder_multimaterial was added to force pages on_value_change(opt_key, value); // rebuild - let's make sure the on_value_change is not skipped
on_value_change(opt_key, value); // rebuild - let's make sure the on_value_change is not skipped
if (boost::any_cast<bool>(value) && tab->m_extruders_count > 1) { if (boost::any_cast<bool>(value) && tab->m_extruders_count > 1) {
SuppressBackgroundProcessingUpdate sbpu; SuppressBackgroundProcessingUpdate sbpu;
std::vector<double> nozzle_diameters = static_cast<const ConfigOptionFloats*>(m_config->option("nozzle_diameter"))->values; std::vector<double> nozzle_diameters = static_cast<const ConfigOptionFloats*>(m_config->option("nozzle_diameter"))->values;
const double frst_diam = nozzle_diameters[0]; const double frst_diam = nozzle_diameters[0];
for (auto cur_diam : nozzle_diameters) { for (auto cur_diam : nozzle_diameters) {
// if value is differs from first nozzle diameter value // if value is differs from first nozzle diameter value
if (fabs(cur_diam - frst_diam) > EPSILON) { if (fabs(cur_diam - frst_diam) > EPSILON) {
const wxString msg_text = _(L("Single Extruder Multi Material is selected, \n" const wxString msg_text = _(L("Single Extruder Multi Material is selected, \n"
"and all extruders must have the same diameter.\n" "and all extruders must have the same diameter.\n"
"Do you want to change the diameter for all extruders to first extruder nozzle diameter value?")); "Do you want to change the diameter for all extruders to first extruder nozzle diameter value?"));
wxMessageDialog dialog(parent(), msg_text, _(L("Nozzle diameter")), wxICON_WARNING | wxYES_NO); wxMessageDialog dialog(parent(), msg_text, _(L("Nozzle diameter")), wxICON_WARNING | wxYES_NO);
DynamicPrintConfig new_conf = *m_config; DynamicPrintConfig new_conf = *m_config;
if (dialog.ShowModal() == wxID_YES) { if (dialog.ShowModal() == wxID_YES) {
for (size_t i = 1; i < nozzle_diameters.size(); i++) for (size_t i = 1; i < nozzle_diameters.size(); i++)
nozzle_diameters[i] = frst_diam; nozzle_diameters[i] = frst_diam;
new_conf.set_key_value("nozzle_diameter", new ConfigOptionFloats(nozzle_diameters)); new_conf.set_key_value("nozzle_diameter", new ConfigOptionFloats(nozzle_diameters));
} else } else
new_conf.set_key_value("single_extruder_multi_material", new ConfigOptionBool(false)); new_conf.set_key_value("single_extruder_multi_material", new ConfigOptionBool(false));
load_config(new_conf); load_config(new_conf);
break; break;
}
} }
} }
} }
} else {
update_dirty();
on_value_change(opt_key, value);
} }
}); }
}); });
} else if (params[i] == "milling_count_event") { } else if (params[i] == "milling_count_event") {
TabPrinter* tab = nullptr; TabPrinter* tab = nullptr;
@ -1295,39 +1297,29 @@ bool Tab::create_pages(std::string setting_type_name, int idx_page)
// optgroup->get_value() return int for def.type == coInt, // optgroup->get_value() return int for def.type == coInt,
// Thus, there should be boost::any_cast<int> ! // Thus, there should be boost::any_cast<int> !
// Otherwise, boost::any_cast<size_t> causes an "unhandled unknown exception" // Otherwise, boost::any_cast<size_t> causes an "unhandled unknown exception"
size_t milling_count = size_t(boost::any_cast<int>(current_group->get_value("milling_count"))); if (opt_key == "milling_count") {
wxTheApp->CallAfter([this, tab, opt_key, value, milling_count]() { size_t milling_count = size_t(boost::any_cast<int>(current_group->get_value("milling_count")));
if (opt_key == "milling_count") { tab->milling_count_changed(milling_count);
tab->milling_count_changed(milling_count); init_options_list(); // m_options_list should be updated before UI updating
init_options_list(); // m_options_list should be updated before UI updating }
update_dirty();
} else {
update_dirty();
on_value_change(opt_key, value);
}
});
}); });
} }
else if (params[i] == "silent_mode_event") { else if (params[i] == "silent_mode_event") {
TabPrinter* tab = nullptr; TabPrinter* tab = nullptr;
if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) continue; if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) continue;
current_group->m_on_change = [this, tab](t_config_option_key opt_key, boost::any value) { current_group->m_on_change = set_or_add(current_group->m_on_change, [this, tab](t_config_option_key opt_key, boost::any value) {
wxTheApp->CallAfter([this, tab, opt_key, value]() { if (opt_key == "silent_mode") {
if (opt_key == "silent_mode") { bool val = boost::any_cast<bool>(value);
bool val = boost::any_cast<bool>(value); if (tab->m_use_silent_mode != val) {
if (tab->m_use_silent_mode != val) { tab->m_rebuild_kinematics_page = true;
tab->m_rebuild_kinematics_page = true; tab->m_use_silent_mode = val;
tab->m_use_silent_mode = val;
}
} }
tab->build_unregular_pages(); }
update_dirty(); tab->build_unregular_pages();
on_value_change(opt_key, value); });
});
};
} }
else if (params[i] == "material_density_event") { else if (params[i] == "material_density_event") {
current_group->m_on_change = [this, current_group](t_config_option_key opt_key, boost::any value) current_group->m_on_change = set_or_add(current_group->m_on_change, [this, current_group](t_config_option_key opt_key, boost::any value)
{ {
DynamicPrintConfig new_conf = *m_config; DynamicPrintConfig new_conf = *m_config;
@ -1346,14 +1338,11 @@ bool Tab::create_pages(std::string setting_type_name, int idx_page)
load_config(new_conf); load_config(new_conf);
update_dirty();
on_value_change(opt_key, value);
if (opt_key == "bottle_volume" || opt_key == "bottle_cost") { if (opt_key == "bottle_volume" || opt_key == "bottle_cost") {
wxGetApp().sidebar().update_sliced_info_sizer(); wxGetApp().sidebar().update_sliced_info_sizer();
wxGetApp().sidebar().Layout(); wxGetApp().sidebar().Layout();
} }
}; });
} }
} }
if (logs) std::cout << "create group " << params.back() << "\n"; if (logs) std::cout << "create group " << params.back() << "\n";
@ -1598,7 +1587,7 @@ bool Tab::create_pages(std::string setting_type_name, int idx_page)
Option option(def, "milling_count"); Option option(def, "milling_count");
current_group->append_single_option_line(option); current_group->append_single_option_line(option);
} else if (full_line == "update_nozzle_diameter") { } else if (full_line == "update_nozzle_diameter") {
current_group->m_on_change = [this, idx_page](const t_config_option_key& opt_key, boost::any value) current_group->m_on_change = set_or_add(current_group->m_on_change, [this, idx_page](const t_config_option_key& opt_key, boost::any value)
{ {
TabPrinter* tab = nullptr; TabPrinter* tab = nullptr;
if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) return; if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) return;
@ -1630,9 +1619,8 @@ bool Tab::create_pages(std::string setting_type_name, int idx_page)
} }
} }
update_dirty();
update(); update();
}; });
}else if(full_line == "reset_to_filament_color") { }else if(full_line == "reset_to_filament_color") {
TabPrinter* tab = nullptr; TabPrinter* tab = nullptr;
if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) continue; if ((tab = dynamic_cast<TabPrinter*>(this)) == nullptr) continue;
@ -2124,7 +2112,7 @@ void TabPrinter::extruders_count_changed(size_t extruders_count)
build_unregular_pages(); build_unregular_pages();
if (is_count_changed) { if (is_count_changed) {
on_value_change("extruders_count", extruders_count); on_value_change("extruders_count", (int)extruders_count);
wxGetApp().sidebar().update_objects_list_extruder_column(extruders_count); wxGetApp().sidebar().update_objects_list_extruder_column(extruders_count);
} }
} }
@ -2244,6 +2232,7 @@ PageShp TabPrinter::build_kinematics_page()
void TabPrinter::build_unregular_pages() void TabPrinter::build_unregular_pages()
{ {
size_t n_before_extruders = 2; // Count of pages before Extruder pages size_t n_before_extruders = 2; // Count of pages before Extruder pages
bool changed = false;
/* ! Freeze/Thaw in this function is needed to avoid call OnPaint() for erased pages /* ! Freeze/Thaw in this function is needed to avoid call OnPaint() for erased pages
* and be cause of application crash, when try to change Preset in moment, * and be cause of application crash, when try to change Preset in moment,
@ -2276,6 +2265,8 @@ void TabPrinter::build_unregular_pages()
if (existed_page < n_before_extruders) { if (existed_page < n_before_extruders) {
auto page = build_kinematics_page(); auto page = build_kinematics_page();
changed = true;
m_rebuild_kinematics_page = false;
#ifdef __WXMSW__ #ifdef __WXMSW__
layout_page(page); layout_page(page);
#endif #endif
@ -2292,6 +2283,7 @@ void TabPrinter::build_unregular_pages()
for (size_t i = 0; i < m_pages.size(); ++i) // first make sure it's not there already for (size_t i = 0; i < m_pages.size(); ++i) // first make sure it's not there already
if (m_pages[i]->title().find(_(L("Single extruder MM setup"))) != std::string::npos) { if (m_pages[i]->title().find(_(L("Single extruder MM setup"))) != std::string::npos) {
m_pages.erase(m_pages.begin() + i); m_pages.erase(m_pages.begin() + i);
changed = true;
break; break;
} }
m_has_single_extruder_MM_page = false; m_has_single_extruder_MM_page = false;
@ -2312,6 +2304,7 @@ void TabPrinter::build_unregular_pages()
optgroup->append_single_option_line("wipe_advanced_algo"); optgroup->append_single_option_line("wipe_advanced_algo");
m_pages.insert(m_pages.end() - n_after_single_extruder_MM, page); m_pages.insert(m_pages.end() - n_after_single_extruder_MM, page);
m_has_single_extruder_MM_page = true; m_has_single_extruder_MM_page = true;
changed = true;
} }
// Build missed extruder pages // Build missed extruder pages
@ -2319,14 +2312,16 @@ void TabPrinter::build_unregular_pages()
if (this->create_pages("extruder.ui", extruder_idx)) { if (this->create_pages("extruder.ui", extruder_idx)) {
std::rotate(m_pages.begin() + n_before_extruders + extruder_idx, m_pages.end() - 1, m_pages.end()); std::rotate(m_pages.begin() + n_before_extruders + extruder_idx, m_pages.end() - 1, m_pages.end());
continue; changed = true;
} }
} }
// # remove extra pages // # remove extra pages
if (m_extruders_count < m_extruders_count_old) if (m_extruders_count < m_extruders_count_old) {
m_pages.erase(m_pages.begin() + n_before_extruders + m_extruders_count, m_pages.erase(m_pages.begin() + n_before_extruders + m_extruders_count,
m_pages.begin() + n_before_extruders + m_extruders_count_old); m_pages.begin() + n_before_extruders + m_extruders_count_old);
changed = true;
}
m_extruders_count_old = m_extruders_count; m_extruders_count_old = m_extruders_count;
// Build missed milling pages // Build missed milling pages
@ -2334,19 +2329,22 @@ void TabPrinter::build_unregular_pages()
if (this->create_pages("milling.ui", milling_idx)) { if (this->create_pages("milling.ui", milling_idx)) {
std::rotate(m_pages.begin() + n_before_extruders + m_extruders_count + milling_idx, m_pages.end() - 1, m_pages.end()); std::rotate(m_pages.begin() + n_before_extruders + m_extruders_count + milling_idx, m_pages.end() - 1, m_pages.end());
continue; changed = true;
} }
} }
// # remove extra pages // # remove extra pages
if (m_milling_count < m_milling_count_old) if (m_milling_count < m_milling_count_old) {
m_pages.erase( m_pages.begin() + n_before_extruders + m_extruders_count + m_milling_count, m_pages.erase(m_pages.begin() + n_before_extruders + m_extruders_count + m_milling_count,
m_pages.begin() + n_before_extruders + m_extruders_count + m_milling_count_old); m_pages.begin() + n_before_extruders + m_extruders_count + m_milling_count_old);
changed = true;
}
m_milling_count_old = m_milling_count; m_milling_count_old = m_milling_count;
Thaw(); Thaw();
rebuild_page_tree(); if(changed)
rebuild_page_tree();
// Reload preset pages with current configuration values // Reload preset pages with current configuration values
reload_config(); reload_config();
@ -2371,6 +2369,7 @@ void TabPrinter::on_preset_loaded()
void TabPrinter::update_pages() void TabPrinter::update_pages()
{ {
// update m_pages ONLY if printer technology is changed // update m_pages ONLY if printer technology is changed
const PrinterTechnology new_printer_technology = m_presets->get_edited_preset().printer_technology(); const PrinterTechnology new_printer_technology = m_presets->get_edited_preset().printer_technology();
if (new_printer_technology == m_printer_technology) if (new_printer_technology == m_printer_technology)
@ -2394,7 +2393,7 @@ void TabPrinter::update_pages()
if (m_extruders_count > 1) if (m_extruders_count > 1)
{ {
m_preset_bundle->update_multi_material_filament_presets(); m_preset_bundle->update_multi_material_filament_presets();
on_value_change("extruders_count", m_extruders_count); on_value_change("extruders_count", (int)m_extruders_count);
} }
} }
else else