Clean-up of print step invalidation.

This commit is contained in:
bubnikv 2017-05-31 17:02:23 +02:00
parent c8b934f8d3
commit 556f40bf00
4 changed files with 130 additions and 100 deletions

View File

@ -7,6 +7,7 @@
#include "SupportMaterial.hpp" #include "SupportMaterial.hpp"
#include "GCode/WipeTowerPrusaMM.hpp" #include "GCode/WipeTowerPrusaMM.hpp"
#include <algorithm> #include <algorithm>
#include <unordered_set>
#include <boost/filesystem.hpp> #include <boost/filesystem.hpp>
#include <boost/lexical_cast.hpp> #include <boost/lexical_cast.hpp>
@ -19,7 +20,9 @@ void Print::clear_objects()
{ {
for (int i = int(this->objects.size())-1; i >= 0; --i) for (int i = int(this->objects.size())-1; i >= 0; --i)
this->delete_object(i); this->delete_object(i);
this->clear_regions(); for (PrintRegion *region : this->regions)
delete region;
this->regions.clear();
} }
void Print::delete_object(size_t idx) void Print::delete_object(size_t idx)
@ -31,7 +34,7 @@ void Print::delete_object(size_t idx)
// TODO: purge unused regions // TODO: purge unused regions
} }
void Print::reload_object(size_t idx) void Print::reload_object(size_t /* idx */)
{ {
/* TODO: this method should check whether the per-object config and per-material configs /* TODO: this method should check whether the per-object config and per-material configs
have changed in such a way that regions need to be rearranged or we can just apply have changed in such a way that regions need to be rearranged or we can just apply
@ -59,13 +62,6 @@ bool Print::reload_model_instances()
return invalidated; return invalidated;
} }
void Print::clear_regions()
{
for (PrintRegion *region : this->regions)
delete region;
this->regions.clear();
}
PrintRegion* Print::add_region() PrintRegion* Print::add_region()
{ {
regions.push_back(new PrintRegion(this)); regions.push_back(new PrintRegion(this));
@ -79,10 +75,91 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
if (opt_keys.empty()) if (opt_keys.empty())
return false; return false;
// Cache the plenty of parameters, which influence the G-code generator only,
// or they are only notes not influencing the generated G-code.
static std::unordered_set<std::string> steps_ignore;
if (steps_ignore.empty()) {
steps_ignore.insert("avoid_crossing_perimeters");
steps_ignore.insert("bed_shape");
steps_ignore.insert("bed_temperature");
steps_ignore.insert("before_layer_gcode");
steps_ignore.insert("bridge_acceleration");
steps_ignore.insert("bridge_fan_speed");
steps_ignore.insert("cooling");
steps_ignore.insert("default_acceleration");
steps_ignore.insert("deretract_speed");
steps_ignore.insert("disable_fan_first_layers");
steps_ignore.insert("duplicate_distance");
steps_ignore.insert("end_gcode");
steps_ignore.insert("extrusion_axis");
steps_ignore.insert("extruder_clearance_height");
steps_ignore.insert("extruder_clearance_radius");
steps_ignore.insert("extruder_colour");
steps_ignore.insert("extruder_offset");
steps_ignore.insert("extrusion_multiplier");
steps_ignore.insert("fan_always_on");
steps_ignore.insert("fan_below_layer_time");
steps_ignore.insert("filament_colour");
steps_ignore.insert("filament_diameter");
steps_ignore.insert("filament_density");
steps_ignore.insert("filament_notes");
steps_ignore.insert("filament_cost");
steps_ignore.insert("filament_max_volumetric_speed");
steps_ignore.insert("first_layer_acceleration");
steps_ignore.insert("first_layer_bed_temperature");
steps_ignore.insert("first_layer_speed");
steps_ignore.insert("gcode_comments");
steps_ignore.insert("gcode_flavor");
steps_ignore.insert("infill_acceleration");
steps_ignore.insert("infill_first");
steps_ignore.insert("layer_gcode");
steps_ignore.insert("min_fan_speed");
steps_ignore.insert("max_fan_speed");
steps_ignore.insert("min_print_speed");
steps_ignore.insert("max_print_speed");
steps_ignore.insert("max_volumetric_speed");
steps_ignore.insert("max_volumetric_extrusion_rate_slope_positive");
steps_ignore.insert("max_volumetric_extrusion_rate_slope_negative");
steps_ignore.insert("notes");
steps_ignore.insert("only_retract_when_crossing_perimeters");
steps_ignore.insert("output_filename_format");
steps_ignore.insert("perimeter_acceleration");
steps_ignore.insert("post_process");
steps_ignore.insert("printer_notes");
steps_ignore.insert("retract_before_travel");
steps_ignore.insert("retract_before_wipe");
steps_ignore.insert("retract_layer_change");
steps_ignore.insert("retract_length");
steps_ignore.insert("retract_length_toolchange");
steps_ignore.insert("retract_lift");
steps_ignore.insert("retract_lift_above");
steps_ignore.insert("retract_lift_below");
steps_ignore.insert("retract_restart_extra");
steps_ignore.insert("retract_restart_extra_toolchange");
steps_ignore.insert("retract_speed");
steps_ignore.insert("slowdown_below_layer_time");
steps_ignore.insert("standby_temperature_delta");
steps_ignore.insert("start_gcode");
steps_ignore.insert("toolchange_gcode");
steps_ignore.insert("threads");
steps_ignore.insert("travel_speed");
steps_ignore.insert("use_firmware_retraction");
steps_ignore.insert("use_relative_e_distances");
steps_ignore.insert("use_volumetric_e");
steps_ignore.insert("set_and_wait_temperatures");
steps_ignore.insert("variable_layer_height");
steps_ignore.insert("wipe");
}
std::vector<PrintStep> steps; std::vector<PrintStep> steps;
std::vector<PrintObjectStep> osteps; std::vector<PrintObjectStep> osteps;
bool invalidated = false;
for (const t_config_option_key &opt_key : opt_keys) { for (const t_config_option_key &opt_key : opt_keys) {
if ( opt_key == "skirts" if (steps_ignore.find(opt_key) != steps_ignore.end()) {
// These options only affect G-code export or they are just notes without influence on the generated G-code,
// so there is nothing to invalidate.
} else if (
opt_key == "skirts"
|| opt_key == "skirt_height" || opt_key == "skirt_height"
|| opt_key == "skirt_distance" || opt_key == "skirt_distance"
|| opt_key == "min_skirt_length" || opt_key == "min_skirt_length"
@ -91,12 +168,14 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
} else if (opt_key == "brim_width") { } else if (opt_key == "brim_width") {
steps.emplace_back(psBrim); steps.emplace_back(psBrim);
steps.emplace_back(psSkirt); steps.emplace_back(psSkirt);
} else if (opt_key == "nozzle_diameter" } else if (
opt_key == "nozzle_diameter"
|| opt_key == "resolution") { || opt_key == "resolution") {
osteps.emplace_back(posSlice); osteps.emplace_back(posSlice);
} else if ( } else if (
opt_key == "complete_objects" opt_key == "complete_objects"
|| opt_key == "filament_type" || opt_key == "filament_type"
|| opt_key == "filament_soluble"
|| opt_key == "first_layer_temperature" || opt_key == "first_layer_temperature"
|| opt_key == "gcode_flavor" || opt_key == "gcode_flavor"
|| opt_key == "single_extruder_multi_material" || opt_key == "single_extruder_multi_material"
@ -109,67 +188,10 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
|| opt_key == "wipe_tower_per_color_wipe" || opt_key == "wipe_tower_per_color_wipe"
|| opt_key == "z_offset") { || opt_key == "z_offset") {
steps.emplace_back(psWipeTower); steps.emplace_back(psWipeTower);
} else if (opt_key == "avoid_crossing_perimeters" } else if (
|| opt_key == "bed_shape" opt_key == "first_layer_extrusion_width"
|| opt_key == "bed_temperature" || opt_key == "min_layer_height"
|| opt_key == "bridge_acceleration" || opt_key == "max_layer_height") {
|| opt_key == "bridge_fan_speed"
|| opt_key == "cooling"
|| opt_key == "default_acceleration"
|| opt_key == "disable_fan_first_layers"
|| opt_key == "duplicate_distance"
|| opt_key == "end_gcode"
|| opt_key == "extruder_clearance_height"
|| opt_key == "extruder_clearance_radius"
|| opt_key == "extruder_colour"
|| opt_key == "extruder_offset"
|| opt_key == "extrusion_axis"
|| opt_key == "extrusion_multiplier"
|| opt_key == "fan_always_on"
|| opt_key == "fan_below_layer_time"
|| opt_key == "filament_diameter"
|| opt_key == "filament_notes"
|| opt_key == "filament_soluble"
|| opt_key == "first_layer_acceleration"
|| opt_key == "first_layer_bed_temperature"
|| opt_key == "first_layer_speed"
|| opt_key == "gcode_comments"
|| opt_key == "infill_acceleration"
|| opt_key == "infill_first"
|| opt_key == "layer_gcode"
|| opt_key == "min_fan_speed"
|| opt_key == "max_fan_speed"
|| opt_key == "min_print_speed"
|| opt_key == "notes"
|| opt_key == "only_retract_when_crossing_perimeters"
|| opt_key == "output_filename_format"
|| opt_key == "perimeter_acceleration"
|| opt_key == "post_process"
|| opt_key == "retract_before_travel"
|| opt_key == "retract_before_wipe"
|| opt_key == "retract_layer_change"
|| opt_key == "retract_length"
|| opt_key == "retract_length_toolchange"
|| opt_key == "retract_lift"
|| opt_key == "retract_lift_above"
|| opt_key == "retract_lift_below"
|| opt_key == "retract_restart_extra"
|| opt_key == "retract_restart_extra_toolchange"
|| opt_key == "retract_speed"
|| opt_key == "deretract_speed"
|| opt_key == "slowdown_below_layer_time"
|| opt_key == "standby_temperature_delta"
|| opt_key == "start_gcode"
|| opt_key == "threads"
|| opt_key == "toolchange_gcode"
|| opt_key == "travel_speed"
|| opt_key == "use_firmware_retraction"
|| opt_key == "use_relative_e_distances"
|| opt_key == "wipe"
|| opt_key == "max_volumetric_extrusion_rate_slope_negative"
|| opt_key == "max_volumetric_extrusion_rate_slope_positive") {
// these options only affect G-code export, so nothing to invalidate
} else if (opt_key == "first_layer_extrusion_width") {
osteps.emplace_back(posPerimeters); osteps.emplace_back(posPerimeters);
osteps.emplace_back(posInfill); osteps.emplace_back(posInfill);
osteps.emplace_back(posSupportMaterial); osteps.emplace_back(posSupportMaterial);
@ -179,11 +201,11 @@ bool Print::invalidate_state_by_config_options(const std::vector<t_config_option
} else { } else {
// for legacy, if we can't handle this option let's invalidate all steps // for legacy, if we can't handle this option let's invalidate all steps
//FIXME invalidate all steps of all objects as well? //FIXME invalidate all steps of all objects as well?
return this->invalidate_all_steps(); invalidated |= this->invalidate_all_steps();
// Continue with the other opt_keys to possibly invalidate any object specific steps.
} }
} }
bool invalidated = false;
sort_remove_duplicates(steps); sort_remove_duplicates(steps);
for (PrintStep step : steps) for (PrintStep step : steps)
invalidated |= this->invalidate_step(step); invalidated |= this->invalidate_step(step);
@ -198,6 +220,7 @@ bool Print::invalidate_step(PrintStep step)
{ {
bool invalidated = this->state.invalidate(step); bool invalidated = this->state.invalidate(step);
// Propagate to dependent steps. // Propagate to dependent steps.
//FIXME Why should skirt invalidate brim? Shouldn't it be vice versa?
if (step == psSkirt) if (step == psSkirt)
invalidated |= this->state.invalidate(psBrim); invalidated |= this->state.invalidate(psBrim);
return invalidated; return invalidated;

View File

@ -252,7 +252,6 @@ public:
PrintRegion* add_region(); PrintRegion* add_region();
// methods for handling state // methods for handling state
bool invalidate_state_by_config_options(const std::vector<t_config_option_key> &opt_keys);
bool invalidate_step(PrintStep step); bool invalidate_step(PrintStep step);
bool invalidate_all_steps() { return this->state.invalidate_all(); } bool invalidate_all_steps() { return this->state.invalidate_all(); }
bool step_done(PrintObjectStep step) const; bool step_done(PrintObjectStep step) const;
@ -294,7 +293,7 @@ public:
std::string output_filepath(const std::string &path); std::string output_filepath(const std::string &path);
private: private:
void clear_regions(); bool invalidate_state_by_config_options(const std::vector<t_config_option_key> &opt_keys);
PrintRegionConfig _region_config_from_model_volume(const ModelVolume &volume); PrintRegionConfig _region_config_from_model_volume(const ModelVolume &volume);
}; };

View File

@ -162,7 +162,7 @@ class StaticPrintConfig : public PrintConfigBase, public StaticConfig
// This object is mapped to Perl as Slic3r::Config::PrintObject. // This object is mapped to Perl as Slic3r::Config::PrintObject.
class PrintObjectConfig : public virtual StaticPrintConfig class PrintObjectConfig : public virtual StaticPrintConfig
{ {
public: public:
ConfigOptionBool clip_multipart_objects; ConfigOptionBool clip_multipart_objects;
ConfigOptionBool dont_support_bridges; ConfigOptionBool dont_support_bridges;
ConfigOptionFloatOrPercent extrusion_width; ConfigOptionFloatOrPercent extrusion_width;
@ -555,7 +555,7 @@ public:
class HostConfig : public virtual StaticPrintConfig class HostConfig : public virtual StaticPrintConfig
{ {
public: public:
ConfigOptionString octoprint_host; ConfigOptionString octoprint_host;
ConfigOptionString octoprint_apikey; ConfigOptionString octoprint_apikey;
ConfigOptionString serial_port; ConfigOptionString serial_port;

View File

@ -137,7 +137,7 @@ bool PrintObject::invalidate_state_by_config_options(const std::vector<t_config_
std::vector<PrintObjectStep> steps; std::vector<PrintObjectStep> steps;
for (const t_config_option_key &opt_key : opt_keys) { for (const t_config_option_key &opt_key : opt_keys) {
if (opt_key == "perimeters" if ( opt_key == "perimeters"
|| opt_key == "extra_perimeters" || opt_key == "extra_perimeters"
|| opt_key == "gap_fill_speed" || opt_key == "gap_fill_speed"
|| opt_key == "overhangs" || opt_key == "overhangs"
@ -147,25 +147,29 @@ bool PrintObject::invalidate_state_by_config_options(const std::vector<t_config_
|| opt_key == "thin_walls" || opt_key == "thin_walls"
|| opt_key == "external_perimeters_first") { || opt_key == "external_perimeters_first") {
steps.emplace_back(posPerimeters); steps.emplace_back(posPerimeters);
} else if (opt_key == "layer_height" } else if (
opt_key == "layer_height"
|| opt_key == "first_layer_height" || opt_key == "first_layer_height"
|| opt_key == "raft_layers") { || opt_key == "raft_layers") {
steps.emplace_back(posSlice); steps.emplace_back(posSlice);
this->reset_layer_height_profile(); this->reset_layer_height_profile();
} }
else if (opt_key == "clip_multipart_objects" else if (
opt_key == "clip_multipart_objects"
|| opt_key == "xy_size_compensation") { || opt_key == "xy_size_compensation") {
steps.emplace_back(posSlice); steps.emplace_back(posSlice);
} else if (opt_key == "support_material" } else if (
opt_key == "support_material"
|| opt_key == "support_material_angle" || opt_key == "support_material_angle"
|| opt_key == "support_material_buildplate_only"
|| opt_key == "support_material_contact_distance"
|| opt_key == "support_material_enforce_layers"
|| opt_key == "support_material_extruder" || opt_key == "support_material_extruder"
|| opt_key == "support_material_extrusion_width" || opt_key == "support_material_extrusion_width"
|| opt_key == "support_material_interface_layers" || opt_key == "support_material_interface_layers"
|| opt_key == "support_material_interface_contact_loops" || opt_key == "support_material_interface_contact_loops"
|| opt_key == "support_material_interface_extruder" || opt_key == "support_material_interface_extruder"
|| opt_key == "support_material_interface_spacing" || opt_key == "support_material_interface_spacing"
|| opt_key == "support_material_interface_speed"
|| opt_key == "support_material_buildplate_only"
|| opt_key == "support_material_pattern" || opt_key == "support_material_pattern"
|| opt_key == "support_material_xy_spacing" || opt_key == "support_material_xy_spacing"
|| opt_key == "support_material_spacing" || opt_key == "support_material_spacing"
@ -175,7 +179,8 @@ bool PrintObject::invalidate_state_by_config_options(const std::vector<t_config_
|| opt_key == "dont_support_bridges" || opt_key == "dont_support_bridges"
|| opt_key == "first_layer_extrusion_width") { || opt_key == "first_layer_extrusion_width") {
steps.emplace_back(posSupportMaterial); steps.emplace_back(posSupportMaterial);
} else if (opt_key == "interface_shells" } else if (
opt_key == "interface_shells"
|| opt_key == "infill_only_where_needed" || opt_key == "infill_only_where_needed"
|| opt_key == "infill_every_layers" || opt_key == "infill_every_layers"
|| opt_key == "solid_infill_every_layers" || opt_key == "solid_infill_every_layers"
@ -187,7 +192,8 @@ bool PrintObject::invalidate_state_by_config_options(const std::vector<t_config_
|| opt_key == "infill_extrusion_width" || opt_key == "infill_extrusion_width"
|| opt_key == "ensure_vertical_shell_thickness") { || opt_key == "ensure_vertical_shell_thickness") {
steps.emplace_back(posPrepareInfill); steps.emplace_back(posPrepareInfill);
} else if (opt_key == "external_fill_pattern" } else if (
opt_key == "external_fill_pattern"
|| opt_key == "external_fill_link_max_length" || opt_key == "external_fill_link_max_length"
|| opt_key == "fill_angle" || opt_key == "fill_angle"
|| opt_key == "fill_pattern" || opt_key == "fill_pattern"
@ -195,21 +201,25 @@ bool PrintObject::invalidate_state_by_config_options(const std::vector<t_config_
|| opt_key == "top_infill_extrusion_width" || opt_key == "top_infill_extrusion_width"
|| opt_key == "first_layer_extrusion_width") { || opt_key == "first_layer_extrusion_width") {
steps.emplace_back(posInfill); steps.emplace_back(posInfill);
} else if (opt_key == "fill_density" } else if (
opt_key == "fill_density"
|| opt_key == "solid_infill_extrusion_width") { || opt_key == "solid_infill_extrusion_width") {
steps.emplace_back(posPerimeters); steps.emplace_back(posPerimeters);
steps.emplace_back(posPrepareInfill); steps.emplace_back(posPrepareInfill);
} else if (opt_key == "external_perimeter_extrusion_width" } else if (
opt_key == "external_perimeter_extrusion_width"
|| opt_key == "perimeter_extruder") { || opt_key == "perimeter_extruder") {
steps.emplace_back(posPerimeters); steps.emplace_back(posPerimeters);
steps.emplace_back(posSupportMaterial); steps.emplace_back(posSupportMaterial);
} else if (opt_key == "bridge_flow_ratio") { } else if (opt_key == "bridge_flow_ratio") {
steps.emplace_back(posPerimeters); steps.emplace_back(posPerimeters);
steps.emplace_back(posInfill); steps.emplace_back(posInfill);
} else if (opt_key == "seam_position" } else if (
opt_key == "seam_position"
|| opt_key == "seam_preferred_direction" || opt_key == "seam_preferred_direction"
|| opt_key == "seam_preferred_direction_jitter" || opt_key == "seam_preferred_direction_jitter"
|| opt_key == "support_material_speed" || opt_key == "support_material_speed"
|| opt_key == "support_material_interface_speed"
|| opt_key == "bridge_speed" || opt_key == "bridge_speed"
|| opt_key == "external_perimeter_speed" || opt_key == "external_perimeter_speed"
|| opt_key == "infill_speed" || opt_key == "infill_speed"
@ -241,28 +251,26 @@ bool PrintObject::invalidate_step(PrintObjectStep step)
invalidated |= invalidated |=
this->invalidate_step(posPrepareInfill) || this->invalidate_step(posPrepareInfill) ||
this->_print->invalidate_step(psSkirt) || this->_print->invalidate_step(psSkirt) ||
this->_print->invalidate_step(psBrim) || this->_print->invalidate_step(psBrim);
this->_print->invalidate_step(psWipeTower);
} else if (step == posPrepareInfill) { } else if (step == posPrepareInfill) {
invalidated |= invalidated |=
this->invalidate_step(posInfill); this->invalidate_step(posInfill);
} else if (step == posInfill) { } else if (step == posInfill) {
invalidated |= invalidated |=
this->_print->invalidate_step(psSkirt) || this->_print->invalidate_step(psSkirt) ||
this->_print->invalidate_step(psBrim) || this->_print->invalidate_step(psBrim);
this->_print->invalidate_step(psWipeTower);
} else if (step == posSlice) { } else if (step == posSlice) {
invalidated |= invalidated |=
this->invalidate_step(posPerimeters) || this->invalidate_step(posPerimeters) ||
this->invalidate_step(posSupportMaterial) || this->invalidate_step(posSupportMaterial);
this->_print->invalidate_step(psWipeTower);
} else if (step == posSupportMaterial) { } else if (step == posSupportMaterial) {
invalidated |= invalidated |=
this->_print->invalidate_step(psSkirt) || this->_print->invalidate_step(psSkirt) ||
this->_print->invalidate_step(psBrim) || this->_print->invalidate_step(psBrim);
this->_print->invalidate_step(psWipeTower);
} }
// Wipe tower depends on the ordering of extruders, which in turn depends on everything.
invalidated |= this->_print->invalidate_step(psWipeTower);
return invalidated; return invalidated;
} }