Fix of infill_only_where_needed for complex objects:

When propagating overhangs to be supported, the regions are newly
properly merged and regularized.

Fix of Stuck at "preparing infill" with "only infill where needed" enabled 1.41.2 #1696
"Only infill where needed" makes slicer crash for some models #6385
[BUG] Slicing stuck for 14h now, 0.8 NZL Ender 5+ Gyroid infill only where need
This commit is contained in:
Vojtech Bubnik 2021-12-07 09:52:58 +01:00
parent 940690ecdb
commit 7f0fcd1354

View File

@ -6,6 +6,7 @@
#include "Geometry.hpp" #include "Geometry.hpp"
#include "I18N.hpp" #include "I18N.hpp"
#include "Layer.hpp" #include "Layer.hpp"
#include "MutablePolygon.hpp"
#include "SupportMaterial.hpp" #include "SupportMaterial.hpp"
#include "Surface.hpp" #include "Surface.hpp"
#include "Slicing.hpp" #include "Slicing.hpp"
@ -1709,9 +1710,6 @@ void PrintObject::clip_fill_surfaces()
Layer *layer = m_layers[layer_id]; Layer *layer = m_layers[layer_id];
Layer *lower_layer = m_layers[layer_id - 1]; Layer *lower_layer = m_layers[layer_id - 1];
// Detect things that we need to support. // Detect things that we need to support.
// Cummulative slices.
Polygons slices;
polygons_append(slices, layer->lslices);
// Cummulative fill surfaces. // Cummulative fill surfaces.
Polygons fill_surfaces; Polygons fill_surfaces;
// Solid surfaces to be supported. // Solid surfaces to be supported.
@ -1736,7 +1734,7 @@ void PrintObject::clip_fill_surfaces()
{ {
// Get perimeters area as the difference between slices and fill_surfaces // Get perimeters area as the difference between slices and fill_surfaces
// Only consider the area that is not supported by lower perimeters // Only consider the area that is not supported by lower perimeters
Polygons perimeters = intersection(diff(slices, fill_surfaces), lower_layer_fill_surfaces); Polygons perimeters = intersection(diff(layer->lslices, fill_surfaces), lower_layer_fill_surfaces);
// Only consider perimeter areas that are at least one extrusion width thick. // Only consider perimeter areas that are at least one extrusion width thick.
//FIXME Offset2 eats out from both sides, while the perimeters are create outside in. //FIXME Offset2 eats out from both sides, while the perimeters are create outside in.
//Should the pw not be half of the current value? //Should the pw not be half of the current value?
@ -1746,9 +1744,15 @@ void PrintObject::clip_fill_surfaces()
// Append such thick perimeters to the areas that need support // Append such thick perimeters to the areas that need support
polygons_append(overhangs, opening(perimeters, pw)); polygons_append(overhangs, opening(perimeters, pw));
} }
// Find new internal infill. // Merge the new overhangs, find new internal infill.
polygons_append(overhangs, std::move(upper_internal)); polygons_append(upper_internal, std::move(overhangs));
upper_internal = intersection(overhangs, lower_layer_internal_surfaces); static constexpr const auto closing_radius = scaled<float>(2.f);
upper_internal = intersection(
// Regularize the overhang regions, so that the infill areas will not become excessively jagged.
smooth_outward(
closing(upper_internal, closing_radius, ClipperLib::jtSquare, 0.),
scaled<coord_t>(0.1)),
lower_layer_internal_surfaces);
// Apply new internal infill to regions. // Apply new internal infill to regions.
for (LayerRegion *layerm : lower_layer->m_regions) { for (LayerRegion *layerm : lower_layer->m_regions) {
if (layerm->region().config().fill_density.value == 0) if (layerm->region().config().fill_density.value == 0)