From 2820d244b5b3e5891d57b48169376f4e7b70cc32 Mon Sep 17 00:00:00 2001 From: remi durand Date: Sat, 13 Mar 2021 17:40:06 +0100 Subject: [PATCH] Fix printing 1-point segments (that shouldn't be here, so ignoring them) avoid nan crash --- src/libslic3r/ExtrusionEntity.hpp | 10 +++++----- src/libslic3r/GCode.cpp | 19 +++++++++++++------ src/libslic3r/PerimeterGenerator.cpp | 3 +++ 3 files changed, 21 insertions(+), 11 deletions(-) diff --git a/src/libslic3r/ExtrusionEntity.hpp b/src/libslic3r/ExtrusionEntity.hpp index d36cdf57c..2f55d51fc 100644 --- a/src/libslic3r/ExtrusionEntity.hpp +++ b/src/libslic3r/ExtrusionEntity.hpp @@ -225,11 +225,11 @@ public: float height; ExtrusionPath(ExtrusionRole role) : mm3_per_mm(-1), width(-1), height(-1), m_role(role) {} - ExtrusionPath(ExtrusionRole role, double mm3_per_mm, float width, float height) : mm3_per_mm(mm3_per_mm), width(width), height(height), m_role(role) {} - ExtrusionPath(const ExtrusionPath& rhs) : polyline(rhs.polyline), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) {} - ExtrusionPath(ExtrusionPath&& rhs) : polyline(std::move(rhs.polyline)), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) {} - ExtrusionPath(const Polyline &polyline, const ExtrusionPath &rhs) : polyline(polyline), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) {} - ExtrusionPath(Polyline &&polyline, const ExtrusionPath &rhs) : polyline(std::move(polyline)), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) {} + ExtrusionPath(ExtrusionRole role, double mm3_per_mm, float width, float height) : mm3_per_mm(mm3_per_mm), width(width), height(height), m_role(role) { assert(mm3_per_mm == mm3_per_mm); assert(width == width); assert(height == height); } + ExtrusionPath(const ExtrusionPath& rhs) : polyline(rhs.polyline), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) { assert(mm3_per_mm == mm3_per_mm); assert(width == width); assert(height == height); } + ExtrusionPath(ExtrusionPath&& rhs) : polyline(std::move(rhs.polyline)), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) { assert(mm3_per_mm == mm3_per_mm); assert(width == width); assert(height == height); } + ExtrusionPath(const Polyline &polyline, const ExtrusionPath &rhs) : polyline(polyline), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) { assert(mm3_per_mm == mm3_per_mm); assert(width == width); assert(height == height); } + ExtrusionPath(Polyline &&polyline, const ExtrusionPath &rhs) : polyline(std::move(polyline)), mm3_per_mm(rhs.mm3_per_mm), width(rhs.width), height(rhs.height), m_role(rhs.m_role) { assert(mm3_per_mm == mm3_per_mm); assert(width == width); assert(height == height); } ExtrusionPath& operator=(const ExtrusionPath& rhs) { m_role = rhs.m_role; this->mm3_per_mm = rhs.mm3_per_mm; this->width = rhs.width; this->height = rhs.height; this->polyline = rhs.polyline; return *this; } ExtrusionPath& operator=(ExtrusionPath&& rhs) { m_role = rhs.m_role; this->mm3_per_mm = rhs.mm3_per_mm; this->width = rhs.width; this->height = rhs.height; this->polyline = std::move(rhs.polyline); return *this; } diff --git a/src/libslic3r/GCode.cpp b/src/libslic3r/GCode.cpp index dd6e637f9..1b8e7ffb4 100644 --- a/src/libslic3r/GCode.cpp +++ b/src/libslic3r/GCode.cpp @@ -2025,8 +2025,9 @@ namespace Skirt { std::map> skirt_loops_per_extruder_out; if (print.has_skirt() && ! print.skirt().entities.empty() && // Not enough skirt layers printed yet. - //FIXME infinite or high skirt does not make sense for sequential print! (skirt_done.size() < (size_t)print.config().skirt_height.value || print.has_infinite_skirt()) && + // infinite or high skirt does not make sense for sequential print! + (layer_tools.print_z - skirt_done.back() < print.config().skirt_extrusion_width) && // This print_z has not been extruded yet (sequential print) // FIXME: The skirt_done should not be empty at this point. The check is a workaround // of https://github.com/prusa3d/PrusaSlicer/issues/5652, but it deserves a real fix. @@ -2369,6 +2370,8 @@ void GCode::process_layer( // Adjust flow according to this layer's layer height. ExtrusionLoop loop = *dynamic_cast(print.skirt().entities[i]); for (ExtrusionPath &path : loop.paths) { + assert(layer_skirt_flow.height == layer_skirt_flow.height); + assert(mm3_per_mm == mm3_per_mm); path.height = layer_skirt_flow.height; path.mm3_per_mm = mm3_per_mm; } @@ -3095,11 +3098,13 @@ std::string GCode::extrude_loop(const ExtrusionLoop &original_loop, const std::s } // extrude along the path + //FIXME: we can have one-point paths in the loop that don't move : it's useless! and can create problems! std::string gcode; for (ExtrusionPaths::iterator path = paths.begin(); path != paths.end(); ++path) { //path->simplify(SCALED_RESOLUTION); //should already be simplified //gcode += this->_extrude(*path, description, speed); - gcode += extrude_path(*path, description, speed); + if(path->polyline.points.size()>1) + gcode += extrude_path(*path, description, speed); } // reset acceleration @@ -3269,14 +3274,16 @@ void GCode::use(const ExtrusionEntityCollection &collection) { std::string GCode::extrude_path(const ExtrusionPath &path, const std::string &description, double speed) { ExtrusionPath simplifed_path = path; - if (this->config().min_length.value != 0 && !m_last_too_small.empty()) { + if (this->config().min_length.value != 0 && !m_last_too_small.empty() /*&& m_last_too_small.length() > 0*/) { //descr += " trys fusion " + std::to_string(unscaled(m_last_too_small.last_point().x())) + " , " + std::to_string(unscaled(path.first_point().x())); //ensure that it's a continous thing - if (m_last_too_small.last_point().distance_to_square(path.first_point()) < scale_(this->config().min_length)) { + if (m_last_too_small.first_point().distance_to_square(path.first_point()) < scale_(this->config().min_length) /*&& m_last_too_small.first_point().distance_to_square(path.first_point()) > EPSILON*/) { //descr += " ! fusion " + std::to_string(simplifed_path.polyline.points.size()); - simplifed_path.height = (m_last_too_small.height * m_last_too_small.length() + path.height * path.length()) / (m_last_too_small.length() + path.length()); - simplifed_path.mm3_per_mm = (m_last_too_small.mm3_per_mm * m_last_too_small.length() + path.mm3_per_mm * path.length()) / (m_last_too_small.length() + path.length()); + simplifed_path.height = (m_last_too_small.height * m_last_too_small.length() + simplifed_path.height * simplifed_path.length()) / (m_last_too_small.length() + simplifed_path.length()); + simplifed_path.mm3_per_mm = (m_last_too_small.mm3_per_mm * m_last_too_small.length() + simplifed_path.mm3_per_mm * simplifed_path.length()) / (m_last_too_small.length() + simplifed_path.length()); simplifed_path.polyline.points.insert(simplifed_path.polyline.points.begin(), m_last_too_small.polyline.points.begin(), m_last_too_small.polyline.points.end()-1); + assert(simplifed_path.height == simplifed_path.height); + assert(simplifed_path.mm3_per_mm == simplifed_path.mm3_per_mm); } m_last_too_small.polyline.points.clear(); } diff --git a/src/libslic3r/PerimeterGenerator.cpp b/src/libslic3r/PerimeterGenerator.cpp index fdd552f1c..b5aeb7d28 100644 --- a/src/libslic3r/PerimeterGenerator.cpp +++ b/src/libslic3r/PerimeterGenerator.cpp @@ -1153,6 +1153,9 @@ ExtrusionEntityCollection PerimeterGenerator::_traverse_loops( path.mm3_per_mm = is_external ? this->_ext_mm3_per_mm : this->_mm3_per_mm; path.width = is_external ? this->ext_perimeter_flow.width : this->perimeter_flow.width; path.height = (float) this->layer->height; + assert(path.mm3_per_mm == path.mm3_per_mm); + assert(path.width == path.width); + assert(path.height == path.height); paths.push_back(path); }