diff --git a/.travis.yml b/.travis.yml index a2e58f228..fecb82a8d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -139,7 +139,7 @@ script: ### I2C PANELS ### # # LCD_I2C_SAINSMART_YWROBOT - # Failing at the moment needs different library + # Failing at the moment needs different library #- restore_configs #- opt_enable LCD_I2C_SAINSMART_YWROBOT #- build_marlin @@ -199,6 +199,12 @@ script: - opt_set_adv Z2_MAX_PIN 2 - build_marlin # + # Test PRINTCOUNTER + # + - restore_configs + - opt_enable PRINTCOUNTER + - build_marlin + # # ######## Example Configurations ############## # diff --git a/Marlin/Configuration.h b/Marlin/Configuration.h index 37e5ea20b..e0b9a2ff4 100644 --- a/Marlin/Configuration.h +++ b/Marlin/Configuration.h @@ -757,6 +757,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/Marlin.h b/Marlin/Marlin.h index cc08d724b..9cd13c90e 100644 --- a/Marlin/Marlin.h +++ b/Marlin/Marlin.h @@ -65,7 +65,11 @@ typedef unsigned long millis_t; #include "WString.h" -#include "stopwatch.h" +#if ENABLED(PRINTCOUNTER) + #include "printcounter.h" +#else + #include "stopwatch.h" +#endif #ifdef USBCON #if ENABLED(BLUETOOTH) @@ -364,7 +368,11 @@ extern bool axis_homed[3]; // axis[n].is_homed #endif // Print job timer -extern Stopwatch print_job_timer; +#if ENABLED(PRINTCOUNTER) + extern PrintCounter print_job_timer; +#else + extern Stopwatch print_job_timer; +#endif // Handling multiple extruders pins extern uint8_t active_extruder; diff --git a/Marlin/Marlin_main.cpp b/Marlin/Marlin_main.cpp index eac4acf10..18d69cada 100644 --- a/Marlin/Marlin_main.cpp +++ b/Marlin/Marlin_main.cpp @@ -137,6 +137,10 @@ * M33 - Get the longname version of a path * M42 - Change pin status via gcode Use M42 Px Sy to set pin x to value y, when omitting Px the onboard led will be used. * M48 - Measure Z_Probe repeatability. M48 [P # of points] [X position] [Y position] [V_erboseness #] [E_ngage Probe] [L # of legs of travel] + * M75 - Start the print job timer + * M76 - Pause the print job timer + * M77 - Stop the print job timer + * M78 - Show statistical information about the print jobs * M80 - Turn on Power Supply * M81 - Turn off Power Supply * M82 - Set E codes absolute (default) @@ -327,7 +331,11 @@ static millis_t max_inactive_time = 0; static millis_t stepper_inactive_time = (DEFAULT_STEPPER_DEACTIVE_TIME) * 1000UL; // Print Job Timer -Stopwatch print_job_timer = Stopwatch(); +#if ENABLED(PRINTCOUNTER) + PrintCounter print_job_timer = PrintCounter(); +#else + Stopwatch print_job_timer = Stopwatch(); +#endif static uint8_t target_extruder; @@ -4252,6 +4260,15 @@ inline void gcode_M77() { print_job_timer.stop(); } +#if ENABLED(PRINTCOUNTER) + /*+ + * M78: Show print statistics + */ + inline void gcode_M78() { + print_job_timer.showStats(); + } +#endif + /** * M104: Set hot end temperature */ @@ -6641,6 +6658,12 @@ void process_next_command() { gcode_M77(); break; + #if ENABLED(PRINTCOUNTER) + case 78: // Show print statistics + gcode_M78(); + break; + #endif + #if ENABLED(M100_FREE_MEMORY_WATCHER) case 100: gcode_M100(); @@ -7755,6 +7778,9 @@ void idle( ); host_keepalive(); lcd_update(); + #if ENABLED(PRINTCOUNTER) + print_job_timer.tick(); + #endif } /** diff --git a/Marlin/example_configurations/Felix/Configuration.h b/Marlin/example_configurations/Felix/Configuration.h index 017888c70..1209c667b 100644 --- a/Marlin/example_configurations/Felix/Configuration.h +++ b/Marlin/example_configurations/Felix/Configuration.h @@ -739,6 +739,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/Hephestos/Configuration.h b/Marlin/example_configurations/Hephestos/Configuration.h index d971dbb51..b9201e5b3 100644 --- a/Marlin/example_configurations/Hephestos/Configuration.h +++ b/Marlin/example_configurations/Hephestos/Configuration.h @@ -748,6 +748,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = true; // set to true to invert the lo #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/Hephestos_2/Configuration.h b/Marlin/example_configurations/Hephestos_2/Configuration.h index 2f51a9b46..6217383a8 100644 --- a/Marlin/example_configurations/Hephestos_2/Configuration.h +++ b/Marlin/example_configurations/Hephestos_2/Configuration.h @@ -750,6 +750,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/K8200/Configuration.h b/Marlin/example_configurations/K8200/Configuration.h index 23a376742..ddd3edd2a 100644 --- a/Marlin/example_configurations/K8200/Configuration.h +++ b/Marlin/example_configurations/K8200/Configuration.h @@ -773,6 +773,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 60 // K8200: set back to 110 if you have an upgraded heatbed power supply #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/RepRapWorld/Megatronics/Configuration.h b/Marlin/example_configurations/RepRapWorld/Megatronics/Configuration.h index 5ce12bbd6..8010cd7e6 100644 --- a/Marlin/example_configurations/RepRapWorld/Megatronics/Configuration.h +++ b/Marlin/example_configurations/RepRapWorld/Megatronics/Configuration.h @@ -756,6 +756,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/RigidBot/Configuration.h b/Marlin/example_configurations/RigidBot/Configuration.h index 4c0d912a9..c9dada365 100644 --- a/Marlin/example_configurations/RigidBot/Configuration.h +++ b/Marlin/example_configurations/RigidBot/Configuration.h @@ -1,4 +1,4 @@ -/** +f/** * Marlin 3D Printer Firmware * Copyright (C) 2016 MarlinFirmware [https://github.com/MarlinFirmware/Marlin] * @@ -751,6 +751,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/SCARA/Configuration.h b/Marlin/example_configurations/SCARA/Configuration.h index e5e13c19d..2acd5f337 100644 --- a/Marlin/example_configurations/SCARA/Configuration.h +++ b/Marlin/example_configurations/SCARA/Configuration.h @@ -764,6 +764,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/TAZ4/Configuration.h b/Marlin/example_configurations/TAZ4/Configuration.h index 68f1cd99e..0a6e093b6 100644 --- a/Marlin/example_configurations/TAZ4/Configuration.h +++ b/Marlin/example_configurations/TAZ4/Configuration.h @@ -777,6 +777,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/WITBOX/Configuration.h b/Marlin/example_configurations/WITBOX/Configuration.h index 390ede3ec..81db59816 100644 --- a/Marlin/example_configurations/WITBOX/Configuration.h +++ b/Marlin/example_configurations/WITBOX/Configuration.h @@ -748,6 +748,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = true; // set to true to invert the lo #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/adafruit/ST7565/Configuration.h b/Marlin/example_configurations/adafruit/ST7565/Configuration.h index 4f23b136c..c7d69f79f 100644 --- a/Marlin/example_configurations/adafruit/ST7565/Configuration.h +++ b/Marlin/example_configurations/adafruit/ST7565/Configuration.h @@ -756,6 +756,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 110 #define ABS_PREHEAT_FAN_SPEED 0 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/delta/biv2.5/Configuration.h b/Marlin/example_configurations/delta/biv2.5/Configuration.h index 50ebe27ce..0c77a1177 100644 --- a/Marlin/example_configurations/delta/biv2.5/Configuration.h +++ b/Marlin/example_configurations/delta/biv2.5/Configuration.h @@ -885,6 +885,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = true; // set to true to invert the lo #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/delta/generic/Configuration.h b/Marlin/example_configurations/delta/generic/Configuration.h index c84aeb3b0..6e7691636 100644 --- a/Marlin/example_configurations/delta/generic/Configuration.h +++ b/Marlin/example_configurations/delta/generic/Configuration.h @@ -885,6 +885,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = true; // set to true to invert the lo #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/delta/kossel_mini/Configuration.h b/Marlin/example_configurations/delta/kossel_mini/Configuration.h index 63e2014ef..c04781810 100644 --- a/Marlin/example_configurations/delta/kossel_mini/Configuration.h +++ b/Marlin/example_configurations/delta/kossel_mini/Configuration.h @@ -889,6 +889,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/delta/kossel_pro/Configuration.h b/Marlin/example_configurations/delta/kossel_pro/Configuration.h index 038305958..c8093b161 100644 --- a/Marlin/example_configurations/delta/kossel_pro/Configuration.h +++ b/Marlin/example_configurations/delta/kossel_pro/Configuration.h @@ -882,6 +882,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/delta/kossel_xl/Configuration.h b/Marlin/example_configurations/delta/kossel_xl/Configuration.h index 579999ba1..73e49c7e5 100644 --- a/Marlin/example_configurations/delta/kossel_xl/Configuration.h +++ b/Marlin/example_configurations/delta/kossel_xl/Configuration.h @@ -890,6 +890,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/makibox/Configuration.h b/Marlin/example_configurations/makibox/Configuration.h index 77adce269..416765b25 100644 --- a/Marlin/example_configurations/makibox/Configuration.h +++ b/Marlin/example_configurations/makibox/Configuration.h @@ -759,6 +759,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = false; // set to true to invert the l #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/example_configurations/tvrrug/Round2/Configuration.h b/Marlin/example_configurations/tvrrug/Round2/Configuration.h index 425914893..65fd6aacc 100644 --- a/Marlin/example_configurations/tvrrug/Round2/Configuration.h +++ b/Marlin/example_configurations/tvrrug/Round2/Configuration.h @@ -750,6 +750,19 @@ const bool Z_MIN_PROBE_ENDSTOP_INVERTING = true; // set to true to invert the lo #define ABS_PREHEAT_HPB_TEMP 100 #define ABS_PREHEAT_FAN_SPEED 255 // Insert Value between 0 and 255 + +// +// Print Counter +// +// When enabled Marlin will keep track of some print statistical data such as: +// - Total print jobs +// - Total successful print jobs +// - Total failed print jobs +// - Total time printing +// +// This information can be viewed by the M78 command. +//#define PRINTCOUNTER + //============================================================================= //============================= LCD and SD support ============================ //============================================================================= diff --git a/Marlin/printcounter.cpp b/Marlin/printcounter.cpp new file mode 100644 index 000000000..59b8bc3e3 --- /dev/null +++ b/Marlin/printcounter.cpp @@ -0,0 +1,179 @@ +/* + * Marlin 3D Printer Firmware + * Copyright (C) 2016 MarlinFirmware [https://github.com/MarlinFirmware/Marlin] + * + * Based on Sprinter and grbl. + * Copyright (C) 2011 Camiel Gubbels / Erik van der Zalm + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + */ + +#include "Marlin.h" +#include "printcounter.h" +#include + +PrintCounter::PrintCounter(): super() { + this->loadStats(); +} + +uint16_t PrintCounter::deltaDuration() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("deltaDuration")); + #endif + + uint16_t tmp = this->lastDuration; + this->lastDuration = this->duration(); + return this->lastDuration - tmp; +} + +bool PrintCounter::isLoaded() { + return this->loaded; +} + +void PrintCounter::initStats() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("initStats")); + #endif + + this->loaded = true; + this->data = { 0, 0, 0, 0 }; + + this->saveStats(); + eeprom_write_byte((uint8_t *) this->address, 0x16); +} + +void PrintCounter::loadStats() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("loadStats")); + #endif + + // Checks if the EEPROM block is initialized + if (eeprom_read_byte((uint8_t *) this->address) != 0x16) this->initStats(); + else eeprom_read_block(&this->data, (void *)(this->address + sizeof(uint8_t)), sizeof(printStatistics)); + + this->loaded = true; +} + +void PrintCounter::saveStats() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("saveStats")); + #endif + + // Refuses to save data is object is not loaded + if (!this->isLoaded()) return; + + eeprom_update_block(&this->data, (void *)(this->address + sizeof(uint8_t)), sizeof(printStatistics)); +} + +void PrintCounter::showStats() { + SERIAL_ECHOPGM("Print statistics: Total: "); + SERIAL_ECHO(this->data.totalPrints); + + SERIAL_ECHOPGM(", Finished: "); + SERIAL_ECHO(this->data.finishedPrints); + + SERIAL_ECHOPGM(", Failed: "); + SERIAL_ECHO(this->data.totalPrints - this->data.finishedPrints + - (this->isRunning() || this->isPaused()) ? 1 : 0); // Removes 1 from failures with an active counter + + uint32_t t = this->data.printTime /60; + SERIAL_ECHOPGM(", Total print time: "); + SERIAL_ECHO(t / 60); + + SERIAL_ECHOPGM("h "); + SERIAL_ECHO(t % 60); + + SERIAL_ECHOPGM("min"); + + #if ENABLED(DEBUG_PRINTCOUNTER) + SERIAL_ECHOPGM(" ("); + SERIAL_ECHO(this->data.printTime); + SERIAL_ECHOPGM(")"); + #endif + + // @todo longestPrint missing implementation + SERIAL_EOL; +} + +void PrintCounter::tick() { + if (!this->isRunning()) return; + + static uint32_t update_before = millis(), + eeprom_before = millis(); + + uint32_t now = millis(); + + // Trying to get the amount of calculations down to the bare min + const static uint16_t i = this->updateInterval * 1000; + + if (now - update_before >= i) { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("tick")); + #endif + + uint16_t t = this->duration();; + this->data.printTime += this->deltaDuration(); + update_before = now; + } + + // Trying to get the amount of calculations down to the bare min + const static uint16_t j = this->saveInterval * 1000; + + if (now - eeprom_before >= j) { + eeprom_before = now; + this->saveStats(); + } +} + +void PrintCounter::start() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("start")); + #endif + + if (!this->isPaused()) this->data.totalPrints++; + super::start(); +} + +void PrintCounter::stop() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("stop")); + #endif + + super::stop(); + this->data.finishedPrints++; + this->data.printTime += this->deltaDuration(); + this->saveStats(); +} + +void PrintCounter::reset() { + #if ENABLED(DEBUG_PRINTCOUNTER) + PrintCounter::debug(PSTR("stop")); + #endif + + this->lastDuration = 0; + super::reset(); +} + +#if ENABLED(DEBUG_PRINTCOUNTER) + + void PrintCounter::debug(const char func[]) { + if (DEBUGGING(INFO)) { + SERIAL_ECHOPGM("PrintCounter::"); + serialprintPGM(func); + SERIAL_ECHOLNPGM("()"); + } + } + +#endif diff --git a/Marlin/printcounter.h b/Marlin/printcounter.h new file mode 100644 index 000000000..b44caeefd --- /dev/null +++ b/Marlin/printcounter.h @@ -0,0 +1,154 @@ +/* + * Marlin 3D Printer Firmware + * Copyright (C) 2016 MarlinFirmware [https://github.com/MarlinFirmware/Marlin] + * + * Based on Sprinter and grbl. + * Copyright (C) 2011 Camiel Gubbels / Erik van der Zalm + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + * + */ + +#ifndef PRINTCOUNTER_H +#define PRINTCOUNTER_H + +#include "macros.h" +#include "stopwatch.h" + +// Print debug messages with M111 S2 +//#define DEBUG_PRINTCOUNTER + +struct printStatistics { // 13 bytes + //const uint8_t magic; // Magic header, it will always be 0x16 + uint16_t totalPrints; // Number of prints + uint16_t finishedPrints; // Number of complete prints + uint32_t printTime; // Total printing time + uint32_t longestPrint; // Longest print job - not in use +}; + +class PrintCounter: public Stopwatch { + private: + typedef Stopwatch super; + + printStatistics data; + + /** + * @brief EEPROM address + * @details Defines the start offset address where the data is stored. + */ + const uint16_t address = 0x32; + + /** + * @brief Interval in seconds between counter updates + * @details This const value defines what will be the time between each + * accumulator update. This is different from the EEPROM save interval. + */ + const uint16_t updateInterval = 10; + + /** + * @brief Interval in seconds between EEPROM saves + * @details This const value defines what will be the time between each + * EEPROM save cycle, the development team recommends to set this value + * no lower than 3600 secs (1 hour). + */ + const uint16_t saveInterval = 3600; + + /** + * @brief Timestamp of the last call to deltaDuration() + * @details Stores the timestamp of the last deltaDuration(), this is + * required due to the updateInterval cycle. + */ + uint16_t lastDuration; + + /** + * @brief Stats were loaded from EERPROM + * @details If set to true it indicates if the statistical data was already + * loaded from the EEPROM. + */ + bool loaded = false; + + protected: + /** + * @brief dT since the last call + * @details Returns the elapsed time in seconds since the last call, this is + * used internally for print statistics accounting is not intended to be a + * user callable function. + */ + uint16_t deltaDuration(); + + public: + /** + * @brief Class constructor + */ + PrintCounter(); + + /** + * @brief Checks if Print Statistics has been loaded + * @details Returns true if the statistical data has been loaded. + * @return bool + */ + bool isLoaded(); + + /** + * @brief Resets the Print Statistics + * @details Resets the statistics to zero and saves them to EEPROM creating + * also the magic header. + */ + void initStats(); + + /** + * @brief Loads the Print Statistics + * @details Loads the statistics from EEPROM + */ + void loadStats(); + + /** + * @brief Saves the Print Statistics + * @details Saves the statistics to EEPROM + */ + void saveStats(); + + /** + * @brief Serial output the Print Statistics + * @details This function may change in the future, for now it directly + * prints the statistical data to serial. + */ + void showStats(); + + /** + * @brief Loop function + * @details This function should be called at loop, it will take care of + * periodically save the statistical data to EEPROM and do time keeping. + */ + void tick(); + + /** + * The following functions are being overridden + */ + void start(); + void stop(); + void reset(); + + #if ENABLED(DEBUG_PRINTCOUNTER) + + /** + * @brief Prints a debug message + * @details Prints a simple debug message "PrintCounter::function" + */ + static void debug(const char func[]); + + #endif +}; + +#endif // PRINTCOUNTER_H diff --git a/Marlin/stopwatch.cpp b/Marlin/stopwatch.cpp index f871af1c7..4a1344db1 100644 --- a/Marlin/stopwatch.cpp +++ b/Marlin/stopwatch.cpp @@ -29,7 +29,7 @@ Stopwatch::Stopwatch() { void Stopwatch::stop() { #if ENABLED(DEBUG_STOPWATCH) - debug(PSTR("stop")); + Stopwatch::debug(PSTR("stop")); #endif if (!this->isRunning()) return; @@ -40,7 +40,7 @@ void Stopwatch::stop() { void Stopwatch::pause() { #if ENABLED(DEBUG_STOPWATCH) - debug(PSTR("pause")); + Stopwatch::debug(PSTR("pause")); #endif if (!this->isRunning()) return; @@ -51,7 +51,7 @@ void Stopwatch::pause() { void Stopwatch::start() { #if ENABLED(DEBUG_STOPWATCH) - debug(PSTR("start")); + Stopwatch::debug(PSTR("start")); #endif if (this->isRunning()) return; @@ -65,7 +65,7 @@ void Stopwatch::start() { void Stopwatch::reset() { #if ENABLED(DEBUG_STOPWATCH) - debug(PSTR("reset")); + Stopwatch::debug(PSTR("reset")); #endif this->state = STPWTCH_STOPPED;