diff --git a/src/libslic3r/Geometry.cpp b/src/libslic3r/Geometry.cpp index 54dcb14cca..49e50a671d 100644 --- a/src/libslic3r/Geometry.cpp +++ b/src/libslic3r/Geometry.cpp @@ -640,6 +640,22 @@ Transform3d Transformation::get_matrix_no_scaling_factor() const return copy.get_matrix(); } +// Orca: Implement prusa's filament shrink compensation approach +Transform3d Transformation::get_matrix_with_applied_shrinkage_compensation(const Vec3d &shrinkage_compensation) const { + const Transform3d shrinkage_trafo = Geometry::scale_transform(shrinkage_compensation); + const Vec3d trafo_offset = this->get_offset(); + const Vec3d trafo_offset_xy = Vec3d(trafo_offset.x(), trafo_offset.y(), 0.); + + Transformation copy(*this); + copy.set_offset(Axis::X, 0.); + copy.set_offset(Axis::Y, 0.); + + Transform3d trafo_after_shrinkage = (shrinkage_trafo * copy.get_matrix()); + trafo_after_shrinkage.translation() += trafo_offset_xy; + + return trafo_after_shrinkage; + } + Transformation Transformation::operator * (const Transformation& other) const { return Transformation(get_matrix() * other.get_matrix()); diff --git a/src/libslic3r/Geometry.hpp b/src/libslic3r/Geometry.hpp index 67b27dd293..2b027a231a 100644 --- a/src/libslic3r/Geometry.hpp +++ b/src/libslic3r/Geometry.hpp @@ -466,6 +466,9 @@ public: Transform3d get_matrix_no_offset() const; Transform3d get_matrix_no_scaling_factor() const; + // Orca: Implement prusa's filament shrink compensation approach + Transform3d get_matrix_with_applied_shrinkage_compensation(const Vec3d &shrinkage_compensation) const; + void set_matrix(const Transform3d& transform) { m_matrix = transform; } Transformation operator * (const Transformation& other) const; diff --git a/src/libslic3r/Model.cpp b/src/libslic3r/Model.cpp index 63be317b6d..fe8ff61018 100644 --- a/src/libslic3r/Model.cpp +++ b/src/libslic3r/Model.cpp @@ -2779,6 +2779,24 @@ void ModelVolume::convert_from_meters() this->source.is_converted_from_meters = true; } +// Orca: Implement prusa's filament shrink compensation approach +// Returns 0-based indices of extruders painted by multi-material painting gizmo. +std::vector ModelVolume::get_extruders_from_multi_material_painting() const { + if (!this->is_mm_painted()) + return {}; + + assert(static_cast(TriangleStateType::Extruder1) - 1 == 0); + const TriangleSelector::TriangleSplittingData &data = this->mmu_segmentation_facets.get_data(); + + std::vector extruders; + for (size_t state_idx = static_cast(EnforcerBlockerType::Extruder1); state_idx < data.used_states.size(); ++state_idx) { + if (data.used_states[state_idx]) + extruders.emplace_back(state_idx - 1); + } + + return extruders; + } + void ModelInstance::transform_mesh(TriangleMesh* mesh, bool dont_translate) const { mesh->transform(dont_translate ? get_matrix_no_offset() : get_matrix()); diff --git a/src/libslic3r/Model.hpp b/src/libslic3r/Model.hpp index 9fc315778f..56f1f7afed 100644 --- a/src/libslic3r/Model.hpp +++ b/src/libslic3r/Model.hpp @@ -991,6 +991,10 @@ public: bool is_fdm_support_painted() const { return !this->supported_facets.empty(); } bool is_seam_painted() const { return !this->seam_facets.empty(); } bool is_mm_painted() const { return !this->mmu_segmentation_facets.empty(); } + + // Orca: Implement prusa's filament shrink compensation approach + // Returns 0-based indices of extruders painted by multi-material painting gizmo. + std::vector get_extruders_from_multi_material_painting() const; protected: friend class Print; diff --git a/src/libslic3r/Preset.cpp b/src/libslic3r/Preset.cpp index cbab85b88a..c9328821be 100644 --- a/src/libslic3r/Preset.cpp +++ b/src/libslic3r/Preset.cpp @@ -840,7 +840,7 @@ static std::vector s_Preset_filament_options { "filament_wipe_distance", "additional_cooling_fan_speed", "nozzle_temperature_range_low", "nozzle_temperature_range_high", //SoftFever - "enable_pressure_advance", "pressure_advance","adaptive_pressure_advance","adaptive_pressure_advance_model","adaptive_pressure_advance_overhangs", "adaptive_pressure_advance_bridges","chamber_temperature", "filament_shrink", "support_material_interface_fan_speed", "filament_notes" /*,"filament_seam_gap"*/, + "enable_pressure_advance", "pressure_advance","adaptive_pressure_advance","adaptive_pressure_advance_model","adaptive_pressure_advance_overhangs", "adaptive_pressure_advance_bridges","chamber_temperature", "filament_shrink","filament_shrinkage_compensation_z", "support_material_interface_fan_speed", "filament_notes" /*,"filament_seam_gap"*/, "filament_loading_speed", "filament_loading_speed_start", "filament_unloading_speed", "filament_unloading_speed_start", "filament_toolchange_delay", "filament_cooling_moves", "filament_stamping_loading_speed", "filament_stamping_distance", "filament_cooling_initial_speed", "filament_cooling_final_speed", "filament_ramming_parameters", diff --git a/src/libslic3r/Print.cpp b/src/libslic3r/Print.cpp index 03f76fe3a3..532875434b 100644 --- a/src/libslic3r/Print.cpp +++ b/src/libslic3r/Print.cpp @@ -234,6 +234,7 @@ bool Print::invalidate_state_by_config_options(const ConfigOptionResolver & /* n opt_key == "initial_layer_print_height" || opt_key == "nozzle_diameter" || opt_key == "filament_shrink" + || opt_key == "filament_shrinkage_compensation_z" || opt_key == "resolution" || opt_key == "precise_z_height" // Spiral Vase forces different kind of slicing than the normal model: @@ -1120,13 +1121,29 @@ StringObjectException Print::validate(StringObjectException *warning, Polygons* const PrintObject &print_object = *m_objects[print_object_idx]; //FIXME It is quite expensive to generate object layers just to get the print height! if (auto layers = generate_object_layers(print_object.slicing_parameters(), layer_height_profile(print_object_idx), print_object.config().precise_z_height.value); - ! layers.empty() && layers.back() > this->config().printable_height + EPSILON) { - return + !layers.empty()) { + + Vec3d test =this->shrinkage_compensation(); + const double shrinkage_compensation_z = this->shrinkage_compensation().z(); + + if (shrinkage_compensation_z != 1. && layers.back() > (this->config().printable_height / shrinkage_compensation_z + EPSILON)) { + // The object exceeds the maximum build volume height because of shrinkage compensation. + return StringObjectException{ + Slic3r::format(_u8L("While the object %1% itself fits the build volume, it exceeds the maximum build volume height because of material shrinkage compensation."), print_object.model_object()->name), + print_object.model_object(), + "" + }; + } else if (layers.back() > this->config().printable_height + EPSILON) { // Test whether the last slicing plane is below or above the print volume. - { 0.5 * (layers[layers.size() - 2] + layers.back()) > this->config().printable_height + EPSILON ? + return StringObjectException{ + 0.5 * (layers[layers.size() - 2] + layers.back()) > this->config().printable_height + EPSILON ? Slic3r::format(_u8L("The object %1% exceeds the maximum build volume height."), print_object.model_object()->name) : Slic3r::format(_u8L("While the object %1% itself fits the build volume, its last layer exceeds the maximum build volume height."), print_object.model_object()->name) + - " " + _u8L("You might want to reduce the size of your model or change current print settings and retry.") }; + " " + _u8L("You might want to reduce the size of your model or change current print settings and retry."), + print_object.model_object(), + "" + }; + } } } @@ -1568,6 +1585,10 @@ StringObjectException Print::validate(StringObjectException *warning, Polygons* BOOST_LOG_TRIVIAL(warning) << "Orca: validate motion ability failed: " << e.what() << std::endl; } } + if (!this->has_same_shrinkage_compensations()){ + warning->string = L("Filament shrinkage will not be used because filament shrinkage for the used filaments differs significantly."); + warning->opt_key = ""; + } return {}; } @@ -2949,6 +2970,44 @@ std::string PrintStatistics::finalize_output_path(const std::string &path_in) co return final_path; } +// Orca: Implement prusa's filament shrink compensation approach +// Returns if all used filaments have same shrinkage compensations. + bool Print::has_same_shrinkage_compensations() const { + const std::vector extruders = this->extruders(); + if (extruders.empty()) + return false; + + const double filament_shrinkage_compensation_xy = m_config.filament_shrink.get_at(extruders.front()); + const double filament_shrinkage_compensation_z = m_config.filament_shrinkage_compensation_z.get_at(extruders.front()); + + for (unsigned int extruder : extruders) { + if (filament_shrinkage_compensation_xy != m_config.filament_shrink.get_at(extruder) || + filament_shrinkage_compensation_z != m_config.filament_shrinkage_compensation_z.get_at(extruder)) { + return false; + } + } + + return true; + } + +// Orca: Implement prusa's filament shrink compensation approach, but amended so 100% from the user is the equivalent to 0 in orca. + // Returns scaling for each axis representing shrinkage compensations in each axis. +Vec3d Print::shrinkage_compensation() const +{ + if (!this->has_same_shrinkage_compensations()) + return Vec3d::Ones(); + + const unsigned int first_extruder = this->extruders().front(); + + const double xy_shrinkage_percent = m_config.filament_shrink.get_at(first_extruder); + const double z_shrinkage_percent = m_config.filament_shrinkage_compensation_z.get_at(first_extruder); + + const double xy_compensation = 100.0 / xy_shrinkage_percent; + const double z_compensation = 100.0 / z_shrinkage_percent; + + return { xy_compensation, xy_compensation, z_compensation }; +} + const std::string PrintStatistics::FilamentUsedG = "filament used [g]"; const std::string PrintStatistics::FilamentUsedGMask = "; filament used [g] ="; diff --git a/src/libslic3r/Print.hpp b/src/libslic3r/Print.hpp index aebb46899f..9d5217e534 100644 --- a/src/libslic3r/Print.hpp +++ b/src/libslic3r/Print.hpp @@ -401,7 +401,8 @@ public: // The slicing parameters are dependent on various configuration values // (layer height, first layer height, raft settings, print nozzle diameter etc). const SlicingParameters& slicing_parameters() const { return m_slicing_params; } - static SlicingParameters slicing_parameters(const DynamicPrintConfig &full_config, const ModelObject &model_object, float object_max_z); + // Orca: XYZ shrinkage compensation has introduced the const Vec3d &object_shrinkage_compensation parameter to the function below + static SlicingParameters slicing_parameters(const DynamicPrintConfig &full_config, const ModelObject &model_object, float object_max_z, const Vec3d &object_shrinkage_compensation); size_t num_printing_regions() const throw() { return m_shared_regions->all_regions.size(); } const PrintRegion& printing_region(size_t idx) const throw() { return *m_shared_regions->all_regions[idx].get(); } @@ -981,6 +982,12 @@ public: bool is_all_objects_are_short() const { return std::all_of(this->objects().begin(), this->objects().end(), [&](PrintObject* obj) { return obj->height() < scale_(this->config().nozzle_height.value); }); } + + // Orca: Implement prusa's filament shrink compensation approach + // Returns if all used filaments have same shrinkage compensations. + bool has_same_shrinkage_compensations() const; + // Returns scaling for each axis representing shrinkage compensations in each axis. + Vec3d shrinkage_compensation() const; protected: // Invalidates the step, and its depending steps in Print. diff --git a/src/libslic3r/PrintApply.cpp b/src/libslic3r/PrintApply.cpp index 232c86b9ec..3767ccd2a9 100644 --- a/src/libslic3r/PrintApply.cpp +++ b/src/libslic3r/PrintApply.cpp @@ -131,7 +131,8 @@ struct PrintObjectTrafoAndInstances }; // Generate a list of trafos and XY offsets for instances of a ModelObject -static std::vector print_objects_from_model_object(const ModelObject &model_object) +// Orca: Updated to include XYZ filament shrinkage compensation +static std::vector print_objects_from_model_object(const ModelObject &model_object, const Vec3d &shrinkage_compensation) { std::set trafos; PrintObjectTrafoAndInstances trafo; @@ -139,7 +140,10 @@ static std::vector print_objects_from_model_object int index = 0; for (ModelInstance *model_instance : model_object.instances) { if (model_instance->is_printable()) { - trafo.trafo = model_instance->get_matrix(); + // Orca: Updated with XYZ filament shrinkage compensation + Geometry::Transformation model_instance_transformation = model_instance->get_transformation(); + trafo.trafo = model_instance_transformation.get_matrix_with_applied_shrinkage_compensation(shrinkage_compensation); + auto shift = Point::new_scale(trafo.trafo.data()[12], trafo.trafo.data()[13]); // Reset the XY axes of the transformation. trafo.trafo.data()[12] = 0; @@ -1358,7 +1362,8 @@ Print::ApplyStatus Print::apply(const Model &model, DynamicPrintConfig new_full_ // Walk over all new model objects and check, whether there are matching PrintObjects. for (ModelObject *model_object : m_model.objects) { ModelObjectStatus &model_object_status = const_cast(model_object_status_db.reuse(*model_object)); - model_object_status.print_instances = print_objects_from_model_object(*model_object); + // Orca: Updated for XYZ filament shrink compensation + model_object_status.print_instances = print_objects_from_model_object(*model_object, this->shrinkage_compensation()); std::vector old; old.reserve(print_object_status_db.count(*model_object)); for (const PrintObjectStatus &print_object_status : print_object_status_db.get_range(*model_object)) diff --git a/src/libslic3r/PrintConfig.cpp b/src/libslic3r/PrintConfig.cpp index d3c3554a58..4803ba3b88 100644 --- a/src/libslic3r/PrintConfig.cpp +++ b/src/libslic3r/PrintConfig.cpp @@ -1907,7 +1907,7 @@ void PrintConfigDef::init_fff_params() def->set_default_value(new ConfigOptionFloats{ 0.4157 }); def = this->add("filament_shrink", coPercents); - def->label = L("Shrinkage"); + def->label = L("Shrinkage (XY)"); // xgettext:no-c-format, no-boost-format def->tooltip = L("Enter the shrinkage percentage that the filament will get after cooling (94% if you measure 94mm instead of 100mm)." " The part will be scaled in xy to compensate." @@ -1918,6 +1918,16 @@ void PrintConfigDef::init_fff_params() def->min = 10; def->mode = comAdvanced; def->set_default_value(new ConfigOptionPercents{ 100 }); + + def = this->add("filament_shrinkage_compensation_z", coPercents); + def->label = L("Shrinkage (Z)"); + def->tooltip = L("Enter the shrinkage percentage that the filament will get after cooling (94% if you measure 94mm instead of 100mm)." + " The part will be scaled in Z to compensate."); + def->sidetext = L("%"); + def->ratio_over = ""; + def->min = 10; + def->mode = comAdvanced; + def->set_default_value(new ConfigOptionPercents{ 100 }); def = this->add("filament_loading_speed", coFloats); def->label = L("Loading speed"); diff --git a/src/libslic3r/PrintConfig.hpp b/src/libslic3r/PrintConfig.hpp index 015befbd9f..c191e7ff57 100644 --- a/src/libslic3r/PrintConfig.hpp +++ b/src/libslic3r/PrintConfig.hpp @@ -1274,6 +1274,7 @@ PRINT_CONFIG_CLASS_DERIVED_DEFINE( ((ConfigOptionBool, independent_support_layer_height)) // SoftFever ((ConfigOptionPercents, filament_shrink)) + ((ConfigOptionPercents, filament_shrinkage_compensation_z)) ((ConfigOptionBool, gcode_label_objects)) ((ConfigOptionBool, exclude_object)) ((ConfigOptionBool, gcode_comments)) diff --git a/src/libslic3r/PrintObject.cpp b/src/libslic3r/PrintObject.cpp index 8674c1a4ea..7b16f8a697 100644 --- a/src/libslic3r/PrintObject.cpp +++ b/src/libslic3r/PrintObject.cpp @@ -2966,12 +2966,15 @@ void PrintObject::generate_support_preview() void PrintObject::update_slicing_parameters() { - if (!m_slicing_params.valid) - m_slicing_params = SlicingParameters::create_from_config( - this->print()->config(), m_config, this->model_object()->max_z(), this->object_extruders()); + // Orca: updated function call for XYZ shrinkage compensation + if (!m_slicing_params.valid) { + m_slicing_params = SlicingParameters::create_from_config(this->print()->config(), m_config, this->model_object()->max_z(), + this->object_extruders(), this->print()->shrinkage_compensation()); + } } -SlicingParameters PrintObject::slicing_parameters(const DynamicPrintConfig& full_config, const ModelObject& model_object, float object_max_z) +// Orca: XYZ shrinkage compensation has introduced the const Vec3d &object_shrinkage_compensation parameter to the function below +SlicingParameters PrintObject::slicing_parameters(const DynamicPrintConfig &full_config, const ModelObject &model_object, float object_max_z, const Vec3d &object_shrinkage_compensation) { PrintConfig print_config; PrintObjectConfig object_config; @@ -3006,7 +3009,7 @@ SlicingParameters PrintObject::slicing_parameters(const DynamicPrintConfig& full if (object_max_z <= 0.f) object_max_z = (float)model_object.raw_bounding_box().size().z(); - return SlicingParameters::create_from_config(print_config, object_config, object_max_z, object_extruders); + return SlicingParameters::create_from_config(print_config, object_config, object_max_z, object_extruders, object_shrinkage_compensation); } // returns 0-based indices of extruders used to print the object (without brim, support and other helper extrusions) @@ -3049,7 +3052,7 @@ bool PrintObject::update_layer_height_profile(const ModelObject &model_object, c // Must not be of even length. ((layer_height_profile.size() & 1) != 0 || // Last entry must be at the top of the object. - std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_parameters.object_print_z_max + slicing_parameters.object_print_z_min) > 1e-3)) + std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_parameters.object_print_z_uncompensated_max + slicing_parameters.object_print_z_min) > 1e-3)) layer_height_profile.clear(); if (layer_height_profile.empty() || layer_height_profile[1] != slicing_parameters.first_object_layer_height) { diff --git a/src/libslic3r/PrintObjectSlice.cpp b/src/libslic3r/PrintObjectSlice.cpp index 98f7d8b20e..21c9770663 100644 --- a/src/libslic3r/PrintObjectSlice.cpp +++ b/src/libslic3r/PrintObjectSlice.cpp @@ -449,22 +449,6 @@ static std::vector> slices_to_regions( }); } - // SoftFever: ported from SuperSlicer - // filament shrink - for (const std::unique_ptr& pr : print_object_regions.all_regions) { - if (pr.get()) { - std::vector& region_polys = slices_by_region[pr->print_object_region_id()]; - const size_t extruder_id = pr->extruder(FlowRole::frPerimeter) - 1; - double scale = print_config.filament_shrink.values[extruder_id] * 0.01; - if (scale != 1) { - scale = 1 / scale; - for (ExPolygons& polys : region_polys) - for (ExPolygon& poly : polys) - poly.scale(scale); - } - } - } - return slices_by_region; } diff --git a/src/libslic3r/Slicing.cpp b/src/libslic3r/Slicing.cpp index 636a3c471f..290871b914 100644 --- a/src/libslic3r/Slicing.cpp +++ b/src/libslic3r/Slicing.cpp @@ -60,10 +60,11 @@ coordf_t Slicing::max_layer_height_from_nozzle(const DynamicPrintConfig &print_c } SlicingParameters SlicingParameters::create_from_config( - const PrintConfig &print_config, - const PrintObjectConfig &object_config, - coordf_t object_height, - const std::vector &object_extruders) + const PrintConfig &print_config, + const PrintObjectConfig &object_config, + coordf_t object_height, + const std::vector &object_extruders, + const Vec3d &object_shrinkage_compensation) { coordf_t initial_layer_print_height = (print_config.initial_layer_print_height.value <= 0) ? object_config.layer_height.value : print_config.initial_layer_print_height.value; @@ -81,7 +82,10 @@ SlicingParameters SlicingParameters::create_from_config( params.first_print_layer_height = initial_layer_print_height; params.first_object_layer_height = initial_layer_print_height; params.object_print_z_min = 0.; - params.object_print_z_max = object_height; + // Orca: XYZ filament compensation + params.object_print_z_max = object_height * object_shrinkage_compensation.z(); + params.object_print_z_uncompensated_max = object_height; + params.object_shrinkage_compensation_z = object_shrinkage_compensation.z(); params.base_raft_layers = object_config.raft_layers.value; params.soluble_interface = soluble_interface; @@ -153,6 +157,7 @@ SlicingParameters SlicingParameters::create_from_config( coordf_t print_z = params.raft_contact_top_z + params.gap_raft_object; params.object_print_z_min = print_z; params.object_print_z_max += print_z; + params.object_print_z_uncompensated_max += print_z; } params.valid = true; @@ -225,10 +230,10 @@ std::vector layer_height_profile_from_ranges( lh_append(hi, height); } - if (coordf_t z = last_z(); z < slicing_params.object_print_z_height()) { + if (coordf_t z = last_z(); z < slicing_params.object_print_z_uncompensated_height()) { // Insert a step of normal layer height up to the object top. lh_append(z, slicing_params.layer_height); - lh_append(slicing_params.object_print_z_height(), slicing_params.layer_height); + lh_append(slicing_params.object_print_z_uncompensated_height(), slicing_params.layer_height); } return layer_height_profile; @@ -450,12 +455,12 @@ void adjust_layer_height_profile( std::pair z_span_variable = std::pair( slicing_params.first_object_layer_height_fixed() ? slicing_params.first_object_layer_height : 0., - slicing_params.object_print_z_height()); + slicing_params.object_print_z_uncompensated_height()); if (z < z_span_variable.first || z > z_span_variable.second) return; assert(layer_height_profile.size() >= 2); - assert(std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_params.object_print_z_height()) < EPSILON); + assert(std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_params.object_print_z_uncompensated_height()) < EPSILON); // 1) Get the current layer thickness at z. coordf_t current_layer_height = slicing_params.layer_height; @@ -616,7 +621,7 @@ void adjust_layer_height_profile( assert(layer_height_profile.size() > 2); assert(layer_height_profile.size() % 2 == 0); assert(layer_height_profile[0] == 0.); - assert(std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_params.object_print_z_height()) < EPSILON); + assert(std::abs(layer_height_profile[layer_height_profile.size() - 2] - slicing_params.object_print_z_uncompensated_height()) < EPSILON); #ifdef _DEBUG for (size_t i = 2; i < layer_height_profile.size(); i += 2) assert(layer_height_profile[i - 2] <= layer_height_profile[i]); @@ -739,6 +744,8 @@ std::vector generate_object_layers( out.push_back(print_z); } + // Orca: XYZ shrinkage compensation + const coordf_t shrinkage_compensation_z = slicing_params.object_shrinkage_compensation_z; size_t idx_layer_height_profile = 0; // loop until we have at least one layer and the max slice_z reaches the object height coordf_t slice_z = print_z + 0.5 * slicing_params.min_layer_height; @@ -747,17 +754,20 @@ std::vector generate_object_layers( if (idx_layer_height_profile < layer_height_profile.size()) { size_t next = idx_layer_height_profile + 2; for (;;) { - if (next >= layer_height_profile.size() || slice_z < layer_height_profile[next]) + // Orca: XYZ shrinkage compensation + if (next >= layer_height_profile.size() || slice_z < layer_height_profile[next] * shrinkage_compensation_z) break; idx_layer_height_profile = next; next += 2; } - coordf_t z1 = layer_height_profile[idx_layer_height_profile]; - coordf_t h1 = layer_height_profile[idx_layer_height_profile + 1]; + // Orca: XYZ shrinkage compensation + const coordf_t z1 = layer_height_profile[idx_layer_height_profile] * shrinkage_compensation_z; + const coordf_t h1 = layer_height_profile[idx_layer_height_profile + 1]; height = h1; if (next < layer_height_profile.size()) { - coordf_t z2 = layer_height_profile[next]; - coordf_t h2 = layer_height_profile[next + 1]; + // Orca: XYZ shrinkage compensation + const coordf_t z2 = layer_height_profile[next] * shrinkage_compensation_z; + const coordf_t h2 = layer_height_profile[next + 1]; height = lerp(h1, h2, (slice_z - z1) / (z2 - z1)); assert(height >= slicing_params.min_layer_height - EPSILON && height <= slicing_params.max_layer_height + EPSILON); } diff --git a/src/libslic3r/Slicing.hpp b/src/libslic3r/Slicing.hpp index c519a3d194..d6cd7dcb41 100644 --- a/src/libslic3r/Slicing.hpp +++ b/src/libslic3r/Slicing.hpp @@ -28,11 +28,13 @@ struct SlicingParameters { SlicingParameters() = default; + // Orca: XYZ filament compensation introduced object_shrinkage_compensation static SlicingParameters create_from_config( - const PrintConfig &print_config, - const PrintObjectConfig &object_config, - coordf_t object_height, - const std::vector &object_extruders); + const PrintConfig &print_config, + const PrintObjectConfig &object_config, + coordf_t object_height, + const std::vector &object_extruders, + const Vec3d &object_shrinkage_compensation); // Has any raft layers? bool has_raft() const { return raft_layers() > 0; } @@ -43,6 +45,10 @@ struct SlicingParameters // Height of the object to be printed. This value does not contain the raft height. coordf_t object_print_z_height() const { return object_print_z_max - object_print_z_min; } + + // Height of the object to be printed. This value does not contain the raft height. + // This value isn't scaled by shrinkage compensation in the Z-axis. + coordf_t object_print_z_uncompensated_height() const { return object_print_z_uncompensated_max - object_print_z_min; } bool valid { false }; @@ -95,7 +101,14 @@ struct SlicingParameters coordf_t raft_contact_top_z { 0 }; // In case of a soluble interface, object_print_z_min == raft_contact_top_z, otherwise there is a gap between the raft and the 1st object layer. coordf_t object_print_z_min { 0 }; + // This value of maximum print Z is scaled by shrinkage compensation in the Z-axis. coordf_t object_print_z_max { 0 }; + + // Orca: XYZ shrinkage compensation + // This value of maximum print Z isn't scaled by shrinkage compensation. + coordf_t object_print_z_uncompensated_max { 0 }; + // Scaling factor for compensating shrinkage in Z-axis. + coordf_t object_shrinkage_compensation_z { 0 }; }; static_assert(IsTriviallyCopyable::value, "SlicingParameters class is not POD (and it should be - see constructor)."); diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 5f45d9b1c5..551697e26f 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -666,8 +666,9 @@ void GLCanvas3D::LayersEditing::update_slicing_parameters() { if (m_slicing_parameters == nullptr) { m_slicing_parameters = new SlicingParameters(); - *m_slicing_parameters = PrintObject::slicing_parameters(*m_config, *m_model_object, m_object_max_z); + *m_slicing_parameters = PrintObject::slicing_parameters(*m_config, *m_model_object, m_object_max_z, m_shrinkage_compensation); } + } float GLCanvas3D::LayersEditing::thickness_bar_width(const GLCanvas3D & canvas) @@ -1489,6 +1490,11 @@ void GLCanvas3D::set_config(const DynamicPrintConfig* config) { m_config = config; m_layers_editing.set_config(config); + + // Orca: Filament shrinkage compensation + const Print *print = fff_print(); + if (print != nullptr) + m_layers_editing.set_shrinkage_compensation(fff_print()->shrinkage_compensation()); } void GLCanvas3D::set_process(BackgroundSlicingProcess *process) diff --git a/src/slic3r/GUI/GLCanvas3D.hpp b/src/slic3r/GUI/GLCanvas3D.hpp index 023e95a976..2d67401d5f 100644 --- a/src/slic3r/GUI/GLCanvas3D.hpp +++ b/src/slic3r/GUI/GLCanvas3D.hpp @@ -216,6 +216,9 @@ class GLCanvas3D }; static const float THICKNESS_BAR_WIDTH; + + // Orca: Shrinkage compensation + void set_shrinkage_compensation(const Vec3d &shrinkage_compensation) { m_shrinkage_compensation = shrinkage_compensation; }; private: bool m_enabled{ false }; @@ -229,6 +232,9 @@ class GLCanvas3D // Owned by LayersEditing. SlicingParameters* m_slicing_parameters{ nullptr }; std::vector m_layer_height_profile; + + // Orca: Shrinkage compensation to apply when we need to use object_max_z with Z compensation. + Vec3d m_shrinkage_compensation{ Vec3d::Ones() }; mutable float m_adaptive_quality{ 0.5f }; mutable HeightProfileSmoothingParams m_smooth_params; diff --git a/src/slic3r/GUI/Tab.cpp b/src/slic3r/GUI/Tab.cpp index 077a095993..8b6477fc4b 100644 --- a/src/slic3r/GUI/Tab.cpp +++ b/src/slic3r/GUI/Tab.cpp @@ -3245,6 +3245,7 @@ void TabFilament::build() optgroup->append_single_option_line("filament_density"); optgroup->append_single_option_line("filament_shrink"); + optgroup->append_single_option_line("filament_shrinkage_compensation_z"); optgroup->append_single_option_line("filament_cost"); //BBS optgroup->append_single_option_line("temperature_vitrification");