Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/supermerill/SuperSlicer.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorsupermerill <merill@free.fr>2022-02-16 05:20:55 +0300
committersupermerill <merill@free.fr>2022-02-17 01:59:42 +0300
commitbc5979afef6fa6b7ad4b7530946252c36e0df852 (patch)
tree2646b3e489b6ce5282a94ae8afeba57e2671b51e
parentf5afec0a5edc8109244b416d271a3946baf50f32 (diff)
Fix raft flow problem & raft double sheath, also
Now sheath infill is printed just after the perimeter sheath remove support_material_solid_first_layer as there is no a % and there is always a sheath supermerill/SuperSlicer#2394 supermerill/SuperSlicer#2400
-rw-r--r--resources/ui_layout/print.ui1
-rw-r--r--src/libslic3r/Brim.cpp4
-rw-r--r--src/libslic3r/ExtrusionEntityCollection.hpp17
-rw-r--r--src/libslic3r/Fill/FillBase.cpp89
-rw-r--r--src/libslic3r/Fill/FillBase.hpp22
-rw-r--r--src/libslic3r/Fill/FillRectilinear.cpp83
-rw-r--r--src/libslic3r/Fill/FillRectilinear.hpp11
-rw-r--r--src/libslic3r/Preset.cpp1
-rw-r--r--src/libslic3r/PrintConfig.cpp13
-rw-r--r--src/libslic3r/PrintConfig.hpp1
-rw-r--r--src/libslic3r/PrintObject.cpp3
-rw-r--r--src/libslic3r/SupportMaterial.cpp203
12 files changed, 231 insertions, 217 deletions
diff --git a/resources/ui_layout/print.ui b/resources/ui_layout/print.ui
index 6ed8eaabc..22ff7a78b 100644
--- a/resources/ui_layout/print.ui
+++ b/resources/ui_layout/print.ui
@@ -214,7 +214,6 @@ group:Support material
setting:support_material_threshold
setting:support_material_enforce_layers
group:Raft
- setting:support_material_solid_first_layer
setting:raft_layers
line:First layer
setting:raft_first_layer_density
diff --git a/src/libslic3r/Brim.cpp b/src/libslic3r/Brim.cpp
index 2f265fc4e..2208af917 100644
--- a/src/libslic3r/Brim.cpp
+++ b/src/libslic3r/Brim.cpp
@@ -988,8 +988,8 @@ void make_brim_ears(const Print& print, const Flow& flow, const PrintObjectPtrs&
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 100% fill
- if (object->config().support_material_solid_first_layer) {
+ //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]);
}
diff --git a/src/libslic3r/ExtrusionEntityCollection.hpp b/src/libslic3r/ExtrusionEntityCollection.hpp
index ac21bba48..b84f035d1 100644
--- a/src/libslic3r/ExtrusionEntityCollection.hpp
+++ b/src/libslic3r/ExtrusionEntityCollection.hpp
@@ -175,6 +175,23 @@ public:
virtual void use(const ExtrusionEntityCollection &coll) override;
};
+#ifdef _DEBUG
+class TestCollection : public ExtrusionVisitorRecursiveConst {
+public:
+ virtual void default_use(const ExtrusionEntity& entity) override {
+ assert(entity.as_polyline().size() > 0);
+ }
+ virtual void use(const ExtrusionEntityCollection& coll) override {
+ for (const ExtrusionEntity* entity : coll.entities()) {
+ assert(entity);
+ std::cout << "entity at " << ((uint64_t)(void*)entity) << "\n";
+ entity->visit(*this);
+ }
+
+ }
+};
+#endif
+
} // namespace Slic3r
#endif
diff --git a/src/libslic3r/Fill/FillBase.cpp b/src/libslic3r/Fill/FillBase.cpp
index a3e237135..e0d838650 100644
--- a/src/libslic3r/Fill/FillBase.cpp
+++ b/src/libslic3r/Fill/FillBase.cpp
@@ -53,7 +53,7 @@ Fill* Fill::new_from_type(const InfillPattern type)
case ipSmooth: return new FillSmooth();
case ipSmoothTriple: return new FillSmoothTriple();
case ipSmoothHilbert: return new FillSmoothHilbert();
- case ipRectiWithPerimeter: return new FillRectilinearPeri();
+ case ipRectiWithPerimeter: return new FillWithPerimeter(new FillRectilinear());
case ipSawtooth: return new FillRectilinearSawtooth();
case ipAdaptiveCubic: return new FillAdaptive::Filler();
case ipSupportCubic: return new FillAdaptive::Filler();
@@ -3565,4 +3565,91 @@ void Fill::connect_infill(Polylines&& infill_ordered, const ExPolygon& boundary,
}
}
+
+void
+FillWithPerimeter::fill_surface_extrusion(const Surface* surface, const FillParams& params, ExtrusionEntitiesPtr& out) const
+{
+ ExtrusionEntityCollection* eecroot = new ExtrusionEntityCollection();
+ //you don't want to sort the extrusions: big infill first, small second
+ eecroot->set_can_sort_reverse(true, true);
+
+ //set Fill params
+ *infill = *this;
+
+ // === extrude perimeter & associated surface at the same time, in the right order ===
+ //generate perimeter:
+ ExPolygons path_perimeter = offset2_ex(ExPolygons{ surface->expolygon },
+ scale_d(-this->get_spacing()), scale_d(this->get_spacing() / 2),
+ ClipperLib::jtMiter, scale_d(this->get_spacing()) * 10);
+ //fix a bug that can happens when (positive) offsetting with a big miter limit and two island merge. See https://github.com/supermerill/SuperSlicer/issues/609
+ path_perimeter = intersection_ex(path_perimeter, offset_ex(surface->expolygon, scale_d(-this->get_spacing() / 2)));
+ for (ExPolygon& expolygon : path_perimeter) {
+ ExtrusionEntityCollection* eec_expoly = path_perimeter.size() == 1 ? eecroot : new ExtrusionEntityCollection();
+ if (path_perimeter.size() > 1) eecroot->append(ExtrusionEntitiesPtr{ eec_expoly });
+ eec_expoly->set_can_sort_reverse(false, false);
+
+ //create perimeter
+ expolygon.contour.make_counter_clockwise();
+ Polylines polylines_peri = { expolygon.contour.split_at_index(0) };
+ for (Polygon hole : expolygon.holes) {
+ hole.make_clockwise();
+ polylines_peri.push_back(hole.split_at_index(0));
+ }
+ if (!polylines_peri.empty()) {
+ // Save into layer.
+ ExtrusionEntityCollection* eec_peri = new ExtrusionEntityCollection();
+ /// pass the no_sort attribute to the extrusion path
+ eec_peri->set_can_sort_reverse(!this->no_sort(), !this->no_sort());
+ /// add it into the collection
+ eec_expoly->append(ExtrusionEntitiesPtr{ eec_peri });
+ //get the role
+ ExtrusionRole good_role = getRoleFromSurfaceType(params, surface);
+ /// push the path
+ extrusion_entities_append_paths(
+ eec_peri->set_entities(),
+ polylines_peri,
+ good_role,
+ params.flow.mm3_per_mm() * params.flow_mult,
+ params.flow.width() * params.flow_mult,
+ params.flow.height());
+
+ // === extrude infill ===
+ //50% overlap with the new perimeter
+ ExPolygons path_inner = offset2_ex(ExPolygons{ expolygon }, scale_d(-this->get_spacing() * (ratio_fill_inside+0.5)), scale_d(this->get_spacing()/2));
+ for (ExPolygon& expolygon : path_inner) {
+ Surface surfInner(*surface, expolygon);
+ Polylines polys_infill = infill->fill_surface(&surfInner, params);
+ if (!polys_infill.empty()) {
+ // Save into layer.
+ ExtrusionEntityCollection* eec_infill = new ExtrusionEntityCollection();
+ /// pass the no_sort attribute to the extrusion path
+ eec_infill->set_can_sort_reverse(!this->no_sort(), !this->no_sort());
+ /// add it into the collection
+ eec_expoly->append(ExtrusionEntitiesPtr{ eec_infill });
+ //get the role
+ ExtrusionRole good_role = getRoleFromSurfaceType(params, surface);
+ /// push the path
+ extrusion_entities_append_paths(
+ eec_infill->set_entities(),
+ polys_infill,
+ good_role,
+ params.flow.mm3_per_mm() * params.flow_mult,
+ params.flow.width() * params.flow_mult,
+ params.flow.height());
+ }
+ }
+ }
+
+ }
+
+ // === end ===
+ if (!eecroot->empty()) {
+ out.push_back(eecroot);
+ } else {
+ delete eecroot;
+ }
+
+}
+
+
} // namespace Slic3r
diff --git a/src/libslic3r/Fill/FillBase.hpp b/src/libslic3r/Fill/FillBase.hpp
index fe1ea4c7c..76ca17de0 100644
--- a/src/libslic3r/Fill/FillBase.hpp
+++ b/src/libslic3r/Fill/FillBase.hpp
@@ -209,6 +209,28 @@ namespace NaiveConnect {
void connect_infill(Polylines&& infill_ordered, const ExPolygon& boundary, Polylines& polylines_out, const double spacing, const FillParams& params);
}
+// composite filler
+class FillWithPerimeter : public Fill
+{
+public:
+ std::unique_ptr<Fill> infill{ nullptr };
+ float ratio_fill_inside = 0.f;
+ FillWithPerimeter() : Fill() {}
+ FillWithPerimeter(Fill* parent) : infill(parent), Fill() {}
+ FillWithPerimeter(const FillWithPerimeter& o) : infill(o.infill.get() ? o.infill->clone() : nullptr), ratio_fill_inside(o.ratio_fill_inside), Fill(o) {}
+ Fill* clone() const override {
+ FillWithPerimeter* n = new FillWithPerimeter(*this);
+ if (infill != nullptr) {
+ n->infill.reset(infill->clone());
+ }
+ return n;
+ };
+ ~FillWithPerimeter() override = default;
+ //Polylines fill_surface(const Surface *surface, const FillParams &params);
+ void fill_surface_extrusion(const Surface* surface, const FillParams& params, ExtrusionEntitiesPtr& out) const override;
+
+};
+
class ExtrusionSetRole : public ExtrusionVisitor {
ExtrusionRole new_role;
public:
diff --git a/src/libslic3r/Fill/FillRectilinear.cpp b/src/libslic3r/Fill/FillRectilinear.cpp
index e04c63d8c..72d86a73b 100644
--- a/src/libslic3r/Fill/FillRectilinear.cpp
+++ b/src/libslic3r/Fill/FillRectilinear.cpp
@@ -3247,89 +3247,6 @@ Polylines FillSupportBase::fill_surface(const Surface *surface, const FillParams
return polylines_out;
}
-void
-FillRectilinearPeri::fill_surface_extrusion(const Surface *surface, const FillParams &params, ExtrusionEntitiesPtr &out) const
-{
- ExtrusionEntityCollection *eecroot = new ExtrusionEntityCollection();
- //you don't want to sort the extrusions: big infill first, small second
- eecroot->set_can_sort_reverse(false, false);
-
- // === extrude perimeter ===
- Polylines polylines_1;
- //generate perimeter:
- ExPolygons path_perimeter = offset2_ex(ExPolygons{ surface->expolygon },
- scale_d(-this->get_spacing()), scale_d(this->get_spacing() / 2),
- ClipperLib::jtMiter, scale_d(this->get_spacing()) * 10);
- //fix a bug that can happens when (positive) offsetting with a big miter limit and two island merge. See https://github.com/supermerill/SuperSlicer/issues/609
- path_perimeter = intersection_ex(path_perimeter, offset_ex(surface->expolygon, scale_d(-this->get_spacing() / 2)));
- for (ExPolygon &expolygon : path_perimeter) {
- expolygon.contour.make_counter_clockwise();
- polylines_1.push_back(expolygon.contour.split_at_index(0));
- for (Polygon hole : expolygon.holes) {
- hole.make_clockwise();
- polylines_1.push_back(hole.split_at_index(0));
- }
- }
-
- if (!polylines_1.empty()) {
- // Save into layer.
- ExtrusionEntityCollection *eec = new ExtrusionEntityCollection();
- /// pass the no_sort attribute to the extrusion path
- eec->set_can_sort_reverse(!this->no_sort(), !this->no_sort());
- /// add it into the collection
- eecroot->append(ExtrusionEntitiesPtr{ eec });
- //get the role
- ExtrusionRole good_role = getRoleFromSurfaceType(params, surface);
- /// push the path
- extrusion_entities_append_paths(
- eec->set_entities(),
- polylines_1,
- good_role,
- params.flow.mm3_per_mm() * params.flow_mult,
- params.flow.width() * params.flow_mult,
- params.flow.height());
- }
-
-
- // === extrude dense infill ===
- Polylines polylines_2;
- bool canFill = true;
- //50% overlap with the new perimeter
- ExPolygons path_inner = offset2_ex(ExPolygons{ surface->expolygon }, scale_d(-this->get_spacing() * 1.5), scale_d(this->get_spacing()));
- for (ExPolygon &expolygon : path_inner) {
- Surface surfInner(*surface, expolygon);
- if (!fill_surface_by_lines(&surfInner, params, 0.f, 0.f, polylines_2)) {
- printf("FillRectilinear2::fill_surface() failed to fill a region.\n");
- canFill = false;
- }
- }
- if (canFill && !polylines_2.empty()) {
- // Save into layer.
- ExtrusionEntityCollection *eec = new ExtrusionEntityCollection();
- /// pass the no_sort attribute to the extrusion path
- eec->set_can_sort_reverse(!this->no_sort(), !this->no_sort());
- /// add it into the collection
- eecroot->append(ExtrusionEntitiesPtr{ eec });
- //get the role
- ExtrusionRole good_role = getRoleFromSurfaceType(params, surface);
- /// push the path
- extrusion_entities_append_paths(
- eec->set_entities(),
- polylines_2,
- good_role,
- params.flow.mm3_per_mm() * params.flow_mult,
- params.flow.width() * params.flow_mult,
- params.flow.height());
- }
-
- // === end ===
- if (!eecroot->empty()) {
- out.push_back(eecroot);
- } else {
- delete eecroot;
- }
-
-}
/* Returns a float uniformly distributed in the range [0..1.0) using the given integer as the seed
*
diff --git a/src/libslic3r/Fill/FillRectilinear.hpp b/src/libslic3r/Fill/FillRectilinear.hpp
index 483a7e5a0..0c7eee3c8 100644
--- a/src/libslic3r/Fill/FillRectilinear.hpp
+++ b/src/libslic3r/Fill/FillRectilinear.hpp
@@ -113,17 +113,6 @@ protected:
float _layer_angle(size_t idx) const override { return 0.f; }
};
-class FillRectilinearPeri : public FillRectilinear
-{
-public:
- Fill* clone() const override { return new FillRectilinearPeri(*this); };
- ~FillRectilinearPeri() override = default;
- //Polylines fill_surface(const Surface *surface, const FillParams &params);
- void fill_surface_extrusion(const Surface* surface, const FillParams& params, ExtrusionEntitiesPtr& out) const override;
-
-};
-
-
class FillScatteredRectilinear : public FillRectilinear
{
public:
diff --git a/src/libslic3r/Preset.cpp b/src/libslic3r/Preset.cpp
index 14261db65..f5778501d 100644
--- a/src/libslic3r/Preset.cpp
+++ b/src/libslic3r/Preset.cpp
@@ -652,7 +652,6 @@ static std::vector<std::string> s_Preset_print_options {
"compatible_printers", "compatible_printers_condition", "inherits",
"infill_dense", "infill_dense_algo",
"no_perimeter_unsupported_algo",
- "support_material_solid_first_layer",
"exact_last_layer_height",
"perimeter_loop",
"perimeter_loop_seam",
diff --git a/src/libslic3r/PrintConfig.cpp b/src/libslic3r/PrintConfig.cpp
index 6626cefa6..d52c00c20 100644
--- a/src/libslic3r/PrintConfig.cpp
+++ b/src/libslic3r/PrintConfig.cpp
@@ -3963,13 +3963,6 @@ void PrintConfigDef::init_fff_params()
def->mode = comExpert;
def->set_default_value(new ConfigOptionFloat(3.));
- def = this->add("support_material_solid_first_layer", coBool);
- def->label = L("Solid first layer");
- def->category = OptionCategory::support;
- def->tooltip = L("Use a solid layer instead of a raft for the layer that touches the build plate.");
- def->mode = comAdvanced;
- def->set_default_value(new ConfigOptionBool(false));
-
def = this->add("raft_layers", coInt);
def->label = L("Raft layers");
def->category = OptionCategory::support;
@@ -6808,6 +6801,11 @@ void PrintConfigDef::handle_legacy(t_config_option_key &opt_key, std::string &va
opt_key = "";
return;
}
+ //in ps 2.4, the raft_first_layer_density is now more powerful than the support_material_solid_first_layer, also it always does the perimeter.
+ if ("support_material_solid_first_layer" == opt_key) {
+ opt_key = "raft_first_layer_density";
+ value = "100";
+ }
//prusa
if ("gcode_flavor" == opt_key) {
@@ -7033,7 +7031,6 @@ std::unordered_set<std::string> prusa_export_to_remove_keys = {
"support_material_contact_distance_type",
"support_material_interface_acceleration",
"support_material_interface_pattern",
-"support_material_solid_first_layer",
"thin_perimeters_all",
"thin_perimeters",
"thin_walls_acceleration",
diff --git a/src/libslic3r/PrintConfig.hpp b/src/libslic3r/PrintConfig.hpp
index 30d1b0423..04624a731 100644
--- a/src/libslic3r/PrintConfig.hpp
+++ b/src/libslic3r/PrintConfig.hpp
@@ -728,7 +728,6 @@ PRINT_CONFIG_CLASS_DEFINE(
((ConfigOptionFloat, support_material_spacing))
((ConfigOptionFloatOrPercent, support_material_speed))
((ConfigOptionEnum<SupportMaterialStyle>, support_material_style))
- ((ConfigOptionBool, support_material_solid_first_layer))
((ConfigOptionBool, support_material_synchronize_layers))
// Overhang angle threshold.
((ConfigOptionInt, support_material_threshold))
diff --git a/src/libslic3r/PrintObject.cpp b/src/libslic3r/PrintObject.cpp
index 698bf4677..cd3c9f4b9 100644
--- a/src/libslic3r/PrintObject.cpp
+++ b/src/libslic3r/PrintObject.cpp
@@ -818,8 +818,7 @@ bool PrintObject::invalidate_state_by_config_options(
|| opt_key == "support_material_closing_radius"
|| opt_key == "support_material_synchronize_layers"
|| opt_key == "support_material_threshold"
- || opt_key == "support_material_with_sheath"
- || opt_key == "support_material_solid_first_layer") {
+ || opt_key == "support_material_with_sheath") {
steps.emplace_back(posSupportMaterial);
} else if (opt_key == "bottom_solid_layers") {
steps.emplace_back(posPrepareInfill);
diff --git a/src/libslic3r/SupportMaterial.cpp b/src/libslic3r/SupportMaterial.cpp
index 87d99e278..b64663f63 100644
--- a/src/libslic3r/SupportMaterial.cpp
+++ b/src/libslic3r/SupportMaterial.cpp
@@ -334,7 +334,7 @@ PrintObjectSupportMaterial::PrintObjectSupportMaterial(const PrintObject *object
m_support_params.support_material_flow = support_material_flow(object, float(slicing_params.layer_height));
m_support_params.support_material_interface_flow = support_material_interface_flow(object, float(slicing_params.layer_height));
m_support_params.support_layer_height_min = 0.01;
- m_support_params.raft_bridge_flow_ratio = object->print()->default_region_config().bridge_flow_ratio.value;
+ m_support_params.raft_bridge_flow_ratio = object->print()->default_region_config().bridge_flow_ratio.get_abs_value(1.);
// Calculate a minimum support layer height as a minimum over all extruders, but not smaller than 10um.
m_support_params.support_layer_height_min = 1000000.;
@@ -3303,59 +3303,59 @@ static inline void fill_expolygons_generate_paths(
fill_params.config = &region_config;
fill_expolygons_generate_paths(dst, std::move(expolygons), filler, fill_params, density, role, flow, spacing);
}
-
-static inline void fill_expolygons_with_sheath_generate_paths(
- ExtrusionEntitiesPtr &dst,
- const Polygons &polygons,
- Fill *filler,
- float density,
- ExtrusionRole role,
- const Flow &flow,
- coordf_t spacing,
- bool with_sheath,
- bool no_sort,
- const PrintRegionConfig& region_config)
-{
- if (polygons.empty())
- return;
-
- if (! with_sheath) {
- fill_expolygons_generate_paths(dst, closing_ex(polygons, float(SCALED_EPSILON)), filler, density, role, flow, spacing, region_config);
- return;
- }
-
- FillParams fill_params;
- fill_params.density = density;
- fill_params.dont_adjust = true;
- fill_params.config = &region_config;
-
- // Clip the sheath path to avoid the extruder to get exactly on the first point of the loop.
- double clip_length = spacing * 0.15;
-
- for (ExPolygon &expoly : closing_ex(polygons, float(SCALED_EPSILON), float(SCALED_EPSILON + 0.5*flow.scaled_width()))) {
- // Don't reorder the skirt and its infills.
- std::unique_ptr<ExtrusionEntityCollection> eec;
- if (no_sort) {
- eec = std::make_unique<ExtrusionEntityCollection>();
- eec->set_can_sort_reverse(false, true);
- }
- ExtrusionEntitiesPtr &out = no_sort ? eec->set_entities() : dst;
- // Draw the perimeters.
- Polylines polylines;
- polylines.reserve(expoly.holes.size() + 1);
- for (size_t i = 0; i <= expoly.holes.size(); ++ i) {
- Polyline pl(i == 0 ? expoly.contour.points : expoly.holes[i - 1].points);
- pl.points.emplace_back(pl.points.front());
- pl.clip_end(clip_length);
- polylines.emplace_back(std::move(pl));
- }
- extrusion_entities_append_paths(out, polylines, erSupportMaterial, flow.mm3_per_mm(), flow.width(), flow.height());
- // Fill in the rest.
- fill_expolygons_generate_paths(out, offset_ex(expoly, float(-0.4 * spacing)), filler, fill_params, density, role, flow, spacing);
- if (no_sort && ! eec->empty())
- dst.emplace_back(eec.release());
- }
-}
+// now use FillWithPerimeter
+//static inline void fill_expolygons_with_sheath_generate_paths(
+// ExtrusionEntitiesPtr &dst,
+// const Polygons &polygons,
+// Fill *filler,
+// float density,
+// ExtrusionRole role,
+// const Flow &flow,
+// coordf_t spacing,
+// bool with_sheath,
+// bool no_sort,
+// const PrintRegionConfig& region_config)
+//{
+// if (polygons.empty())
+// return;
+//
+// if (! with_sheath) {
+// fill_expolygons_generate_paths(dst, closing_ex(polygons, float(SCALED_EPSILON)), filler, density, role, flow, spacing, region_config);
+// return;
+// }
+//
+// FillParams fill_params;
+// fill_params.density = density;
+// fill_params.dont_adjust = true;
+// fill_params.config = &region_config;
+//
+// // Clip the sheath path to avoid the extruder to get exactly on the first point of the loop.
+// double clip_length = spacing * 0.15;
+//
+// for (ExPolygon &expoly : closing_ex(polygons, float(SCALED_EPSILON), float(SCALED_EPSILON + 0.5*flow.scaled_width()))) {
+// // Don't reorder the skirt and its infills.
+// std::unique_ptr<ExtrusionEntityCollection> eec;
+// if (no_sort) {
+// eec = std::make_unique<ExtrusionEntityCollection>();
+// eec->set_can_sort_reverse(false, true);
+// }
+// ExtrusionEntitiesPtr &out = no_sort ? eec->set_entities() : dst;
+// // Draw the perimeters.
+// Polylines polylines;
+// polylines.reserve(expoly.holes.size() + 1);
+// for (size_t i = 0; i <= expoly.holes.size(); ++ i) {
+// Polyline pl(i == 0 ? expoly.contour.points : expoly.holes[i - 1].points);
+// pl.points.emplace_back(pl.points.front());
+// pl.clip_end(clip_length);
+// polylines.emplace_back(std::move(pl));
+// }
+// extrusion_entities_append_paths(out, polylines, erSupportMaterial, flow.mm3_per_mm(), flow.width(), flow.height());
+// // Fill in the rest.
+// fill_expolygons_generate_paths(out, offset_ex(expoly, float(-0.4 * spacing)), filler, fill_params, density, role, flow, spacing);
+// if (no_sort && ! eec->empty())
+// dst.emplace_back(eec.release());
+// }
+//}
// Support layers, partially processed.
struct MyLayerExtruded
@@ -4015,7 +4015,10 @@ void PrintObjectSupportMaterial::generate_toolpaths(
std::unique_ptr<Fill> filler_interface = std::unique_ptr<Fill>(Fill::new_from_type(m_support_params.contact_fill_pattern)); //m_support_params.interface_fill_pattern)); FIXME choose
std::unique_ptr<Fill> filler_support = std::unique_ptr<Fill>(Fill::new_from_type(m_support_params.base_fill_pattern));
- std::unique_ptr<Fill> filler_dense = std::unique_ptr<Fill>(Fill::new_from_type(ipRectiWithPerimeter));
+ std::unique_ptr<FillWithPerimeter> filler_support_with_sheath = std::make_unique<FillWithPerimeter>((Fill::new_from_type(m_support_params.base_fill_pattern)));
+ filler_support_with_sheath->ratio_fill_inside = 0.2f;
+ std::unique_ptr<FillWithPerimeter> filler_dense = std::make_unique<FillWithPerimeter>((Fill::new_from_type(ipRectilinear)));
+ filler_dense->ratio_fill_inside = 0.2f;
filler_interface->set_bounding_box(bbox_object);
filler_support->set_bounding_box(bbox_object);
@@ -4028,19 +4031,18 @@ void PrintObjectSupportMaterial::generate_toolpaths(
if (! to_infill_polygons.empty()) {
assert(! raft_layer.bridging);
Flow flow(float(m_support_params.support_material_flow.width()), float(raft_layer.height), m_support_params.support_material_flow.nozzle_diameter(), m_support_params.support_material_flow.spacing_ratio());
- Fill * filler = filler_support.get();
+ Fill * filler = m_support_params.with_sheath ? filler_support_with_sheath.get() : filler_support.get();
filler->angle = raft_angle_base;
filler->link_max_length = scale_t(m_support_params.support_material_flow.spacing() * link_max_length_factor / m_support_params.support_density);
- fill_expolygons_with_sheath_generate_paths(
+ fill_expolygons_generate_paths(
// Destination
support_layer.support_fills.set_entities(),
// Regions to fill
- to_infill_polygons,
+ closing_ex(to_infill_polygons, float(SCALED_EPSILON), float(SCALED_EPSILON + 0.5 * flow.scaled_width())),
// Filler and its parameters
filler, float(m_support_params.support_density),
// Extrusion parameters
erSupportMaterial, flow, m_support_params.support_material_flow.spacing(),
- m_support_params.with_sheath, false,
m_object->print()->default_region_config());
}
}
@@ -4048,17 +4050,12 @@ void PrintObjectSupportMaterial::generate_toolpaths(
Fill *filler = filler_interface.get();
Flow flow = m_support_params.first_layer_flow;
float density = 0.f;
- coordf_t spacing = 0.f;
+ double spacing = 0.f;
if (support_layer_id == 0) {
// Base flange.
- if (this->m_object_config->support_material_solid_first_layer.value) {
- filler = filler_dense.get();
- density = 1.f;
- filler->angle = 0;
- } else {
- filler->angle = raft_angle_1st_layer;
- density = float(m_object_config->raft_first_layer_density.value * 0.01);
- }
+ filler = filler_dense.get();
+ filler->angle = raft_angle_1st_layer;
+ density = float(m_object_config->raft_first_layer_density.value * 0.01);
spacing = m_support_params.first_layer_flow.spacing();
} else if (support_layer_id >= m_slicing_params.base_raft_layers) {
filler->angle = raft_angle_interface;
@@ -4073,18 +4070,16 @@ void PrintObjectSupportMaterial::generate_toolpaths(
density = float(m_support_params.interface_density);
} else
continue;
- filler->link_max_length = coord_t(scale_(spacing * link_max_length_factor / density));
- fill_expolygons_with_sheath_generate_paths(
+ filler->link_max_length = scale_t(spacing * link_max_length_factor / density);
+ fill_expolygons_generate_paths(
// Destination
support_layer.support_fills.set_entities(),
// Regions to fill
- raft_layer.polygons,
+ closing_ex(raft_layer.polygons, float(SCALED_EPSILON), float(SCALED_EPSILON + 0.5 * flow.scaled_width())),
// Filler and its parameters
filler, density,
// Extrusion parameters
(support_layer_id < m_slicing_params.base_raft_layers) ? erSupportMaterial : erSupportMaterialInterface, flow, spacing,
- // sheath at first layer
- support_layer_id == 0, support_layer_id == 0,
m_object->print()->default_region_config());
}
});
@@ -4112,9 +4107,12 @@ void PrintObjectSupportMaterial::generate_toolpaths(
};
std::vector<LayerCache> layer_caches(support_layers.size());
+ // Filler for the 1st layer interface.
+ std::unique_ptr<FillWithPerimeter> filler_first_layer_ptr = std::make_unique<FillWithPerimeter>(Fill::new_from_type(ipRectilinear));
+ filler_first_layer_ptr->ratio_fill_inside = 0.2f;
tbb::parallel_for(tbb::blocked_range<size_t>(n_raft_layers, support_layers.size()),
[this, &support_layers, &bottom_contacts, &top_contacts, &intermediate_layers, &interface_layers, &base_interface_layers, &layer_caches, &loop_interface_processor,
- &bbox_object, &angles, link_max_length_factor]
+ &bbox_object, &angles, link_max_length_factor, &filler_first_layer_ptr]
(const tbb::blocked_range<size_t>& range) {
// Indices of the 1st layer in their respective container at the support layer height.
size_t idx_layer_bottom_contact = size_t(-1);
@@ -4122,26 +4120,27 @@ void PrintObjectSupportMaterial::generate_toolpaths(
size_t idx_layer_intermediate = size_t(-1);
size_t idx_layer_interface = size_t(-1);
size_t idx_layer_base_interface = size_t(-1);
- const InfillPattern fill_type_first_layer = ipRectilinear;
+ const InfillPattern fill_type_first_layer = ipRectiWithPerimeter;
std::unique_ptr<Fill> filler_interface = std::unique_ptr<Fill>(Fill::new_from_type(m_support_params.contact_fill_pattern));
std::unique_ptr<Fill> filler_intermediate_interface = std::unique_ptr<Fill>(Fill::new_from_type(ipRectilinear));
- // Filler for the 1st layer interface, if different from filler_interface.
- std::unique_ptr<Fill> filler_first_layer_ptr = std::unique_ptr<Fill>(range.begin() == 0 && m_support_params.contact_fill_pattern != fill_type_first_layer ? Fill::new_from_type(fill_type_first_layer) : nullptr);
- // Pointer to the 1st layer interface filler.
- Fill* filler_first_layer = filler_first_layer_ptr ? filler_first_layer_ptr.get() : filler_interface.get();
// Filler for the base interface (to be used for soluble interface / non soluble base, to produce non soluble interface layer below soluble interface layer).
std::unique_ptr<Fill> filler_base_interface = std::unique_ptr<Fill>(base_interface_layers.empty() ? nullptr :
Fill::new_from_type(m_support_params.interface_density > 0.95 || m_support_params.with_sheath ? ipRectilinear : ipSupportBase));
- std::unique_ptr<Fill> filler_support = std::unique_ptr<Fill>(Fill::new_from_type(m_support_params.base_fill_pattern));
- std::unique_ptr<Fill> filler_solid = std::unique_ptr<Fill>(Fill::new_from_type(ipRectiWithPerimeter));
+ std::unique_ptr<Fill> filler_support;
+ if (m_support_params.with_sheath) {
+ FillWithPerimeter *ptr = new FillWithPerimeter(Fill::new_from_type(m_support_params.base_fill_pattern));
+ ptr->ratio_fill_inside = 0.2f;
+ filler_support.reset(ptr);
+ } else {
+ filler_support.reset(Fill::new_from_type(m_support_params.base_fill_pattern));
+ }
filler_interface->set_bounding_box(bbox_object);
filler_intermediate_interface->set_bounding_box(bbox_object);
- if (filler_first_layer_ptr)
+ if (range.begin() == 0)
filler_first_layer_ptr->set_bounding_box(bbox_object);
if (filler_base_interface)
filler_base_interface->set_bounding_box(bbox_object);
filler_support->set_bounding_box(bbox_object);
- filler_solid->set_bounding_box(bbox_object);
for (size_t support_layer_id = range.begin(); support_layer_id < range.end(); ++ support_layer_id)
{
SupportLayer &support_layer = *support_layers[support_layer_id];
@@ -4233,9 +4232,9 @@ void PrintObjectSupportMaterial::generate_toolpaths(
float supp_density = m_support_params.interface_density;
coordf_t filler_spacing;
//if first layer and solid first layer : draw concentric with 100% density
- if (support_layer.id() == 0 && this->m_object_config->support_material_solid_first_layer.value) {
- filler = filler_solid.get();
- supp_density = 1.f;
+ if (support_layer.id() == 0) {
+ filler = filler_first_layer_ptr.get();
+ supp_density = float(this->m_object_config->raft_first_layer_density.get_abs_value(1.));
interface_flow = m_support_params.first_layer_flow;
filler->angle = 0;
filler_spacing = interface_flow.spacing();
@@ -4289,45 +4288,35 @@ void PrintObjectSupportMaterial::generate_toolpaths(
// Base support or flange.
if (! base_layer.empty() && ! base_layer.polygons_to_extrude().empty()) {
Fill *filler = filler_support.get();
- coordf_t filler_spacing = filler->get_spacing();
- filler->angle = angles[support_layer_id % angles.size()];
+ coordf_t filler_spacing = m_support_params.support_material_flow.spacing();
// We don't use $base_flow->spacing because we need a constant spacing
// value that guarantees that all layers are correctly aligned.
assert(! base_layer.layer->bridging);
auto flow = m_support_params.support_material_flow.with_height(float(base_layer.layer->height));
- filler_spacing = m_support_params.support_material_flow.spacing();
- filler->link_max_length = coord_t(scale_(filler_spacing * link_max_length_factor / m_support_params.support_density));
float density = float(m_support_params.support_density);
bool sheath = m_support_params.with_sheath;
- bool no_sort = false;
if (base_layer.layer->bottom_z < EPSILON) {
- if (this->m_object_config->support_material_solid_first_layer.value) {
- // Base flange (the 1st layer).
- filler = filler_solid.get(); //FIXME use filler_first_layer, just set it to the right value
- filler->angle = 0;
- density = 1.f;
- } else {
- filler = filler_first_layer_ptr.get() == nullptr ? filler_interface.get() : filler_first_layer_ptr.get();
- filler->angle = Geometry::deg2rad(float(m_object_config->support_material_angle.value + 90.));
- density = float(m_object_config->raft_first_layer_density.value * 0.01);
- filler->link_max_length = scale_t(filler_spacing * link_max_length_factor / density);
- }
+ filler = filler_first_layer_ptr.get();
+ filler->angle = Geometry::deg2rad(float(m_object_config->support_material_angle.value + 90.));
+ density = float(m_object_config->raft_first_layer_density.get_abs_value(1.));
+ filler->link_max_length = scale_t(filler_spacing * link_max_length_factor / density);
flow = m_support_params.first_layer_flow;
// use the proper spacing for first layer as we don't need to align
// its pattern to the other layers
- sheath = true;
- no_sort = true;
+ filler_spacing = flow.spacing();
+ } else{
+ filler->angle = angles[support_layer_id % angles.size()];
+ filler->link_max_length = coord_t(scale_(filler_spacing * link_max_length_factor / m_support_params.support_density));
}
- fill_expolygons_with_sheath_generate_paths(
+ fill_expolygons_generate_paths(
// Destination
base_layer.extrusions.set_entities(),
// Regions to fill
- base_layer.polygons_to_extrude(),
+ closing_ex(base_layer.polygons_to_extrude(), float(SCALED_EPSILON), float(SCALED_EPSILON + 0.5 * flow.scaled_width())),
// Filler and its parameters
filler, density,
// Extrusion parameters
erSupportMaterial, flow, filler_spacing,
- sheath, no_sort,
m_object->print()->default_region_config());
}