mirror of
https://git.mirrors.martin98.com/https://github.com/slic3r/Slic3r.git
synced 2025-07-30 19:31:58 +08:00
ironing: bugfix & clean
- remove some debug logs - bugfix: 2D toolpath now can draw collection of paths. - bugfix: fillsmooth doesn't bug if the area is too small to draw anything.
This commit is contained in:
parent
0544793128
commit
fe657e645d
@ -491,16 +491,20 @@ sub Render {
|
||||
sub _draw {
|
||||
my ($self, $object, $print_z, $path) = @_;
|
||||
|
||||
my @paths = ($path->isa('Slic3r::ExtrusionLoop') || $path->isa('Slic3r::ExtrusionMultiPath'))
|
||||
? @$path
|
||||
: ($path);
|
||||
if ($path->isa('Slic3r::ExtrusionPath::Collection')) {
|
||||
$self->_draw($object, $print_z, $_) for @{$path};
|
||||
}else{
|
||||
my @paths = ($path->isa('Slic3r::ExtrusionLoop') || $path->isa('Slic3r::ExtrusionMultiPath'))
|
||||
? @$path
|
||||
: ($path);
|
||||
|
||||
$self->_draw_path($object, $print_z, $_) for @paths;
|
||||
$self->_draw_path($object, $print_z, $_) for @paths;
|
||||
}
|
||||
}
|
||||
|
||||
sub _draw_path {
|
||||
my ($self, $object, $print_z, $path) = @_;
|
||||
|
||||
|
||||
return if $print_z - $path->height > $self->z - epsilon;
|
||||
|
||||
if (abs($print_z - $self->z) < epsilon) {
|
||||
|
@ -35,8 +35,10 @@ Fill* Fill::new_from_type(const InfillPattern type)
|
||||
// case ipGrid: return new FillGrid();
|
||||
case ipArchimedeanChords: return new FillArchimedeanChords();
|
||||
case ipHilbertCurve: return new FillHilbertCurve();
|
||||
case ipOctagramSpiral: return new FillOctagramSpiral();
|
||||
case ipOctagramSpiral: return new FillOctagramSpiral();
|
||||
case ipSmooth: return new FillSmooth();
|
||||
case ipSmoothTriple: return new FillSmoothTriple();
|
||||
case ipSmoothHilbert: return new FillSmoothHilbert();
|
||||
default: CONFESS("unknown type"); return nullptr;
|
||||
}
|
||||
}
|
||||
|
@ -23,7 +23,7 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
{
|
||||
coordf_t init_spacing = this->spacing;
|
||||
|
||||
printf("FillSmooth::fill_surface() : you call the right method (fill_surface instead of fill_surface_extrusion).\n");
|
||||
//printf("FillSmooth::fill_surface() : you call the right method (fill_surface instead of fill_surface_extrusion).\n");
|
||||
//second pass with half layer width
|
||||
FillParams params1 = params;
|
||||
FillParams params2 = params;
|
||||
@ -31,9 +31,6 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
params1.density *= percentWidth[0];
|
||||
params2.density *= percentWidth[1];
|
||||
params3.density *= percentWidth[2];
|
||||
// Polylines polylines_layer1;
|
||||
// Polylines polylines_layer2;
|
||||
// Polylines polylines_layer3;
|
||||
|
||||
//a small under-overlap to prevent over-extrudion on thin surfaces (i.e. remove the overlap)
|
||||
Surface surfaceNoOverlap(*surface);
|
||||
@ -43,15 +40,6 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
if(offsetPloys.size() == 1) surfaceNoOverlap.expolygon = offsetPloys[0];
|
||||
//TODO: recursive if multiple polys instead of failing
|
||||
|
||||
//if (! fill_surface_by_lines(&surfaceNoOverlap/* */, params1, anglePass[0], 0.f, polylines_layer1) ||
|
||||
// (nbPass>1 && !fill_surface_by_lines(surface, params2, anglePass[1], 0.f, polylines_layer2)) ||
|
||||
// (nbPass>2 && !fill_surface_by_lines(surface, params3, anglePass[2], 0.f, polylines_layer3))) {
|
||||
// printf("FillSmooth::fill_surface() failed to fill a region.\n");
|
||||
//}
|
||||
/*
|
||||
std::cout<<"polylines_layer1 size ="<<polylines_layer1.size()<<" \n";
|
||||
std::cout<<"polylines_layer2 size ="<<polylines_layer2.size()<<" \n";
|
||||
std::cout<<"polylines_layer3 size ="<<polylines_layer3.size()<<" \n";*/
|
||||
|
||||
//if (polylines_layer1.empty() && polylines_layer2.empty() && polylines_layer3.empty())
|
||||
// return;
|
||||
@ -85,6 +73,8 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
flow.bridge ? erBridgeInfill : rolePass[0],
|
||||
flow.mm3_per_mm()*percentFlow[0], (float)flow.width*percentFlow[0], (float)flow.height*0.9);
|
||||
//reduced flow width & height for a better view (it's only a gui thing)
|
||||
}else{
|
||||
return;
|
||||
}
|
||||
|
||||
//second infill
|
||||
@ -102,21 +92,24 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
f2->loop_clipping = this->loop_clipping;
|
||||
Polylines polylines_layer2 = f2->fill_surface(&surfaceNoOverlap, params2);
|
||||
|
||||
if (fillPattern[2] == InfillPattern::ipRectilinear && polylines_layer2[0].points.size() > 3){
|
||||
polylines_layer2[0].points.erase(polylines_layer2[0].points.begin());
|
||||
polylines_layer2[polylines_layer2.size() - 1].points.pop_back();
|
||||
}
|
||||
if (!polylines_layer2.empty()){
|
||||
if (fillPattern[2] == InfillPattern::ipRectilinear && polylines_layer2[0].points.size() > 3){
|
||||
polylines_layer2[0].points.erase(polylines_layer2[0].points.begin());
|
||||
polylines_layer2[polylines_layer2.size() - 1].points.pop_back();
|
||||
}
|
||||
|
||||
// Save into layer smoothing path.
|
||||
eec = new ExtrusionEntityCollection();
|
||||
eecroot->entities.push_back(eec);
|
||||
eec->no_sort = false;
|
||||
// print thin
|
||||
|
||||
extrusion_entities_append_paths(
|
||||
eec->entities, STDMOVE(polylines_layer2),
|
||||
rolePass[1],
|
||||
flow.mm3_per_mm()*percentFlow[1], (float)flow.width*(percentFlow[1] < 0.1 ? 0.1 : percentFlow[1]), (float)flow.height);
|
||||
}else{
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
@ -134,12 +127,14 @@ void FillSmooth::fill_surface_extrusion(const Surface *surface, const FillParams
|
||||
f3->loop_clipping = this->loop_clipping;
|
||||
Polylines polylines_layer3 = f3->fill_surface(&surfaceNoOverlap, params1);
|
||||
|
||||
//remove some points that are not inside the area
|
||||
if (fillPattern[2] == InfillPattern::ipRectilinear && polylines_layer3[0].points.size() > 3){
|
||||
polylines_layer3[0].points.erase(polylines_layer3[0].points.begin());
|
||||
polylines_layer3[polylines_layer3.size() - 1].points.pop_back();
|
||||
}
|
||||
if (!polylines_layer3.empty()){
|
||||
|
||||
//remove some points that are not inside the area
|
||||
if (fillPattern[2] == InfillPattern::ipRectilinear && polylines_layer3[0].points.size() > 3){
|
||||
polylines_layer3[0].points.erase(polylines_layer3[0].points.begin());
|
||||
polylines_layer3[polylines_layer3.size() - 1].points.pop_back();
|
||||
}
|
||||
|
||||
// Save into layer smoothing path. layer 3
|
||||
eec = new ExtrusionEntityCollection();
|
||||
eecroot->entities.push_back(eec);
|
||||
|
@ -53,6 +53,66 @@ protected:
|
||||
InfillPattern fillPattern[3];
|
||||
};
|
||||
|
||||
|
||||
class FillSmoothTriple : public FillSmooth
|
||||
{
|
||||
public:
|
||||
FillSmoothTriple() {
|
||||
nbPass = 3;
|
||||
anglePass[0] = float(M_PI / 4);
|
||||
anglePass[1] = -float(M_PI / 4);
|
||||
anglePass[2] = 0;
|
||||
fillPattern[0] = InfillPattern::ipRectilinear;
|
||||
fillPattern[1] = InfillPattern::ipRectilinear;
|
||||
fillPattern[2] = InfillPattern::ipRectilinear;
|
||||
rolePass[0] = erSolidInfill;
|
||||
rolePass[1] = erSolidInfill;
|
||||
rolePass[2] = erTopSolidInfill;
|
||||
percentWidth[0] = 0.9;
|
||||
percentWidth[1] = 1.4;
|
||||
percentWidth[2] = 2.5;
|
||||
percentFlow[0] = 0.7 / percentWidth[0];
|
||||
percentFlow[1] = 0.3 / percentWidth[1];
|
||||
percentFlow[2] = 0.0 / percentWidth[2];
|
||||
double extrusionMult = 1.0;
|
||||
percentFlow[0] *= extrusionMult;
|
||||
percentFlow[1] *= extrusionMult;
|
||||
percentFlow[2] *= extrusionMult;
|
||||
}
|
||||
virtual Fill* clone() const { return new FillSmoothTriple(*this); }
|
||||
|
||||
};
|
||||
|
||||
class FillSmoothHilbert : public FillSmooth
|
||||
{
|
||||
public:
|
||||
FillSmoothHilbert() {
|
||||
nbPass = 3;
|
||||
anglePass[0] = 0;
|
||||
anglePass[1] = -float(M_PI / 4);
|
||||
anglePass[2] = float(M_PI / 4);
|
||||
fillPattern[0] = InfillPattern::ipHilbertCurve;
|
||||
fillPattern[1] = InfillPattern::ipRectilinear;
|
||||
fillPattern[2] = InfillPattern::ipRectilinear;
|
||||
rolePass[0] = erSolidInfill;
|
||||
rolePass[1] = erSolidInfill;
|
||||
rolePass[2] = erTopSolidInfill;
|
||||
percentWidth[0] = 1;
|
||||
percentWidth[1] = 1;
|
||||
percentWidth[2] = 2;
|
||||
percentFlow[0] = 0.8 / percentWidth[0];
|
||||
percentFlow[1] = 0.1 / percentWidth[1];
|
||||
percentFlow[2] = 0.1 / percentWidth[2];
|
||||
double extrusionMult = 1.0;
|
||||
percentFlow[0] *= extrusionMult;
|
||||
percentFlow[1] *= extrusionMult;
|
||||
percentFlow[2] *= extrusionMult;
|
||||
}
|
||||
virtual Fill* clone() const { return new FillSmoothHilbert(*this); }
|
||||
|
||||
};
|
||||
|
||||
|
||||
} // namespace Slic3r
|
||||
|
||||
#endif // slic3r_FillSmooth_hpp_
|
||||
|
@ -2018,18 +2018,9 @@ std::string GCode::extrude_infill(const Print &print, const ExtrusionEntityColle
|
||||
for (ExtrusionEntity *fill : chained.entities) {
|
||||
auto *eec = dynamic_cast<ExtrusionEntityCollection*>(fill);
|
||||
if (eec) {
|
||||
std::cout << "recursive infill with role: " << fill->role() << " : " << (fill->role() == ExtrusionRole::erBridgeInfill) << "\n";
|
||||
gcode += extrude_infill(print, *eec);
|
||||
}
|
||||
else {
|
||||
std::cout << "extrude infill with role: " << fill->role() << " : " << (fill->role() == ExtrusionRole::erBridgeInfill) << "\n";
|
||||
if (/*print.config.disable_fan_top_layers.value && */fill->role() == ExtrusionRole::erTopSolidInfill){ //TODO: add && params.get(disable_fan_top_layers)
|
||||
// gcode += ";_DISABLE_FAN_START\n";
|
||||
}
|
||||
} else {
|
||||
gcode += this->extrude_entity(*fill, "infill");
|
||||
if (/*print.config.disable_fan_top_layers.value && */fill->role() == ExtrusionRole::erTopSolidInfill){ //TODO: add && params.get(disable_fan_top_layers)
|
||||
// gcode += ";_DISABLE_FAN_END\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
return gcode;
|
||||
|
@ -263,14 +263,18 @@ PrintConfigDef::PrintConfigDef()
|
||||
def->enum_values.push_back("concentric");
|
||||
def->enum_values.push_back("hilbertcurve");
|
||||
def->enum_values.push_back("archimedeanchords");
|
||||
def->enum_values.push_back("octagramspiral");
|
||||
def->enum_values.push_back("smooth");
|
||||
def->enum_values.push_back("octagramspiral");
|
||||
def->enum_values.push_back("smooth");
|
||||
def->enum_values.push_back("smoothtriple");
|
||||
def->enum_values.push_back("smoothhilbert");
|
||||
def->enum_labels.push_back("Rectilinear");
|
||||
def->enum_labels.push_back("Concentric");
|
||||
def->enum_labels.push_back("Hilbert Curve");
|
||||
def->enum_labels.push_back("Archimedean Chords");
|
||||
def->enum_labels.push_back("Octagram Spiral");
|
||||
def->enum_labels.push_back("Ironing");
|
||||
def->enum_labels.push_back("Ironing");
|
||||
def->enum_labels.push_back("Ironing (triple)");
|
||||
def->enum_labels.push_back("Ironing (hilbert)");
|
||||
// solid_fill_pattern is an obsolete equivalent to top_fill_pattern/bottom_fill_pattern.
|
||||
def->aliases.push_back("solid_fill_pattern");
|
||||
def->default_value = new ConfigOptionEnum<InfillPattern>(ipRectilinear);
|
||||
|
@ -29,7 +29,7 @@ enum GCodeFlavor {
|
||||
|
||||
enum InfillPattern {
|
||||
ipRectilinear, ipGrid, ipTriangles, ipStars, ipCubic, ipLine, ipConcentric, ipHoneycomb, ip3DHoneycomb,
|
||||
ipGyroid, ipHilbertCurve, ipArchimedeanChords, ipOctagramSpiral, ipSmooth,
|
||||
ipGyroid, ipHilbertCurve, ipArchimedeanChords, ipOctagramSpiral, ipSmooth, ipSmoothHilbert, ipSmoothTriple,
|
||||
};
|
||||
|
||||
enum SupportMaterialPattern {
|
||||
@ -77,7 +77,9 @@ template<> inline t_config_enum_values& ConfigOptionEnum<InfillPattern>::get_enu
|
||||
keys_map["hilbertcurve"] = ipHilbertCurve;
|
||||
keys_map["archimedeanchords"] = ipArchimedeanChords;
|
||||
keys_map["octagramspiral"] = ipOctagramSpiral;
|
||||
keys_map["smooth"] = ipSmooth;
|
||||
keys_map["smooth"] = ipSmooth;
|
||||
keys_map["smoothtriple"] = ipSmoothTriple;
|
||||
keys_map["smoothhilbert"] = ipSmoothHilbert;
|
||||
}
|
||||
return keys_map;
|
||||
}
|
||||
|
@ -363,11 +363,8 @@ void PrintObject::_prepare_infill()
|
||||
// the following step needs to be done before combination because it may need
|
||||
// to remove only half of the combined infill
|
||||
this->bridge_over_infill();
|
||||
std::cout<<"INTERNAL BRIDGE ===========================================\n";
|
||||
this->replaceSurfaceType( stInternalSolid, stInternalOverBridge, stInternalBridge);
|
||||
std::cout<<"BOTTOM BRIDGE ===========================================\n";
|
||||
this->replaceSurfaceType( stInternalSolid, stInternalOverBridge, stBottomBridge);
|
||||
std::cout<<"TOP BRIDGE ===========================================\n";
|
||||
this->replaceSurfaceType( stTop, stTopOverBridge, stInternalBridge);
|
||||
this->replaceSurfaceType( stTop, stTopOverBridge, stBottomBridge);
|
||||
|
||||
@ -1185,10 +1182,6 @@ void PrintObject::replaceSurfaceType(SurfaceType st_to_replace, SurfaceType st_r
|
||||
layerm->fill_surfaces.filter_by_type(st_under_it, &stIntBridge_init);
|
||||
double intbridgeareainit=0;
|
||||
for (ExPolygon &ex : union_ex(stIntBridge_init)) intbridgeareainit+=ex.area();
|
||||
|
||||
std::cout<<"init st_replacement="<<totoverareaInit<<", bottombridgearea="<<bottombridgearea
|
||||
<<", st_to_replace="<<internsolidareainit<<", bottomeareainit="<<bottomeareainit
|
||||
<<", st_under_it="<<intbridgeareainit<<"\n";
|
||||
|
||||
// check whether the lower area is deep enough for absorbing the extra flow
|
||||
// (for obvious physical reasons but also for preventing the bridge extrudates
|
||||
@ -1214,16 +1207,12 @@ void PrintObject::replaceSurfaceType(SurfaceType st_to_replace, SurfaceType st_r
|
||||
for (ExPolygon &ex : union_ex(lower_internal_OK)) okarea+=ex.area();
|
||||
for (ExPolygon &ex : union_ex(lower_internal_Bridge)) bridgearea+=ex.area();
|
||||
for (ExPolygon &ex : union_ex(lower_internal_Over)) overarea+=ex.area();
|
||||
std::cout<<"@layer "<<int(layer_it - this->layers.begin())
|
||||
<<" region under has "<<lower_internal_OK.size()<<" st_replacement : "<<okarea
|
||||
<<" , has "<<lower_internal_Bridge.size()<<" st_under_it: "<<bridgearea
|
||||
<<" , has "<<lower_internal_Over.size()<<" st_to_replace: "<<overarea<<"\n";
|
||||
|
||||
(*lower_layerm_it)->fill_surfaces.filter_by_type(st_under_it, &lower_internal);
|
||||
}
|
||||
double sumarea=0;
|
||||
for (ExPolygon &ex : union_ex(lower_internal)) sumarea+=ex.area();
|
||||
std::cout<<"@layer "<<int(layer_it - this->layers.begin())<<" region under has "<<union_ex(lower_internal).size()<<" sum bridge : "<<sumarea<<"\n";
|
||||
|
||||
|
||||
// intersect such lower internal surfaces with the candidate solid surfaces
|
||||
to_overextrude_pp = intersection(to_overextrude_pp, lower_internal);
|
||||
}
|
||||
@ -1241,9 +1230,6 @@ void PrintObject::replaceSurfaceType(SurfaceType st_to_replace, SurfaceType st_r
|
||||
|
||||
// convert into ExPolygons
|
||||
to_overextrude = union_ex(to_overextrude_pp);
|
||||
double finalarea = 0;
|
||||
for (ExPolygon &ex : to_overextrude) finalarea+=ex.area();
|
||||
std::cout<<"find an overextruding area of "<<finalarea<<" on layer "<<int(layer_it - this->layers.begin())<<"\n";
|
||||
}
|
||||
|
||||
#ifdef SLIC3R_DEBUG
|
||||
@ -1268,8 +1254,8 @@ void PrintObject::replaceSurfaceType(SurfaceType st_to_replace, SurfaceType st_r
|
||||
layerm->fill_surfaces.filter_by_type(stInternalOverBridge, &internal_over_tot);
|
||||
double totoverarea=0;
|
||||
for (ExPolygon &ex : union_ex(internal_over_tot)) totoverarea+=ex.area();
|
||||
std::cout<<"final: st_to_replace="<<solidareafinal<<", st_replacement="<<overareafinal<<", totstInternalOverBridge="<<totoverarea<<"\n";
|
||||
/*
|
||||
|
||||
/*
|
||||
# exclude infill from the layers below if needed
|
||||
# see discussion at https://github.com/alexrj/Slic3r/issues/240
|
||||
# Update: do not exclude any infill. Sparse infill is able to absorb the excess material.
|
||||
@ -1768,7 +1754,7 @@ void PrintObject::_infill()
|
||||
### $_->fill_surfaces->clear for map @{$_->regions}, @{$object->layers};
|
||||
*/
|
||||
|
||||
this->state.set_done(posInfill);
|
||||
this->state.set_done(posInfill);
|
||||
}
|
||||
|
||||
// Only active if config->infill_only_where_needed. This step trims the sparse infill,
|
||||
|
Loading…
x
Reference in New Issue
Block a user