mirror of
https://github.com/SoftFever/OrcaSlicer.git
synced 2025-07-17 03:37:54 -06:00
Grow narrow infill regions into void - to be tested more
This commit is contained in:
parent
6058384978
commit
d9b82c79da
3 changed files with 49 additions and 27 deletions
|
@ -13,7 +13,7 @@ use Slic3r::Fill::PlanePath;
|
||||||
use Slic3r::Fill::Rectilinear;
|
use Slic3r::Fill::Rectilinear;
|
||||||
use Slic3r::ExtrusionPath ':roles';
|
use Slic3r::ExtrusionPath ':roles';
|
||||||
use Slic3r::Geometry qw(X Y PI scale chained_path);
|
use Slic3r::Geometry qw(X Y PI scale chained_path);
|
||||||
use Slic3r::Geometry::Clipper qw(union_ex diff_ex);
|
use Slic3r::Geometry::Clipper qw(union_ex diff_ex intersection_ex offset);
|
||||||
use Slic3r::Surface ':types';
|
use Slic3r::Surface ':types';
|
||||||
|
|
||||||
|
|
||||||
|
@ -98,15 +98,40 @@ sub make_fill {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
# add spacing between surfaces
|
# we need to detect any narrow surfaces that might collapse
|
||||||
|
# when adding spacing below
|
||||||
|
# such narrow surfaces are often generated in sloping walls
|
||||||
|
# by bridge_over_infill() and combine_infill() as a result of the
|
||||||
|
# subtraction of the combinable area from the layer infill area,
|
||||||
|
# which leaves small areas near the perimeters
|
||||||
|
# we are going to grow such regions by overlapping them with the void (if any)
|
||||||
|
# TODO: detect and investigate whether there could be narrow regions without
|
||||||
|
# any void neighbors
|
||||||
|
my $distance_between_surfaces = $layerm->infill_flow->scaled_spacing;
|
||||||
{
|
{
|
||||||
my $distance = $layerm->infill_flow->scaled_spacing / 2;
|
my $collapsed = diff_ex(
|
||||||
@surfaces = map $_->offset(-$distance), @surfaces;
|
[ map @{$_->expolygon}, @surfaces ],
|
||||||
|
[ offset(
|
||||||
|
[ offset([ map @{$_->expolygon}, @surfaces ], -$distance_between_surfaces/2) ],
|
||||||
|
+$distance_between_surfaces/2
|
||||||
|
) ],
|
||||||
|
);
|
||||||
|
push @surfaces, map Slic3r::Surface->new(
|
||||||
|
expolygon => $_,
|
||||||
|
surface_type => S_TYPE_INTERNALSOLID,
|
||||||
|
), @{intersection_ex(
|
||||||
|
[ offset([ map @$_, @$collapsed ], $distance_between_surfaces) ],
|
||||||
|
[ map @{$_->expolygon}, grep $_->surface_type == S_TYPE_INTERNALVOID, @surfaces ],
|
||||||
|
)};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# add spacing between surfaces
|
||||||
|
@surfaces = map $_->offset(-$distance_between_surfaces/2), @surfaces;
|
||||||
|
|
||||||
my @fills = ();
|
my @fills = ();
|
||||||
my @fills_ordering_points = ();
|
my @fills_ordering_points = ();
|
||||||
SURFACE: foreach my $surface (@surfaces) {
|
SURFACE: foreach my $surface (@surfaces) {
|
||||||
|
next if $surface->surface_type == S_TYPE_INTERNALVOID;
|
||||||
my $filler = $Slic3r::Config->fill_pattern;
|
my $filler = $Slic3r::Config->fill_pattern;
|
||||||
my $density = $Slic3r::Config->fill_density;
|
my $density = $Slic3r::Config->fill_density;
|
||||||
my $flow_spacing = ($surface->surface_type == S_TYPE_TOP)
|
my $flow_spacing = ($surface->surface_type == S_TYPE_TOP)
|
||||||
|
|
|
@ -516,6 +516,13 @@ sub bridge_over_infill {
|
||||||
[ map $_->p, @$group ],
|
[ map $_->p, @$group ],
|
||||||
[ map @$_, @$to_bridge ],
|
[ map @$_, @$to_bridge ],
|
||||||
)};
|
)};
|
||||||
|
push @new_surfaces, map Slic3r::Surface->new(
|
||||||
|
expolygon => $_,
|
||||||
|
surface_type => S_TYPE_INTERNALVOID,
|
||||||
|
), @{intersection_ex(
|
||||||
|
[ map $_->p, @$group ],
|
||||||
|
[ map @$_, @$to_bridge ],
|
||||||
|
)};
|
||||||
}
|
}
|
||||||
@{$lower_layerm->fill_surfaces} = @new_surfaces;
|
@{$lower_layerm->fill_surfaces} = @new_surfaces;
|
||||||
}
|
}
|
||||||
|
@ -713,7 +720,7 @@ sub combine_infill {
|
||||||
my @this_type = grep $_->surface_type == $type, @{$layerm->fill_surfaces};
|
my @this_type = grep $_->surface_type == $type, @{$layerm->fill_surfaces};
|
||||||
my @other_types = grep $_->surface_type != $type, @{$layerm->fill_surfaces};
|
my @other_types = grep $_->surface_type != $type, @{$layerm->fill_surfaces};
|
||||||
|
|
||||||
@this_type = map Slic3r::Surface->new(expolygon => $_, surface_type => $type),
|
my @new_this_type = map Slic3r::Surface->new(expolygon => $_, surface_type => $type),
|
||||||
@{diff_ex(
|
@{diff_ex(
|
||||||
[ map @{$_->expolygon}, @this_type ],
|
[ map @{$_->expolygon}, @this_type ],
|
||||||
[ @intersection_with_clearance ],
|
[ @intersection_with_clearance ],
|
||||||
|
@ -721,12 +728,20 @@ sub combine_infill {
|
||||||
|
|
||||||
# apply surfaces back with adjusted depth to the uppermost layer
|
# apply surfaces back with adjusted depth to the uppermost layer
|
||||||
if ($layerm->id == $layer_id) {
|
if ($layerm->id == $layer_id) {
|
||||||
push @this_type,
|
push @new_this_type,
|
||||||
map Slic3r::Surface->new(expolygon => $_, surface_type => $type, depth_layers => $every),
|
map Slic3r::Surface->new(expolygon => $_, surface_type => $type, depth_layers => $every),
|
||||||
@$intersection;
|
@$intersection;
|
||||||
|
} else {
|
||||||
|
# save void surfaces
|
||||||
|
push @this_type,
|
||||||
|
map Slic3r::Surface->new(expolygon => $_, surface_type => S_TYPE_INTERNALVOID),
|
||||||
|
@{intersection_ex(
|
||||||
|
[ map @{$_->expolygon}, @this_type ],
|
||||||
|
[ @intersection_with_clearance ],
|
||||||
|
)};
|
||||||
}
|
}
|
||||||
|
|
||||||
@{$layerm->fill_surfaces} = (@this_type, @other_types);
|
@{$layerm->fill_surfaces} = (@new_this_type, @other_types);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,7 +4,7 @@ use warnings;
|
||||||
|
|
||||||
require Exporter;
|
require Exporter;
|
||||||
our @ISA = qw(Exporter);
|
our @ISA = qw(Exporter);
|
||||||
our @EXPORT_OK = qw(S_TYPE_TOP S_TYPE_BOTTOM S_TYPE_INTERNAL S_TYPE_INTERNALSOLID S_TYPE_INTERNALBRIDGE);
|
our @EXPORT_OK = qw(S_TYPE_TOP S_TYPE_BOTTOM S_TYPE_INTERNAL S_TYPE_INTERNALSOLID S_TYPE_INTERNALBRIDGE S_TYPE_INTERNALVOID);
|
||||||
our %EXPORT_TAGS = (types => \@EXPORT_OK);
|
our %EXPORT_TAGS = (types => \@EXPORT_OK);
|
||||||
|
|
||||||
use constant S_EXPOLYGON => 0;
|
use constant S_EXPOLYGON => 0;
|
||||||
|
@ -18,6 +18,7 @@ use constant S_TYPE_BOTTOM => 1;
|
||||||
use constant S_TYPE_INTERNAL => 2;
|
use constant S_TYPE_INTERNAL => 2;
|
||||||
use constant S_TYPE_INTERNALSOLID => 3;
|
use constant S_TYPE_INTERNALSOLID => 3;
|
||||||
use constant S_TYPE_INTERNALBRIDGE => 4;
|
use constant S_TYPE_INTERNALBRIDGE => 4;
|
||||||
|
use constant S_TYPE_INTERNALVOID => 5;
|
||||||
|
|
||||||
sub new {
|
sub new {
|
||||||
my $class = shift;
|
my $class = shift;
|
||||||
|
@ -74,17 +75,6 @@ sub offset {
|
||||||
} $self->expolygon->offset_ex(@_);
|
} $self->expolygon->offset_ex(@_);
|
||||||
}
|
}
|
||||||
|
|
||||||
sub clipper_polygon {
|
|
||||||
my $self = shift;
|
|
||||||
|
|
||||||
return {
|
|
||||||
outer => $self->contour->p,
|
|
||||||
holes => [
|
|
||||||
map $_->p, @{$self->holes}
|
|
||||||
],
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
sub p {
|
sub p {
|
||||||
my $self = shift;
|
my $self = shift;
|
||||||
return @{$self->expolygon};
|
return @{$self->expolygon};
|
||||||
|
@ -99,14 +89,6 @@ sub is_solid {
|
||||||
|| $type == S_TYPE_INTERNALSOLID;
|
|| $type == S_TYPE_INTERNALSOLID;
|
||||||
}
|
}
|
||||||
|
|
||||||
sub is_internal {
|
|
||||||
my $self = shift;
|
|
||||||
my $type = $self->surface_type;
|
|
||||||
return $type == S_TYPE_INTERNAL
|
|
||||||
|| $type == S_TYPE_INTERNALSOLID
|
|
||||||
|| $type == S_TYPE_INTERNALBRIDGE;
|
|
||||||
}
|
|
||||||
|
|
||||||
sub is_bridge {
|
sub is_bridge {
|
||||||
my $self = shift;
|
my $self = shift;
|
||||||
my $type = $self->surface_type;
|
my $type = $self->surface_type;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue