diff --git a/resources/ui_layout/print.ui b/resources/ui_layout/print.ui index cbc562bcf..9fff051cb 100644 --- a/resources/ui_layout/print.ui +++ b/resources/ui_layout/print.ui @@ -172,6 +172,7 @@ group:Brim line:Brim ears setting:brim_ears setting:width$3:brim_ears_max_angle + setting:width$3:brim_ears_detection_length setting:brim_ears_pattern end_line setting:brim_offset diff --git a/src/libslic3r/Preset.cpp b/src/libslic3r/Preset.cpp index b9c068d9f..b485e8ca6 100644 --- a/src/libslic3r/Preset.cpp +++ b/src/libslic3r/Preset.cpp @@ -512,6 +512,7 @@ const std::vector& Preset::print_options() "brim_width", "brim_width_interior", "brim_ears", + "brim_ears_detection_length", "brim_ears_max_angle", "brim_ears_pattern", "brim_offset", diff --git a/src/libslic3r/Print.cpp b/src/libslic3r/Print.cpp index f5d8420fa..1ead6ad7a 100644 --- a/src/libslic3r/Print.cpp +++ b/src/libslic3r/Print.cpp @@ -210,6 +210,7 @@ bool Print::invalidate_state_by_config_options(const std::vectorm_layers.front()->lslices) @@ -2299,21 +2301,37 @@ void Print::_make_brim_ears(const Flow &flow, const PrintObjectPtrs &objects, Ex object_islands.push_back(brim_offset==0?expoly:offset_ex(expoly, brim_offset)[0]); else object_islands.emplace_back(brim_offset == 0 ? to_expolygon(expoly.contour) : offset_ex(to_expolygon(expoly.contour), brim_offset)[0]); + if (!object->support_layers().empty()) { Polygons polys = object->support_layers().front()->support_fills.polygons_covered_by_spacing(float(SCALED_EPSILON)); for (Polygon poly : polys) for (ExPolygon& expoly2 : union_ex(Polygons{ poly })) - if (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0) - object_islands.push_back(brim_offset == 0 ? expoly2 : offset_ex(expoly2, brim_offset)[0]); - else - object_islands.emplace_back(brim_offset == 0 ? to_expolygon(expoly2.contour) : offset_ex(to_expolygon(expoly2.contour), brim_offset)[0]); + //don't put ears over supports unless it's 100% fill + if (object->config().support_material_solid_first_layer) { + if (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0) + object_islands.push_back(brim_offset == 0 ? expoly2 : offset_ex(expoly2, brim_offset)[0]); + else + object_islands.emplace_back(brim_offset == 0 ? to_expolygon(expoly2.contour) : offset_ex(to_expolygon(expoly2.contour), brim_offset)[0]); + } else { + unbrimmable_with_support.push_back(expoly2); + } } islands.reserve(islands.size() + object_islands.size() * object->m_instances.size()); for (const PrintInstance ©_pt : object->m_instances) for (const ExPolygon &poly : object_islands) { islands.push_back(poly); islands.back().translate(copy_pt.shift.x(), copy_pt.shift.y()); - for (const Point &p : poly.contour.convex_points(brim_config.brim_ears_max_angle.value * PI / 180.0)) { + Polygon decimated_polygon = poly.contour; + // brim_ears_detection_length codepath + if (object->config().brim_ears_detection_length.value > 0) { + //copy + decimated_polygon = poly.contour; + //decimate polygon + Points points = poly.contour.points; + points.push_back(points.front()); + decimated_polygon = Polygon(MultiPoint::_douglas_peucker(points, scale_(object->config().brim_ears_detection_length.value))); + } + for (const Point &p : decimated_polygon.convex_points(brim_config.brim_ears_max_angle.value * PI / 180.0)) { pt_ears.push_back(p); pt_ears.back() += (copy_pt.shift); } @@ -2325,17 +2343,16 @@ void Print::_make_brim_ears(const Flow &flow, const PrintObjectPtrs &objects, Ex //get the brimmable area (for the return value only) const size_t num_loops = size_t(floor((brim_config.brim_width.value - brim_config.brim_offset.value) / flow.spacing())); ExPolygons brimmable_areas; + Polygons contours; + Polygons holes; for (ExPolygon &expoly : islands) { for (Polygon poly : offset(expoly.contour, num_loops * flow.scaled_width(), jtSquare)) { - brimmable_areas.emplace_back(); - brimmable_areas.back().contour = poly; - brimmable_areas.back().contour.make_counter_clockwise(); - brimmable_areas.back().holes.push_back(expoly.contour); - brimmable_areas.back().holes.back().make_clockwise(); + contours.push_back(poly); } + holes.push_back(expoly.contour); } - brimmable_areas = union_ex(brimmable_areas); - brimmable_areas = diff_ex(brimmable_areas, unbrimmable, true); + brimmable_areas = diff_ex(union_(contours), union_(holes)); + brimmable_areas = diff_ex(brimmable_areas, unbrimmable_with_support, true); this->throw_if_canceled(); @@ -2396,8 +2413,7 @@ void Print::_make_brim_ears(const Flow &flow, const PrintObjectPtrs &objects, Ex ExPolygons new_brim_area = intersection_ex(brimmable_areas, mouse_ears_ex); unbrimmable.insert(unbrimmable.end(), new_brim_area.begin(), new_brim_area.end()); - } else { - + } else /* brim_config.brim_ears_pattern.value == InfillPattern::ipRectilinear */{ //create ear pattern coord_t size_ear = (scale_((brim_config.brim_width.value - brim_config.brim_offset.value)) - flow.scaled_spacing()); diff --git a/src/libslic3r/PrintConfig.cpp b/src/libslic3r/PrintConfig.cpp index 662b7b0b9..31ac6dafb 100644 --- a/src/libslic3r/PrintConfig.cpp +++ b/src/libslic3r/PrintConfig.cpp @@ -431,6 +431,7 @@ void PrintConfigDef::init_fff_params() def = this->add("brim_ears_max_angle", coFloat); def->label = L("Max angle"); + def->full_label = L("Brim ear max angle"); def->category = OptionCategory::skirtBrim; def->tooltip = L("Maximum angle to let a brim ear appear. \nIf set to 0, no brim will be created. \nIf set to ~178, brim will be created on everything but strait sections."); def->sidetext = L("°"); @@ -439,6 +440,17 @@ void PrintConfigDef::init_fff_params() def->mode = comAdvanced; def->set_default_value(new ConfigOptionFloat(125)); + def = this->add("brim_ears_detection_length", coFloat); + def->label = L("Detection radius"); + def->full_label = L("Brim ear detection length"); + def->category = OptionCategory::skirtBrim; + def->tooltip = L("The geometry will be decimated before dectecting sharp angles. This parameter indicate the minimum length of strait sections after decimation." + "\n0 to deactivate"); + def->sidetext = L("mm"); + def->min = 0; + def->mode = comAdvanced; + def->set_default_value(new ConfigOptionFloat(1)); + def = this->add("brim_ears_pattern", coEnum); def->label = L("Pattern"); def->full_label = L("Ear pattern"); @@ -450,6 +462,7 @@ void PrintConfigDef::init_fff_params() def->enum_values.push_back("rectilinear"); def->enum_labels.push_back(L("Concentric")); def->enum_labels.push_back(L("Rectilinear")); + def->mode = comExpert; def->set_default_value(new ConfigOptionEnum(ipConcentric)); def = this->add("brim_offset", coFloat); @@ -5072,6 +5085,7 @@ void PrintConfigDef::to_prusa(t_config_option_key& opt_key, std::string& value, "brim_inside_holes", "brim_width_interior", "brim_ears", +"brim_ears_detection_length", "brim_ears_max_angle", "brim_ears_pattern", "brim_offset", diff --git a/src/libslic3r/PrintConfig.hpp b/src/libslic3r/PrintConfig.hpp index 192e5c02a..e07915ae5 100644 --- a/src/libslic3r/PrintConfig.hpp +++ b/src/libslic3r/PrintConfig.hpp @@ -589,6 +589,7 @@ public: ConfigOptionFloat brim_width; ConfigOptionFloat brim_width_interior; ConfigOptionBool brim_ears; + ConfigOptionFloat brim_ears_detection_length; ConfigOptionFloat brim_ears_max_angle; ConfigOptionEnum brim_ears_pattern; ConfigOptionFloat brim_offset; @@ -655,6 +656,7 @@ protected: OPT_PTR(brim_width); OPT_PTR(brim_width_interior); OPT_PTR(brim_ears); + OPT_PTR(brim_ears_detection_length); OPT_PTR(brim_ears_max_angle); OPT_PTR(brim_ears_pattern); OPT_PTR(brim_offset); diff --git a/src/libslic3r/PrintObject.cpp b/src/libslic3r/PrintObject.cpp index a92cd1463..6da19c075 100644 --- a/src/libslic3r/PrintObject.cpp +++ b/src/libslic3r/PrintObject.cpp @@ -849,6 +849,7 @@ bool PrintObject::invalidate_state_by_config_options(const std::vectorinvalidate_step(psBrim);