diff options
author | supermerill <merill@free.fr> | 2022-08-04 03:09:43 +0300 |
---|---|---|
committer | supermerill <merill@free.fr> | 2022-08-04 03:09:43 +0300 |
commit | 572e3f970e78febddb73808eaa6c4a013ae5eed4 (patch) | |
tree | 0a6c67e1379856d13e7576e1378ab6a7232c93e9 | |
parent | 284773171247c4ab552984dedac8d7116ecb6c5f (diff) | |
parent | 8719d117fbe0aca921ee196b883a8085e6bb3691 (diff) |
fix brim, random seam, fuzzy skin with arachne
-rw-r--r-- | src/libslic3r/Brim.cpp | 81 | ||||
-rw-r--r-- | src/libslic3r/Fill/Fill.cpp | 14 | ||||
-rw-r--r-- | src/libslic3r/GCode/SeamPlacer.cpp | 2 | ||||
-rw-r--r-- | src/libslic3r/PerimeterGenerator.cpp | 59 | ||||
-rw-r--r-- | src/libslic3r/PerimeterGenerator.hpp | 2 |
5 files changed, 113 insertions, 45 deletions
diff --git a/src/libslic3r/Brim.cpp b/src/libslic3r/Brim.cpp index e3202d781..bf6e1de0d 100644 --- a/src/libslic3r/Brim.cpp +++ b/src/libslic3r/Brim.cpp @@ -714,6 +714,8 @@ ExtrusionEntityCollection make_brim(const Print &print, PrintTryCancel try_cance //superslicer void extrude_brim_from_tree(const Print& print, std::vector<std::vector<BrimLoop>>& loops, const Polygons& frontiers, const Flow& flow, ExtrusionEntityCollection& out, bool reversed/*= false*/) { + if (loops.empty()) + return; // nest contour loops (same as in perimetergenerator) for (int d = loops.size() - 1; d >= 1; --d) { @@ -981,10 +983,23 @@ void make_brim(const Print& print, const Flow& flow, const PrintObjectPtrs& obje for (PrintObject* object : objects) { ExPolygons object_islands; for (ExPolygon& expoly : object->layers().front()->lslices) - if (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0) - 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 (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0) { + if (brim_offset == 0) { + object_islands.push_back(expoly); + } else { + for (ExPolygon& grown_expoly : offset_ex(expoly, brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } + } else { + if (brim_offset == 0) { + object_islands.push_back(to_expolygon(expoly.contour)); + } else { + for (const ExPolygon& grown_expoly : offset_ex(to_expolygon(expoly.contour), brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } + } if (!object->support_layers().empty()) { Polygons polys = object->support_layers().front()->support_fills.polygons_covered_by_spacing(flow.spacing_ratio(), float(SCALED_EPSILON)); for (Polygon poly : polys) { @@ -1060,13 +1075,16 @@ void make_brim(const Print& print, const Flow& flow, const PrintObjectPtrs& obje for (ExPolygon& expoly : last_islands) { for (Polygon& big_contour : offset(expoly.contour, double(scaled_spacing), jtSquare)) { bigger_islands.emplace_back(); - bigger_islands.back().contour = big_contour.simplify(scaled_resolution / 10)[0]; + Polygons simplifiesd_big_contour = big_contour.simplify(scaled_resolution / 10); + if (simplifiesd_big_contour.size() == 1) { + bigger_islands.back().contour = simplifiesd_big_contour.front(); + } } } } else bigger_islands = islands; last_islands = union_ex(bigger_islands); for (ExPolygon& expoly : last_islands) { - loops[i].emplace_back(expoly.contour); + loops.back().emplace_back(expoly.contour); // buggy ////also add hole, in case of it's merged with a contour. <= HOW? if there's an island inside a hole! (in the same object) //for (Polygon &hole : expoly.holes) @@ -1105,18 +1123,38 @@ void make_brim_ears(const Print& print, const Flow& flow, const PrintObjectPtrs& for (PrintObject* object : objects) { ExPolygons object_islands; ExPolygons support_island; - for (const ExPolygon& expoly : object->layers().front()->lslices) - if (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0) - 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]); + for (const ExPolygon& expoly : object->layers().front()->lslices) { + if (brim_config.brim_inside_holes || brim_config.brim_width_interior > 0){ + if (brim_offset == 0) { + object_islands.push_back(expoly); + } else { + for (ExPolygon& grown_expoly : offset_ex(expoly, brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } + } else { + if (brim_offset == 0) { + object_islands.push_back(to_expolygon(expoly.contour)); + } else { + for (const ExPolygon& grown_expoly : offset_ex(to_expolygon(expoly.contour), brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } + } + } if (!object->support_layers().empty()) { Polygons polys = object->support_layers().front()->support_fills.polygons_covered_by_spacing(flow.spacing_ratio(), float(SCALED_EPSILON)); //put ears over supports unless it's more than 30% fill if (object->config().raft_first_layer_density.get_abs_value(1.) > 0.3) { for (Polygon poly : polys) { - object_islands.push_back(brim_offset == 0 ? ExPolygon{ poly } : offset_ex(Polygons{ poly }, brim_offset)[0]); + if (brim_offset == 0) { + object_islands.emplace_back(poly); + } else { + for (const ExPolygon& grown_expoly : offset_ex(Polygons{ poly }, brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } } } else { // offset2+- to avoid bits of brim inside the raft @@ -1278,15 +1316,28 @@ void make_brim_interior(const Print& print, const Flow& flow, const PrintObjectP coordf_t spacing; for (PrintObject* object : objects) { ExPolygons object_islands; - for (const ExPolygon& expoly : object->layers().front()->lslices) - object_islands.push_back(brim_offset == 0 ? expoly : offset_ex(ExPolygons{ expoly }, brim_offset)[0]); + for (const ExPolygon& expoly : object->layers().front()->lslices){ + if (brim_offset == 0) { + object_islands.push_back(expoly); + } else { + for (const ExPolygon& grown_expoly : offset_ex(ExPolygons{ expoly }, brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } + } if (!object->support_layers().empty()) { spacing = scaled(object->config().support_material_interface_spacing.value) + support_material_flow(object, float(print.get_first_layer_height())).scaled_width() * 1.5; Polygons polys = closing( object->support_layers().front()->support_fills.polygons_covered_by_spacing(flow.spacing_ratio(), float(SCALED_EPSILON)) , spacing); for (Polygon poly : polys) { - object_islands.push_back(brim_offset == 0 ? ExPolygon{ poly } : offset_ex(Polygons{ poly }, brim_offset)[0]); + if (brim_offset == 0) { + object_islands.emplace_back(poly); + } else { + for (const ExPolygon& grown_expoly : offset_ex(Polygons{ poly }, brim_offset)) { + object_islands.push_back(std::move(grown_expoly)); + } + } } } islands.reserve(islands.size() + object_islands.size() * object->instances().size()); diff --git a/src/libslic3r/Fill/Fill.cpp b/src/libslic3r/Fill/Fill.cpp index 216858073..51b4e6be5 100644 --- a/src/libslic3r/Fill/Fill.cpp +++ b/src/libslic3r/Fill/Fill.cpp @@ -127,24 +127,28 @@ std::vector<SurfaceFill> group_fills(const Layer &layer) params.density = 1.f; params.pattern = ipRectilinear; params.connection = region_config.infill_connection_solid.value; - if (surface.has_pos_top()) + if (surface.has_pos_top()) { params.connection = region_config.infill_connection_top.value; - if (surface.has_pos_bottom()) + } + if (surface.has_pos_bottom()) { params.connection = region_config.infill_connection_bottom.value; + } //FIXME for non-thick bridges, shall we allow a bottom surface pattern? if (is_bridge) { params.pattern = region_config.bridge_fill_pattern.value; params.connection = region_config.infill_connection_bridge.value; params.bridge_type = region_config.bridge_type.value; } - if (surface.has_pos_external() && !is_bridge) + if (surface.has_pos_external() && !is_bridge) { params.pattern = surface.has_pos_top() ? region_config.top_fill_pattern.value : region_config.bottom_fill_pattern.value; - else if (!is_bridge) + } else if (!is_bridge) { params.pattern = region_config.solid_fill_pattern.value; + } } else { - if (is_bridge) + if (is_bridge) { params.pattern = region_config.bridge_fill_pattern.value; params.connection = region_config.infill_connection_bridge.value; + } if (region_config.infill_dense.getBool() && region_config.fill_density < 40 && surface.maxNbSolidLayersOnTop == 1) { diff --git a/src/libslic3r/GCode/SeamPlacer.cpp b/src/libslic3r/GCode/SeamPlacer.cpp index 12730b84c..83751a3c2 100644 --- a/src/libslic3r/GCode/SeamPlacer.cpp +++ b/src/libslic3r/GCode/SeamPlacer.cpp @@ -322,7 +322,7 @@ void SeamPlacer::plan_perimeters(const std::vector<const ExtrusionEntity*> perim m_plan.resize(perimeters.size()); for (int i = 0; i < int(perimeters.size()); ++i) { - if (perimeters[i]->role() == erExternalPerimeter && perimeters[i]->is_loop()) { + if ((perimeters[i]->role() == erExternalPerimeter || seam_position == SeamPosition::spRandom) && perimeters[i]->is_loop()) { last_pos = this->calculate_seam( layer, seam_position, diff --git a/src/libslic3r/PerimeterGenerator.cpp b/src/libslic3r/PerimeterGenerator.cpp index 6fbcb80df..502622463 100644 --- a/src/libslic3r/PerimeterGenerator.cpp +++ b/src/libslic3r/PerimeterGenerator.cpp @@ -67,12 +67,14 @@ static void fuzzy_polygon(Polygon& poly, coordf_t fuzzy_skin_thickness, coordf_t dist_left_over = p0p1_size - dist_last_point; p0 = &p1; } - while (out.size() < 3) { - size_t point_idx = poly.size() - 2; - out.emplace_back(poly[point_idx]); - if (point_idx == 0) - break; - --point_idx; + if (out.size() < 3) { + size_t point_idx = std::max(size_t(0), poly.size() - 2); + while (out.size() < 3) { + out.emplace_back(poly[point_idx]); + if (point_idx == 0) + break; + --point_idx; + } } if (out.size() >= 3) poly.points = std::move(out); @@ -2387,16 +2389,26 @@ static void fuzzy_paths(ExtrusionPaths& paths, coordf_t fuzzy_skin_thickness, co const coordf_t range_random_point_dist = fuzzy_skin_point_dist / 2.; coordf_t dist_left_over = coordf_t(rand()) * (min_dist_between_points / 2) / double(RAND_MAX); // the distance to be traversed on the line before making the first new point - Point last_point = paths.back().last_point(); - bool is_loop = true; //always a loop currently paths.front().first_point() == last_point; - Point p0 = last_point; + const Point last_point = paths.back().last_point(); + //not always a loop, with arachne + bool is_loop = paths.front().first_point() == last_point; +#ifdef _DEBUG + assert(paths.back().last_point() == paths.front().first_point()); + for (int i = 1; i < paths.size(); i++) { + assert(paths[i - 1].last_point() == paths[i].first_point()); + } + if (is_loop) + assert(paths.front().polyline.points.front() == paths.back().polyline.points.back()); +#endif + Point p0 = is_loop ? last_point : paths.front().first_point(); + const Point* previous_point = is_loop ? &last_point : &paths.front().first_point(); for (ExtrusionPath &path : paths) { Points out; - size_t next_idx = 0; - if (p0 == path.polyline.points.front()) { - next_idx = 1; - } + size_t next_idx = 1; + // it always follow + assert(p0 == path.polyline.points.front()); out.reserve(path.polyline.points.size()); + out.push_back(*previous_point); for (; next_idx < path.polyline.points.size(); next_idx++) { Point& p1 = path.polyline.points[next_idx]; @@ -2415,21 +2427,22 @@ static void fuzzy_paths(ExtrusionPaths& paths, coordf_t fuzzy_skin_thickness, co dist_left_over = p0p1_size - dist_last_point; p0 = p1; } - while (path.polyline.size() < 3) { - size_t point_idx = path.polyline.size() - 2; - out.emplace_back(path.polyline.points[point_idx]); - if (point_idx == 0) - break; - --point_idx; - } - if (out.size() >= 3) - path.polyline.points = std::move(out); + path.polyline.points = std::move(out); + previous_point = &path.polyline.points.back(); } if (is_loop) { + assert(paths.front().polyline.points.front() != paths.back().polyline.points.back()); paths.back().polyline.points.push_back(paths.front().polyline.points.front()); + assert(paths.front().polyline.points.front() == paths.back().polyline.points.back()); } else { paths.back().polyline.points.push_back(last_point); } +#ifdef _DEBUG + assert(paths.back().last_point() == paths.front().first_point()); + for (int i = 1; i < paths.size(); i++) { + assert(paths[i - 1].last_point() == paths[i].first_point()); + } +#endif } ExtrusionEntityCollection PerimeterGenerator::_traverse_loops( @@ -2640,7 +2653,7 @@ ExtrusionEntityCollection PerimeterGenerator::_traverse_extrusions(std::vector<P double nozle_diameter = is_external ? this->ext_perimeter_flow.nozzle_diameter() : this->perimeter_flow.nozzle_diameter(); double fuzzy_skin_thickness = config->fuzzy_skin_thickness.get_abs_value(nozle_diameter); double fuzzy_skin_point_dist = config->fuzzy_skin_point_dist.get_abs_value(nozle_diameter); - fuzzy_paths(paths, scale_d(fuzzy_skin_thickness), scale_d(fuzzy_skin_point_dist)); + fuzzy_paths(paths, scale_d(fuzzy_skin_thickness), scale_d(fuzzy_skin_point_dist)); } // Append paths to collection. diff --git a/src/libslic3r/PerimeterGenerator.hpp b/src/libslic3r/PerimeterGenerator.hpp index 6d0b62796..d7401f3fb 100644 --- a/src/libslic3r/PerimeterGenerator.hpp +++ b/src/libslic3r/PerimeterGenerator.hpp @@ -133,7 +133,7 @@ private: ClipperLib_Z::Paths _lower_slices_bridge_speed_big_clipperpaths; ExtrusionPaths create_overhangs(const Polyline& loop_polygons, ExtrusionRole role, bool is_external) const; - ExtrusionPaths PerimeterGenerator::create_overhangs(const ClipperLib_Z::Path& loop_polygons, ExtrusionRole role, bool is_external) const; + ExtrusionPaths create_overhangs(const ClipperLib_Z::Path& loop_polygons, ExtrusionRole role, bool is_external) const; // transform loops into ExtrusionEntityCollection, adding also thin walls into it. ExtrusionEntityCollection _traverse_loops(const PerimeterGeneratorLoops &loops, ThickPolylines &thin_walls) const; |