Merge branch 'master' of https://github.com/prusa3d/PrusaSlicer into et_world_coordinates

This commit is contained in:
enricoturri1966 2022-02-24 13:21:15 +01:00
commit a32c8b77eb
47 changed files with 18897 additions and 18251 deletions

View file

@ -1285,8 +1285,13 @@ bool GUI_App::on_init_inner()
else
load_current_presets();
// Save the active profiles as a "saved into project".
update_saved_preset_from_current_preset();
if (plater_ != nullptr) {
// Save the names of active presets and project specific config into ProjectDirtyStateManager.
plater_->reset_project_dirty_initial_presets();
// Update Project dirty state, update application title bar.
plater_->update_project_dirty_from_presets();
}
@ -2447,16 +2452,13 @@ void GUI_App::update_saved_preset_from_current_preset()
}
}
std::vector<std::pair<unsigned int, std::string>> GUI_App::get_selected_presets() const
std::vector<const PresetCollection*> GUI_App::get_active_preset_collections() const
{
std::vector<std::pair<unsigned int, std::string>> ret;
std::vector<const PresetCollection*> ret;
PrinterTechnology printer_technology = preset_bundle->printers.get_edited_preset().printer_technology();
for (Tab* tab : tabs_list) {
if (tab->supports_printer_technology(printer_technology)) {
const PresetCollection* presets = tab->get_presets();
ret.push_back({ static_cast<unsigned int>(presets->type()), presets->get_selected_preset_name() });
}
}
for (const Tab* tab : tabs_list)
if (tab->supports_printer_technology(printer_technology))
ret.push_back(tab->get_presets());
return ret;
}

View file

@ -252,7 +252,7 @@ public:
bool has_unsaved_preset_changes() const;
bool has_current_preset_changes() const;
void update_saved_preset_from_current_preset();
std::vector<std::pair<unsigned int, std::string>> get_selected_presets() const;
std::vector<const PresetCollection*> get_active_preset_collections() const;
bool check_and_save_current_preset_changes(const wxString& caption, const wxString& header, bool remember_choice = true, bool use_dont_save_insted_of_discard = false);
void apply_keeped_preset_modifications();
bool check_and_keep_current_preset_changes(const wxString& caption, const wxString& header, int action_buttons, bool* postponed_apply_of_keeped_changes = nullptr);

View file

@ -141,6 +141,8 @@ bool ObjectSettings::update_settings_list()
{
Option option = optgroup->get_option(opt);
option.opt.width = 12;
if (!option.opt.full_label.empty())
option.opt.label = option.opt.full_label;
if (is_extruders_cat)
option.opt.max = wxGetApp().extruders_edited_cnt();
optgroup->append_single_option_line(option);

View file

@ -378,6 +378,8 @@ void GLGizmoCut::update_contours()
MeshSlicingParams slicing_params;
slicing_params.trafo = first_glvolume->get_instance_transformation().get_matrix();
slicing_params.trafo.pretranslate(Vec3d(0., 0., first_glvolume->get_sla_shift_z()));
const Polygons polys = slice_mesh(m_cut_contours.mesh.its, m_cut_z, slicing_params);
if (!polys.empty()) {
m_cut_contours.contours.init_from(polys, static_cast<float>(m_cut_z));

View file

@ -859,7 +859,10 @@ bool MainFrame::save_project_as(const wxString& filename)
{
bool ret = (m_plater != nullptr) ? m_plater->export_3mf(into_path(filename)) : false;
if (ret) {
// wxGetApp().update_saved_preset_from_current_preset();
// Make a copy of the active presets for detecting changes in preset values.
wxGetApp().update_saved_preset_from_current_preset();
// Save the names of active presets and project specific config into ProjectDirtyStateManager.
// Reset ProjectDirtyStateManager's state as saved, mark active UndoRedo step as saved with project.
m_plater->reset_project_dirty_after_save();
}
return ret;

View file

@ -311,7 +311,11 @@ wxString get_wraped_wxString(const wxString& in, size_t line_len /*=80*/)
overwrite = true;
if (newline)
break;
} else if (in[j] == '/') {
} else if (in[j] == '/'
#ifdef _WIN32
|| in[j] == '\\'
#endif // _WIN32
) {
// Insert after the slash.
ibreak = ++ j;
overwrite = false;

View file

@ -502,6 +502,7 @@ FreqChangedParams::FreqChangedParams(wxWindow* parent) :
std::vector<float> extruders = dlg.get_extruders();
(project_config.option<ConfigOptionFloats>("wiping_volumes_matrix"))->values = std::vector<double>(matrix.begin(), matrix.end());
(project_config.option<ConfigOptionFloats>("wiping_volumes_extruders"))->values = std::vector<double>(extruders.begin(), extruders.end());
// Update Project dirty state, update application title bar.
wxGetApp().plater()->update_project_dirty_from_presets();
wxPostEvent(parent, SimpleEvent(EVT_SCHEDULE_BACKGROUND_PROCESS, parent));
}
@ -2359,7 +2360,7 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
}
const auto loading = _L("Loading") + dots;
wxProgressDialog dlg(loading, "", 100, find_toplevel_parent(q), wxPD_AUTO_HIDE);
wxProgressDialog progress_dlg(loading, "", 100, find_toplevel_parent(q), wxPD_AUTO_HIDE);
wxBusyCursor busy;
auto *new_model = (!load_model || one_by_one) ? nullptr : new Slic3r::Model();
@ -2368,7 +2369,8 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
int answer_convert_from_meters = wxOK_DEFAULT;
int answer_convert_from_imperial_units = wxOK_DEFAULT;
for (size_t i = 0; i < input_files.size(); ++i) {
size_t input_files_size = input_files.size();
for (size_t i = 0; i < input_files_size; ++i) {
#ifdef _WIN32
auto path = input_files[i];
// On Windows, we swap slashes to back slashes, see GH #6803 as read_from_file() does not understand slashes on Windows thus it assignes full path to names of loaded objects.
@ -2378,8 +2380,8 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
const auto &path = input_files[i];
#endif // _WIN32
const auto filename = path.filename();
dlg.Update(static_cast<int>(100.0f * static_cast<float>(i) / static_cast<float>(input_files.size())), _L("Loading file") + ": " + from_path(filename));
dlg.Fit();
progress_dlg.Update(static_cast<int>(100.0f * static_cast<float>(i) / static_cast<float>(input_files.size())), _L("Loading file") + ": " + from_path(filename));
progress_dlg.Fit();
const bool type_3mf = std::regex_match(path.string(), pattern_3mf);
const bool type_zip_amf = !type_3mf && std::regex_match(path.string(), pattern_zip_amf);
@ -2390,17 +2392,28 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
bool is_project_file = type_prusa;
try {
if (type_3mf || type_zip_amf) {
#ifdef __linux__
// On Linux Constructor of the ProgressDialog calls DisableOtherWindows() function which causes a disabling of all children of the find_toplevel_parent(q)
// And a destructor of the ProgressDialog calls ReenableOtherWindows() function which revert previously disabled children.
// But if printer technology will be changes during project loading,
// then related SLA Print and Materials Settings or FFF Print and Filaments Settings will be unparent from the wxNoteBook
// and that is why they will never be enabled after destruction of the ProgressDialog.
// So, distroy progress_gialog if we are loading project file
if (input_files_size == 1)
progress_dlg.Destroy();
#endif
DynamicPrintConfig config;
PrinterTechnology loaded_printer_technology {ptFFF};
{
DynamicPrintConfig config_loaded;
ConfigSubstitutionContext config_substitutions{ ForwardCompatibilitySubstitutionRule::Enable };
model = Slic3r::Model::read_from_archive(path.string(), &config_loaded, &config_substitutions, only_if(load_config, Model::LoadAttribute::CheckVersion));
if (load_config && !config_loaded.empty()) {
// Based on the printer technology field found in the loaded config, select the base for the config,
PrinterTechnology printer_technology = Preset::printer_technology(config_loaded);
loaded_printer_technology = Preset::printer_technology(config_loaded);
// We can't to load SLA project if there is at least one multi-part object on the bed
if (printer_technology == ptSLA) {
if (loaded_printer_technology == ptSLA) {
const ModelObjectPtrs& objects = q->model().objects;
for (auto object : objects)
if (object->volumes.size() > 1) {
@ -2412,7 +2425,7 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
}
}
config.apply(printer_technology == ptFFF ?
config.apply(loaded_printer_technology == ptFFF ?
static_cast<const ConfigBase&>(FullPrintConfig::defaults()) :
static_cast<const ConfigBase&>(SLAFullPrintConfig::defaults()));
// and place the loaded config over the base.
@ -2443,7 +2456,7 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
};
std::vector<std::string> names;
if (printer_technology == ptFFF) {
if (loaded_printer_technology == ptFFF) {
update_selected_preset_visibility(preset_bundle->prints, names);
for (const std::string& filament : preset_bundle->filament_presets) {
Preset* preset = preset_bundle->filaments.find_preset(filament);
@ -2474,7 +2487,7 @@ std::vector<size_t> Plater::priv::load_files(const std::vector<fs::path>& input_
}
}
if (printer_technology == ptFFF)
if (loaded_printer_technology == ptFFF)
CustomGCode::update_custom_gcode_per_print_z_from_config(model.custom_gcode_per_print_z, &preset_bundle->project_config);
// For exporting from the amf/3mf we shouldn't check printer_presets for the containing information about "Print Host upload"
@ -5269,8 +5282,11 @@ void Plater::new_project()
take_snapshot(_L("New Project"), UndoRedo::SnapshotType::ProjectSeparator);
Plater::SuppressSnapshots suppress(this);
reset();
// Save the names of active presets and project specific config into ProjectDirtyStateManager.
reset_project_dirty_initial_presets();
// Make a copy of the active presets for detecting changes in preset values.
wxGetApp().update_saved_preset_from_current_preset();
// Update Project dirty state, update application title bar.
update_project_dirty_from_presets();
}
@ -5299,7 +5315,11 @@ void Plater::load_project(const wxString& filename)
if (! load_files({ into_path(filename) }).empty()) {
// At least one file was loaded.
p->set_project_filename(filename);
// Save the names of active presets and project specific config into ProjectDirtyStateManager.
reset_project_dirty_initial_presets();
// Make a copy of the active presets for detecting changes in preset values.
wxGetApp().update_saved_preset_from_current_preset();
// Update Project dirty state, update application title bar.
update_project_dirty_from_presets();
}
}
@ -5984,7 +6004,6 @@ void Plater::export_stl_obj(bool extended, bool selection_only)
}
else if (0 <= instance_id && instance_id < int(mo.instances.size()))
mesh.transform(mo.instances[instance_id]->get_matrix(), true);
return mesh;
};

View file

@ -17,9 +17,11 @@ namespace GUI {
void ProjectDirtyStateManager::update_from_undo_redo_stack(bool dirty)
{
m_plater_dirty = dirty;
if (const Plater *plater = wxGetApp().plater(); plater && wxGetApp().initialized())
wxGetApp().mainframe->update_title();
if (m_plater_dirty != dirty) {
m_plater_dirty = dirty;
if (const Plater *plater = wxGetApp().plater(); plater && wxGetApp().initialized())
wxGetApp().mainframe->update_title();
}
}
void ProjectDirtyStateManager::update_from_presets()
@ -27,11 +29,11 @@ void ProjectDirtyStateManager::update_from_presets()
m_presets_dirty = false;
// check switching of the presets only for exist/loaded project, but not for new
GUI_App &app = wxGetApp();
if (!app.plater()->get_project_filename().IsEmpty()) {
for (const auto& [type, name] : app.get_selected_presets())
m_presets_dirty |= !m_initial_presets[type].empty() && m_initial_presets[type] != name;
bool has_project = ! app.plater()->get_project_filename().IsEmpty();
for (const PresetCollection *preset_collection : app.get_active_preset_collections()) {
auto type = preset_collection->type();
m_presets_dirty |= (has_project && !m_initial_presets[type].empty() && m_initial_presets[type] != preset_collection->get_selected_preset_name()) || preset_collection->saved_is_dirty();
}
m_presets_dirty |= app.has_unsaved_preset_changes();
m_project_config_dirty = m_initial_project_config != app.preset_bundle->project_config;
app.mainframe->update_title();
}
@ -49,8 +51,8 @@ void ProjectDirtyStateManager::reset_initial_presets()
{
m_initial_presets.fill(std::string{});
GUI_App &app = wxGetApp();
for (const auto& [type, name] : app.get_selected_presets())
m_initial_presets[type] = name;
for (const PresetCollection *preset_collection : app.get_active_preset_collections())
m_initial_presets[preset_collection->type()] = preset_collection->get_selected_preset_name();
m_initial_project_config = app.preset_bundle->project_config;
}

View file

@ -1247,6 +1247,7 @@ void Tab::on_presets_changed()
// to avoid needless preset loading from update() function
m_dependent_tabs.clear();
// Update Project dirty state, update application title bar.
wxGetApp().plater()->update_project_dirty_from_presets();
}
@ -4113,7 +4114,7 @@ wxSizer* TabPrint::create_manage_substitution_widget(wxWindow* parent)
create_btn(&m_del_all_substitutions_btn, _L("Delete all"), "cross");
m_del_all_substitutions_btn->Bind(wxEVT_BUTTON, [this, parent](wxCommandEvent e) {
if (MessageDialog(parent, _L("Are you sure you want to delete all substitutions?"), SLIC3R_APP_NAME, wxYES_NO | wxICON_QUESTION).
if (MessageDialog(parent, _L("Are you sure you want to delete all substitutions?"), SLIC3R_APP_NAME, wxYES_NO | wxCANCEL | wxICON_QUESTION).
ShowModal() != wxID_YES)
return;
m_subst_manager.delete_all();

View file

@ -371,6 +371,7 @@ public:
DynamicPrintConfig* get_config() { return m_config; }
PresetCollection* get_presets() { return m_presets; }
const PresetCollection* get_presets() const { return m_presets; }
void on_value_change(const std::string& opt_key, const boost::any& value);