diff options
Diffstat (limited to 'xs/src/libslic3r/GCode.cpp')
-rw-r--r-- | xs/src/libslic3r/GCode.cpp | 76 |
1 files changed, 68 insertions, 8 deletions
diff --git a/xs/src/libslic3r/GCode.cpp b/xs/src/libslic3r/GCode.cpp index b297ddab0..0e85c55a8 100644 --- a/xs/src/libslic3r/GCode.cpp +++ b/xs/src/libslic3r/GCode.cpp @@ -267,9 +267,58 @@ std::string WipeTowerIntegration::finalize(GCode &gcodegen) #define EXTRUDER_CONFIG(OPT) m_config.OPT.get_at(m_writer.extruder()->id()) +// Helper class for writing to file with/without time estimation +class Write +{ + static GCodeTimeEstimator* s_time_estimator; + +public: + static void set_time_estimator(GCodeTimeEstimator* time_estimator) + { + s_time_estimator = time_estimator; + } + + static void write(FILE* file, const std::string& what) + { + if (!what.empty()) + { + fwrite(what.data(), 1, what.size(), file); + + if (s_time_estimator != nullptr) + { + const char endLine = '\n'; + std::string::size_type beginPos = 0; + std::string::size_type endPos = what.find_first_of(endLine, beginPos); + while (endPos != std::string::npos) + { + s_time_estimator->add_gcode_line(what.substr(beginPos, endPos - beginPos + 1)); + + beginPos = endPos + 1; + endPos = what.find_first_of(endLine, beginPos); + } + } + } + } +}; + +//std::string Write::s_cache = ""; +GCodeTimeEstimator* Write::s_time_estimator = nullptr; + inline void write(FILE *file, const std::string &what) { - fwrite(what.data(), 1, what.size(), file); + Write::write(file, what); +} + +inline void write_format(FILE* file, const char* format, ...) +{ + char buffer[1024]; + va_list args; + va_start(args, format); + int res = ::vsnprintf(buffer, 1024, format, args); + va_end(args); + + if (res >= 0) + write(file, buffer); } // Write a string into a file. Add a newline, if the string does not end with a newline already. @@ -277,9 +326,10 @@ inline void write(FILE *file, const std::string &what) inline void writeln(FILE *file, const std::string &what) { if (! what.empty()) { - write(file, what); if (what.back() != '\n') - fprintf(file, "\n"); + write_format(file, "%s\n", what.c_str()); + else + write(file, what); } } @@ -395,6 +445,7 @@ void GCode::do_export(Print *print, const char *path) msg += " !!!!! End of an error report for the custom G-code template ...\n"; throw std::runtime_error(msg); } + if (boost::nowide::rename(path_tmp.c_str(), path) != 0) throw std::runtime_error( std::string("Failed to rename the output G-code file from ") + path_tmp + " to " + path + '\n' + @@ -403,6 +454,10 @@ void GCode::do_export(Print *print, const char *path) void GCode::_do_export(Print &print, FILE *file) { + // resets time estimator + m_time_estimator.reset(); + Write::set_time_estimator(&m_time_estimator); + // How many times will be change_layer() called? // change_layer() in turn increments the progress bar status. m_layer_count = 0; @@ -498,7 +553,7 @@ void GCode::_do_export(Print &print, FILE *file) fprintf(file, "; %s\n", line.c_str()); } if (! lines.empty()) - fprintf(file, "\n"); + fprintf(file, "\n"); } // Write some terse information on the slicing parameters. { @@ -560,7 +615,7 @@ void GCode::_do_export(Print &print, FILE *file) // Disable fan. if (! print.config.cooling.get_at(initial_extruder_id) || print.config.disable_fan_first_layers.get_at(initial_extruder_id)) - write(file, m_writer.set_fan(0, true)); + write(file, m_writer.set_fan(0, true)); // Let the start-up script prime the 1st printing tool. m_placeholder_parser.set("initial_tool", initial_extruder_id); @@ -729,15 +784,15 @@ void GCode::_do_export(Print &print, FILE *file) bbox_prime.offset(0.5f); // Beep for 500ms, tone 800Hz. Yet better, play some Morse. write(file, this->retract()); - fprintf(file, "M300 S800 P500\n"); + write(file, "M300 S800 P500\n"); if (bbox_prime.overlap(bbox_print)) { // Wait for the user to remove the priming extrusions, otherwise they would // get covered by the print. - fprintf(file, "M1 Remove priming towers and click button.\n"); + write(file, "M1 Remove priming towers and click button.\n"); } else { // Just wait for a bit to let the user check, that the priming succeeded. //TODO Add a message explaining what the printer is waiting for. This needs a firmware fix. - fprintf(file, "M1 S10\n"); + write(file, "M1 S10\n"); } } // Extrude the layers. @@ -769,12 +824,16 @@ void GCode::_do_export(Print &print, FILE *file) write(file, m_writer.update_progress(m_layer_count, m_layer_count, true)); // 100% write(file, m_writer.postamble()); + // calculates estimated printing time + m_time_estimator.calculate_time(); + // Get filament stats. print.filament_stats.clear(); print.total_used_filament = 0.; print.total_extruded_volume = 0.; print.total_weight = 0.; print.total_cost = 0.; + print.estimated_print_time = (double)m_time_estimator.get_time() / 60.0; for (const Extruder &extruder : m_writer.extruders()) { double used_filament = extruder.used_filament(); double extruded_volume = extruder.extruded_volume(); @@ -794,6 +853,7 @@ void GCode::_do_export(Print &print, FILE *file) print.total_extruded_volume = print.total_extruded_volume + extruded_volume; } fprintf(file, "; total filament cost = %.1lf\n", print.total_cost); + fprintf(file, "; estimated printing time = %s\n", m_time_estimator.get_time_hms()); // Append full config. fprintf(file, "\n"); |