diff options
Diffstat (limited to 'Sprinter')
-rw-r--r-- | Sprinter/Configuration.h | 34 | ||||
-rw-r--r-- | Sprinter/Sd2Card.cpp | 4 | ||||
-rw-r--r-- | Sprinter/SdFatUtil.h | 4 | ||||
-rw-r--r-- | Sprinter/SdFile.cpp | 4 | ||||
-rw-r--r-- | Sprinter/Sprinter.h | 4 | ||||
-rw-r--r-- | Sprinter/Sprinter.pde | 425 | ||||
-rw-r--r-- | Sprinter/arc_func.cpp | 2 | ||||
-rw-r--r-- | Sprinter/heater.cpp | 404 | ||||
-rw-r--r-- | Sprinter/heater.h | 9 | ||||
-rw-r--r-- | Sprinter/pins.h | 14 | ||||
-rw-r--r-- | Sprinter/store_eeprom.cpp | 2 | ||||
-rw-r--r-- | Sprinter/thermistortables.h | 4 |
12 files changed, 773 insertions, 137 deletions
diff --git a/Sprinter/Configuration.h b/Sprinter/Configuration.h index a9243d2..382741e 100644 --- a/Sprinter/Configuration.h +++ b/Sprinter/Configuration.h @@ -7,6 +7,7 @@ // MEGA/RAMPS up to 1.2 = 3, // RAMPS 1.3/1.4 = 33 // Gen6 = 5, +// Gen6 deluxe = 51 // Sanguinololu up to 1.1 = 6 // Sanguinololu 1.2 and above = 62 // Gen 7 @ 16MHZ only= 7 @@ -152,6 +153,10 @@ const int NUM_AXIS = 4; // The axis order in all axis related arrays is X, Y, Z, #define MAX_STEP_FREQUENCY 30000 // Max step frequency +//For the retract (negative Extruder) move this maxiumum Limit of Feedrate is used +//The next positive Extruder move use also this Limit, +//then for the next (second after retract) move the original Maximum (_MAX_FEEDRATE) Limit is used +#define MAX_RETRACT_FEEDRATE 100 //mm/sec //----------------------------------------------------------------------- //// Not used at the Moment @@ -166,7 +171,9 @@ const int NUM_AXIS = 4; // The axis order in all axis related arrays is X, Y, Z, //#define STEP_DELAY_RATIO 0.25 ///Oscillation reduction. Forces x,y,or z axis to be stationary for ## ms before allowing axis to switch direcitons. Alternative method to prevent skipping steps. Uncomment the line below to activate. +// At this Version with Planner this Function ist not used //#define RAPID_OSCILLATION_REDUCTION + #ifdef RAPID_OSCILLATION_REDUCTION const long min_time_before_dir_change = 30; //milliseconds #endif @@ -231,6 +238,26 @@ const int dropsegments=5; //everything with less than this number of steps will #define N_ARC_CORRECTION 25 //----------------------------------------------------------------------- +//// FANCONTROL WITH SOFT PWM +//----------------------------------------------------------------------- + +//With this option its possible to drive the fan with SOFT PWM (500hz) and use +//every Digital output for it, main usage for Sanguinololu +#define FAN_SOFT_PWM + +//----------------------------------------------------------------------- +//// MINIMUM START SPEED FOR FAN +//----------------------------------------------------------------------- + +//Minimum start speed for FAN when the last speed was zero +//Set to 0 to deaktivate +//If value is set the fan will drive with this minimum speed for MINIMUM_FAN_START_TIME +#define MINIMUM_FAN_START_SPEED 0 + +//This is the time how long the minimum FAN speed is set +#define MINIMUM_FAN_START_TIME 6000 //6sec + +//----------------------------------------------------------------------- //// HEATERCONTROL AND PID PARAMETERS //----------------------------------------------------------------------- @@ -261,6 +288,10 @@ const int dropsegments=5; //everything with less than this number of steps will //Command M601 / Command M602 Reset the MIN/MAX Value //#define DEBUG_HEATER_TEMP +// M303 - PID relay autotune S<temperature> sets the target temperature. +// (default target temperature = 150C) +#define PID_AUTOTUNE + //PID Controler Settings #define PID_INTEGRAL_DRIVE_MAX 80 // too big, and heater will lag after changing temperature, too small and it might not compensate enough for long-term errors #define PID_PGAIN 2560 //256 is 1.0 // value of X means that error of 1 degree is changing PWM duty by X, probably no need to go over 25 @@ -331,6 +362,9 @@ const int dropsegments=5; //everything with less than this number of steps will //#define CONTROLLERFAN_PIN 23 //Pin used for the fan to cool controller, comment out to disable this function #define CONTROLLERFAN_SEC 60 //How many seconds, after all motors were disabled, the fan should run +//This is for controlling a fan that will keep the extruder cool. +//#define EXTRUDERFAN_PIN 66 //Pin used to control the fan, comment out to disable this function +#define EXTRUDERFAN_DEC 50 //Hotend temperature from where the fan will be turned on //----------------------------------------------------------------------- // DEBUGING diff --git a/Sprinter/Sd2Card.cpp b/Sprinter/Sd2Card.cpp index 8222cfd..05832e7 100644 --- a/Sprinter/Sd2Card.cpp +++ b/Sprinter/Sd2Card.cpp @@ -17,7 +17,11 @@ * along with the Arduino Sd2Card Library. If not, see
* <http://www.gnu.org/licenses/>.
*/
+#if defined(ARDUINO) && ARDUINO >= 100
+#include <Arduino.h>
+#else
#include <WProgram.h>
+#endif
#include "Sd2Card.h"
//------------------------------------------------------------------------------
#ifndef SOFTWARE_SPI
diff --git a/Sprinter/SdFatUtil.h b/Sprinter/SdFatUtil.h index de3fee3..361a5a2 100644 --- a/Sprinter/SdFatUtil.h +++ b/Sprinter/SdFatUtil.h @@ -23,7 +23,11 @@ * \file
* Useful utility functions.
*/
+#if defined(ARDUINO) && ARDUINO >= 100
+#include <Arduino.h>
+#else
#include <WProgram.h>
+#endif
#include <avr/pgmspace.h>
/** Store and print a string in flash memory.*/
#define PgmPrint(x) SerialPrint_P(PSTR(x))
diff --git a/Sprinter/SdFile.cpp b/Sprinter/SdFile.cpp index 13f4c6a..c847e01 100644 --- a/Sprinter/SdFile.cpp +++ b/Sprinter/SdFile.cpp @@ -19,7 +19,11 @@ */ #include "SdFat.h" #include <avr/pgmspace.h> +#if defined(ARDUINO) && ARDUINO >= 100 +#include <Arduino.h> +#else #include <WProgram.h> +#endif //------------------------------------------------------------------------------ // callback function for date/time void (*SdFile::dateTime_)(uint16_t* date, uint16_t* time) = NULL; diff --git a/Sprinter/Sprinter.h b/Sprinter/Sprinter.h index 66e6c59..50f3806 100644 --- a/Sprinter/Sprinter.h +++ b/Sprinter/Sprinter.h @@ -123,6 +123,10 @@ void check_buffer_while_arc(); void print_disk_info(void); #endif //SDSUPPORT +#if (MINIMUM_FAN_START_SPEED > 0) +void manage_fan_start_speed(void); +#endif + #ifdef DEBUG void log_message(char* message); void log_bool(char* message, bool value); diff --git a/Sprinter/Sprinter.pde b/Sprinter/Sprinter.pde index 8359fed..50314b0 100644 --- a/Sprinter/Sprinter.pde +++ b/Sprinter/Sprinter.pde @@ -94,9 +94,32 @@ - Make fastio & Arduino pin numbering consistent for AT90USB128x. --> Thanks to lincomatic - Select Speedtable with F_CPU - Use same Values for Speedtables as Marlin -- +- + Version 1.3.12T +- Fixed arc offset. + + Version 1.3.13T +- Extrudmultiply with code M221 Sxxx (S100 original Extrude value) +- use Feedratefaktor only when Extrude > 0 +- M106 / M107 can drive the FAN with PWM + Port check for not using Timer 1 +- Added M93 command. Sends current steps for all axis. +- New Option --> FAN_SOFT_PWM, with this option the FAN PWM can use every digital I/O + + Version 1.3.14T +- When endstop is hit count the virtual steps, so the print lose no position when endstop is hit + + Version 1.3.15T +- M206 - set additional homeing offset +- Option for minimum FAN start speed --> #define MINIMUM_FAN_START_SPEED 50 (set it to zero to deaktivate) + Version 1.3.16T +- Extra Max Feedrate for Retract (MAX_RETRACT_FEEDRATE) + + Version 1.3.17T +- M303 - PID relay autotune possible +- G4 Wait until last move is done + */ @@ -173,6 +196,7 @@ void __cxa_pure_virtual(){}; // or use S<seconds> to specify an inactivity timeout, after which the steppers will be disabled. S0 to disable the timeout. // M85 - Set inactivity shutdown timer with parameter S<seconds>. To disable set zero (default) // M92 - Set axis_steps_per_unit - same syntax as G92 +// M93 - Send axis_steps_per_unit // M115 - Capabilities string // M119 - Show Endstopper State // M140 - Set bed target temp @@ -182,8 +206,14 @@ void __cxa_pure_virtual(){}; // M203 - Set temperture monitor to Sx // M204 - Set default acceleration: S normal moves T filament only moves (M204 S3000 T7000) im mm/sec^2 // M205 - advanced settings: minimum travel speed S=while printing T=travel only, X= maximum xy jerk, Z=maximum Z jerk +// M206 - set additional homeing offset // M220 - set speed factor override percentage S:factor in percent +// M221 - set extruder multiply factor S100 --> original Extrude Speed + +// M303 - PID relay autotune S<temperature> sets the target temperature. (default target temperature = 150C) + +// M400 - Finish all moves // M500 - stores paramters in EEPROM // M501 - reads parameters from EEPROM (if you need reset them after you changed them temporarily). @@ -196,7 +226,7 @@ void __cxa_pure_virtual(){}; // M603 - Show Free Ram -#define _VERSION_TEXT "1.3.11T / 19.03.2012" +#define _VERSION_TEXT "1.3.17T / 04.05.2012" //Stepper Movement Variables char axis_codes[NUM_AXIS] = {'X', 'Y', 'Z', 'E'}; @@ -232,12 +262,17 @@ unsigned long plateau_steps; volatile int feedmultiply=100; //100->original / 200-> Faktor 2 / 50 -> Faktor 0.5 int saved_feedmultiply; volatile bool feedmultiplychanged=false; +volatile int extrudemultiply=100; //100->1 200->2 //boolean acceleration_enabled = false, accelerating = false; //unsigned long interval; float destination[NUM_AXIS] = {0.0, 0.0, 0.0, 0.0}; float current_position[NUM_AXIS] = {0.0, 0.0, 0.0, 0.0}; +float add_homeing[3]={0,0,0}; +static unsigned short virtual_steps_x = 0; +static unsigned short virtual_steps_y = 0; +static unsigned short virtual_steps_z = 0; bool home_all_axis = true; //unsigned ?? ToDo: Check @@ -275,6 +310,12 @@ float offset[3] = {0.0, 0.0, 0.0}; float osc_wait_remainder = 0.0; #endif +#if (MINIMUM_FAN_START_SPEED > 0) + unsigned char fan_last_speed = 0; + unsigned char fan_org_start_speed = 0; + unsigned long previous_millis_fan_start = 0; +#endif + // comm variables and Commandbuffer // BUFSIZE is reduced from 8 to 6 to free more RAM for the PLANNER #define MAX_CMD_SIZE 96 @@ -782,7 +823,7 @@ void setup() #endif - #ifdef PID_SOFT_PWM + #if defined(PID_SOFT_PWM) || (defined(FAN_SOFT_PWM) && (FAN_PIN > -1)) showString(PSTR("Soft PWM Init\r\n")); init_Timer2_softpwm(); #endif @@ -856,6 +897,10 @@ void loop() //check heater every n milliseconds manage_heater(); manage_inactivity(1); + #if (MINIMUM_FAN_START_SPEED > 0) + manage_fan_start_speed(); + #endif + } //------------------------------------------------ @@ -875,10 +920,10 @@ void check_buffer_while_arc() //------------------------------------------------ void get_command() { - while( Serial.available() > 0 && buflen < BUFSIZE) + while( Serial.available() > 0 && buflen < BUFSIZE) { serial_char = Serial.read(); - if(serial_char == '\n' || serial_char == '\r' || serial_char == ':' || serial_count >= (MAX_CMD_SIZE - 1) ) + if(serial_char == '\n' || serial_char == '\r' || (serial_char == ':' && comment_mode == false) || serial_count >= (MAX_CMD_SIZE - 1) ) { if(!serial_count) { //if empty line comment_mode = false; // for new command @@ -984,12 +1029,12 @@ void get_command() { return; } - while( filesize > sdpos && buflen < BUFSIZE) + while( filesize > sdpos && buflen < BUFSIZE) { serial_char = file.read(); read_char_int = (int)serial_char; - if(serial_char == '\n' || serial_char == '\r' || serial_char == ':' || serial_count >= (MAX_CMD_SIZE - 1) || read_char_int == -1) + if(serial_char == '\n' || serial_char == '\r' || (serial_char == ':' && comment_mode == false) || serial_count >= (MAX_CMD_SIZE - 1) || read_char_int == -1) { sdpos = file.curPosition(); if(sdpos >= filesize) @@ -1084,6 +1129,7 @@ FORCE_INLINE void process_commands() if(code_seen('P')) codenum = code_value(); // milliseconds to wait if(code_seen('S')) codenum = code_value() * 1000; // seconds to wait codenum += millis(); // keep track of when we started waiting + st_synchronize(); // wait for all movements to finish while(millis() < codenum ){ manage_heater(); } @@ -1132,6 +1178,7 @@ FORCE_INLINE void process_commands() st_synchronize(); current_position[X_AXIS] = (X_HOME_DIR == -1) ? 0 : X_MAX_LENGTH; + current_position[X_AXIS] += add_homeing[0]; plan_set_position(current_position[X_AXIS], current_position[Y_AXIS], current_position[Z_AXIS], current_position[E_AXIS]); destination[X_AXIS] = current_position[X_AXIS]; feedrate = 0; @@ -1164,6 +1211,7 @@ FORCE_INLINE void process_commands() st_synchronize(); current_position[Y_AXIS] = (Y_HOME_DIR == -1) ? 0 : Y_MAX_LENGTH; + current_position[Y_AXIS] += add_homeing[1]; plan_set_position(current_position[X_AXIS], current_position[Y_AXIS], current_position[Z_AXIS], current_position[E_AXIS]); destination[Y_AXIS] = current_position[Y_AXIS]; feedrate = 0; @@ -1196,6 +1244,7 @@ FORCE_INLINE void process_commands() st_synchronize(); current_position[Z_AXIS] = (Z_HOME_DIR == -1) ? 0 : Z_MAX_LENGTH; + current_position[Z_AXIS] += add_homeing[2]; plan_set_position(current_position[X_AXIS], current_position[Y_AXIS], current_position[Z_AXIS], current_position[E_AXIS]); destination[Z_AXIS] = current_position[Z_AXIS]; feedrate = 0; @@ -1498,6 +1547,9 @@ FORCE_INLINE void process_commands() codenum = millis(); } manage_heater(); + #if (MINIMUM_FAN_START_SPEED > 0) + manage_fan_start_speed(); + #endif #ifdef TEMP_RESIDENCY_TIME /* start/restart the TEMP_RESIDENCY_TIME timer whenever we reach target temp for the first time or when current temp falls outside the hysteresis after target temp was reached */ @@ -1526,6 +1578,9 @@ FORCE_INLINE void process_commands() codenum = millis(); } manage_heater(); + #if (MINIMUM_FAN_START_SPEED > 0) + manage_fan_start_speed(); + #endif } #endif break; @@ -1533,18 +1588,51 @@ FORCE_INLINE void process_commands() case 106: //M106 Fan On if (code_seen('S')) { - WRITE(FAN_PIN, HIGH); - analogWrite_check(FAN_PIN, constrain(code_value(),0,255) ); + unsigned char l_fan_code_val = constrain(code_value(),0,255); + + #if (MINIMUM_FAN_START_SPEED > 0) + if(l_fan_code_val > 0 && fan_last_speed == 0) + { + if(l_fan_code_val < MINIMUM_FAN_START_SPEED) + { + fan_org_start_speed = l_fan_code_val; + l_fan_code_val = MINIMUM_FAN_START_SPEED; + previous_millis_fan_start = millis(); + } + fan_last_speed = l_fan_code_val; + } + else + { + fan_last_speed = l_fan_code_val; + fan_org_start_speed = 0; + } + #endif + + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + g_fan_pwm_val = l_fan_code_val; + #else + WRITE(FAN_PIN, HIGH); + analogWrite_check(FAN_PIN, l_fan_code_val; + #endif + } else { - WRITE(FAN_PIN, HIGH); - analogWrite_check(FAN_PIN, 255 ); + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + g_fan_pwm_val = 255; + #else + WRITE(FAN_PIN, HIGH); + analogWrite_check(FAN_PIN, 255 ); + #endif } break; case 107: //M107 Fan Off - analogWrite_check(FAN_PIN, 0); - WRITE(FAN_PIN, LOW); + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + g_fan_pwm_val = 0; + #else + analogWrite_check(FAN_PIN, 0); + WRITE(FAN_PIN, LOW); + #endif break; #endif #if (PS_ON_PIN > -1) @@ -1594,6 +1682,17 @@ FORCE_INLINE void process_commands() // all steps_per_unit related variables // } break; + case 93: // M93 show current axis steps. + showString(PSTR("ok ")); + showString(PSTR("X:")); + Serial.print(axis_steps_per_unit[0]); + showString(PSTR("Y:")); + Serial.print(axis_steps_per_unit[1]); + showString(PSTR("Z:")); + Serial.print(axis_steps_per_unit[2]); + showString(PSTR("E:")); + Serial.println(axis_steps_per_unit[3]); + break; case 115: // M115 showString(PSTR("FIRMWARE_NAME: Sprinter Experimental PROTOCOL_VERSION:1.0 MACHINE_TYPE:Mendel EXTRUDER_COUNT:1\r\n")); //Serial.println(uuid); @@ -1639,7 +1738,7 @@ FORCE_INLINE void process_commands() showString(PSTR("\r\n")); break; - case 201: // M201 + case 201: // M201 Set maximum acceleration in units/s^2 for print moves (M201 X1000 Y1000) for(int8_t i=0; i < NUM_AXIS; i++) { @@ -1679,18 +1778,46 @@ FORCE_INLINE void process_commands() //if(code_seen('B')) minsegmenttime = code_value() ; if(code_seen('X')) max_xy_jerk = code_value() ; if(code_seen('Z')) max_z_jerk = code_value() ; + break; + case 206: // M206 additional homeing offset + for(int8_t cnt_i=0; cnt_i < 3; cnt_i++) + { + if(code_seen(axis_codes[cnt_i])) add_homeing[cnt_i] = code_value(); + } break; case 220: // M220 S<factor in percent>- set speed factor override percentage { if(code_seen('S')) { feedmultiply = code_value() ; - if(feedmultiply < 20) feedmultiply = 20; - if(feedmultiply > 200) feedmultiply = 200; + feedmultiply = constrain(feedmultiply, 20, 200); feedmultiplychanged=true; } } break; + case 221: // M221 S<factor in percent>- set extrude factor override percentage + { + if(code_seen('S')) + { + extrudemultiply = code_value() ; + extrudemultiply = constrain(extrudemultiply, 40, 200); + } + } + break; +#ifdef PID_AUTOTUNE + case 303: // M303 PID autotune + { + float help_temp = 150.0; + if (code_seen('S')) help_temp=code_value(); + PID_autotune(help_temp); + } + break; +#endif + case 400: // M400 finish all moves + { + st_synchronize(); + } + break; #ifdef USE_EEPROM_SETTINGS case 500: // Store settings in EEPROM { @@ -1796,15 +1923,26 @@ FORCE_INLINE void get_coordinates() } #ifdef USE_ARC_FUNCTION -FORCE_INLINE void get_arc_coordinates() +void get_arc_coordinates() { get_coordinates(); - if(code_seen('I')) offset[0] = code_value(); - if(code_seen('J')) offset[1] = code_value(); + if(code_seen('I')) { + offset[0] = code_value(); + } + else { + offset[0] = 0.0; + } + if(code_seen('J')) { + offset[1] = code_value(); + } + else { + offset[1] = 0.0; + } } #endif + void prepare_move() { long help_feedrate = 0; @@ -1824,8 +1962,16 @@ void prepare_move() if (destination[Z_AXIS] > Z_MAX_LENGTH) destination[Z_AXIS] = Z_MAX_LENGTH; } } + + if(destination[E_AXIS] > current_position[E_AXIS]) + { + help_feedrate = ((long)feedrate*(long)feedmultiply); + } + else + { + help_feedrate = ((long)feedrate*(long)100); + } - help_feedrate = ((long)feedrate*(long)feedmultiply); plan_buffer_line(destination[X_AXIS], destination[Y_AXIS], destination[Z_AXIS], destination[E_AXIS], help_feedrate/6000.0); for(int i=0; i < NUM_AXIS; i++) @@ -1842,8 +1988,15 @@ void prepare_arc_move(char isclockwise) float r = hypot(offset[X_AXIS], offset[Y_AXIS]); // Compute arc radius for mc_arc long help_feedrate = 0; - - help_feedrate = ((long)feedrate*(long)feedmultiply); + if(destination[E_AXIS] > current_position[E_AXIS]) + { + help_feedrate = ((long)feedrate*(long)feedmultiply); + } + else + { + help_feedrate = ((long)feedrate*(long)100); + } + // Trace the arc mc_arc(current_position, destination, offset, X_AXIS, Y_AXIS, Z_AXIS, help_feedrate/6000.0, r, isclockwise); @@ -1892,8 +2045,27 @@ FORCE_INLINE void manage_inactivity(byte debug) check_axes_activity(); } - - +#if (MINIMUM_FAN_START_SPEED > 0) +void manage_fan_start_speed(void) +{ + if(fan_org_start_speed > 0) + { + if((millis() - previous_millis_fan_start) > MINIMUM_FAN_START_TIME ) + { + #if FAN_PIN > -1 + #if defined(FAN_SOFT_PWM) + g_fan_pwm_val = fan_org_start_speed; + #else + WRITE(FAN_PIN, HIGH); + analogWrite_check(FAN_PIN, fan_org_start_speed; + #endif + #endif + + fan_org_start_speed = 0; + } + } +} +#endif // Planner with Interrupt for Stepper @@ -2252,6 +2424,9 @@ void check_axes_activity() { float junction_deviation = 0.1; +float max_E_feedrate_calc = MAX_RETRACT_FEEDRATE; +bool retract_feedrate_aktiv = false; + // Add a new linear movement to the buffer. steps_x, _y and _z is the absolute position in // mm. Microseconds specify how many microseconds the move should take to perform. To aid acceleration // calculation the caller must also provide the physical length of the line in millimeters. @@ -2265,6 +2440,9 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) while(block_buffer_tail == next_buffer_head) { manage_heater(); manage_inactivity(1); + #if (MINIMUM_FAN_START_SPEED > 0) + manage_fan_start_speed(); + #endif } // The target position of the tool in absolute steps @@ -2287,6 +2465,8 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) block->steps_y = labs(target[Y_AXIS]-position[Y_AXIS]); block->steps_z = labs(target[Z_AXIS]-position[Z_AXIS]); block->steps_e = labs(target[E_AXIS]-position[E_AXIS]); + block->steps_e *= extrudemultiply; + block->steps_e /= 100; block->step_event_count = max(block->steps_x, max(block->steps_y, max(block->steps_z, block->steps_e))); // Bail if this is a zero-length block @@ -2297,7 +2477,25 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) if (target[X_AXIS] < position[X_AXIS]) { block->direction_bits |= (1<<X_AXIS); } if (target[Y_AXIS] < position[Y_AXIS]) { block->direction_bits |= (1<<Y_AXIS); } if (target[Z_AXIS] < position[Z_AXIS]) { block->direction_bits |= (1<<Z_AXIS); } - if (target[E_AXIS] < position[E_AXIS]) { block->direction_bits |= (1<<E_AXIS); } + if (target[E_AXIS] < position[E_AXIS]) + { + block->direction_bits |= (1<<E_AXIS); + //High Feedrate for retract + max_E_feedrate_calc = MAX_RETRACT_FEEDRATE; + retract_feedrate_aktiv = true; + } + else + { + if(retract_feedrate_aktiv) + { + if(block->steps_e > 0) + retract_feedrate_aktiv = false; + } + else + { + max_E_feedrate_calc = max_feedrate[E_AXIS]; + } + } #ifdef DELAY_ENABLE @@ -2311,12 +2509,12 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) enable_y(); delayMicroseconds(DELAY_ENABLE); } - if(if(block->steps_z != 0)) + if(block->steps_z != 0) { enable_z(); delayMicroseconds(DELAY_ENABLE); } - if(if(block->steps_e != 0)) + if(block->steps_e != 0) { enable_e(); delayMicroseconds(DELAY_ENABLE); @@ -2346,7 +2544,8 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) delta_mm[X_AXIS] = (target[X_AXIS]-position[X_AXIS])/axis_steps_per_unit[X_AXIS]; delta_mm[Y_AXIS] = (target[Y_AXIS]-position[Y_AXIS])/axis_steps_per_unit[Y_AXIS]; delta_mm[Z_AXIS] = (target[Z_AXIS]-position[Z_AXIS])/axis_steps_per_unit[Z_AXIS]; - delta_mm[E_AXIS] = (target[E_AXIS]-position[E_AXIS])/axis_steps_per_unit[E_AXIS]; + //delta_mm[E_AXIS] = (target[E_AXIS]-position[E_AXIS])/axis_steps_per_unit[E_AXIS]; + delta_mm[E_AXIS] = ((target[E_AXIS]-position[E_AXIS])/axis_steps_per_unit[E_AXIS])*extrudemultiply/100.0; if ( block->steps_x <= dropsegments && block->steps_y <= dropsegments && block->steps_z <= dropsegments ) { block->millimeters = fabs(delta_mm[E_AXIS]); @@ -2381,32 +2580,24 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) */ - // Calculate speed in mm/sec for each axis + // Calculate and limit speed in mm/sec for each axis float current_speed[4]; - for(int i=0; i < 4; i++) { - current_speed[i] = delta_mm[i] * inverse_second; - } - - // Limit speed per axis float speed_factor = 1.0; //factor <=1 do decrease speed - for(int i=0; i < 4; i++) { + for(int i=0; i < 3; i++) + { + current_speed[i] = delta_mm[i] * inverse_second; if(fabs(current_speed[i]) > max_feedrate[i]) speed_factor = min(speed_factor, max_feedrate[i] / fabs(current_speed[i])); } + + current_speed[E_AXIS] = delta_mm[E_AXIS] * inverse_second; + if(fabs(current_speed[E_AXIS]) > max_E_feedrate_calc) + speed_factor = min(speed_factor, max_E_feedrate_calc / fabs(current_speed[E_AXIS])); + // Correct the speed - if( speed_factor < 1.0) { -// Serial.print("speed factor : "); Serial.println(speed_factor); - for(int i=0; i < 4; i++) { - if(fabs(current_speed[i]) > max_feedrate[i]) - speed_factor = min(speed_factor, max_feedrate[i] / fabs(current_speed[i])); - /* - if(speed_factor < 0.1) { - Serial.print("speed factor : "); Serial.println(speed_factor); - Serial.print("current_speed"); Serial.print(i); Serial.print(" : "); Serial.println(current_speed[i]); - } - */ - } + if( speed_factor < 1.0) + { for(unsigned char i=0; i < 4; i++) { current_speed[i] *= speed_factor; } @@ -2554,6 +2745,12 @@ void plan_buffer_line(float x, float y, float z, float e, float feed_rate) st_wake_up(); } +int calc_plannerpuffer_fill(void) +{ + int moves_queued=(block_buffer_head-block_buffer_tail + BLOCK_BUFFER_SIZE) & (BLOCK_BUFFER_SIZE - 1); + return(moves_queued); +} + void plan_set_position(float x, float y, float z, float e) { position[X_AXIS] = lround(x*axis_steps_per_unit[X_AXIS]); @@ -2561,6 +2758,10 @@ void plan_set_position(float x, float y, float z, float e) position[Z_AXIS] = lround(z*axis_steps_per_unit[Z_AXIS]); position[E_AXIS] = lround(e*axis_steps_per_unit[E_AXIS]); + virtual_steps_x = 0; + virtual_steps_y = 0; + virtual_steps_z = 0; + previous_nominal_speed = 0.0; // Resets planner junction speeds. Assumes start from rest. previous_speed[0] = 0.0; previous_speed[1] = 0.0; @@ -2577,16 +2778,19 @@ void getHighESpeed() if((target_temp+2) < autotemp_min) //probably temperature set to zero. return; //do nothing - float high=0; + float high=0.0; uint8_t block_index = block_buffer_tail; - while(block_index != block_buffer_head) - { - float se=block_buffer[block_index].steps_e/float(block_buffer[block_index].step_event_count)*block_buffer[block_index].nominal_rate; - //se; units steps/sec; - if(se>high) - { - high=se; + while(block_index != block_buffer_head) { + if((block_buffer[block_index].steps_x != 0) || + (block_buffer[block_index].steps_y != 0) || + (block_buffer[block_index].steps_z != 0)) { + float se=(float(block_buffer[block_index].steps_e)/float(block_buffer[block_index].step_event_count))*block_buffer[block_index].nominal_speed; + //se; units steps/sec; + if(se>high) + { + high=se; + } } block_index = (block_index+1) & (BLOCK_BUFFER_SIZE - 1); } @@ -2848,10 +3052,18 @@ ISR(TIMER1_COMPA_vect) #if X_MIN_PIN > -1 bool x_min_endstop=(READ(X_MIN_PIN) != X_ENDSTOP_INVERT); if(x_min_endstop && old_x_min_endstop && (current_block->steps_x > 0)) { - endstop_x_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_x_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_x_hit=false; } old_x_min_endstop = x_min_endstop; + #else + endstop_x_hit=false; #endif } } @@ -2862,10 +3074,18 @@ ISR(TIMER1_COMPA_vect) #if X_MAX_PIN > -1 bool x_max_endstop=(READ(X_MAX_PIN) != X_ENDSTOP_INVERT); if(x_max_endstop && old_x_max_endstop && (current_block->steps_x > 0)){ - endstop_x_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_x_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_x_hit=false; } old_x_max_endstop = x_max_endstop; + #else + endstop_x_hit=false; #endif } } @@ -2877,10 +3097,18 @@ ISR(TIMER1_COMPA_vect) #if Y_MIN_PIN > -1 bool y_min_endstop=(READ(Y_MIN_PIN) != Y_ENDSTOP_INVERT); if(y_min_endstop && old_y_min_endstop && (current_block->steps_y > 0)) { - endstop_y_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_y_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_y_hit=false; } old_y_min_endstop = y_min_endstop; + #else + endstop_y_hit=false; #endif } } @@ -2891,10 +3119,18 @@ ISR(TIMER1_COMPA_vect) #if Y_MAX_PIN > -1 bool y_max_endstop=(READ(Y_MAX_PIN) != Y_ENDSTOP_INVERT); if(y_max_endstop && old_y_max_endstop && (current_block->steps_y > 0)){ - endstop_y_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_y_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_y_hit=false; } old_y_max_endstop = y_max_endstop; + #else + endstop_y_hit=false; #endif } } @@ -2906,10 +3142,18 @@ ISR(TIMER1_COMPA_vect) #if Z_MIN_PIN > -1 bool z_min_endstop=(READ(Z_MIN_PIN) != Z_ENDSTOP_INVERT); if(z_min_endstop && old_z_min_endstop && (current_block->steps_z > 0)) { - endstop_z_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_z_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_z_hit=false; } old_z_min_endstop = z_min_endstop; + #else + endstop_z_hit=false; #endif } } @@ -2920,10 +3164,18 @@ ISR(TIMER1_COMPA_vect) #if Z_MAX_PIN > -1 bool z_max_endstop=(READ(Z_MAX_PIN) != Z_ENDSTOP_INVERT); if(z_max_endstop && old_z_max_endstop && (current_block->steps_z > 0)) { - endstop_z_hit=true; - step_events_completed = current_block->step_event_count; + if(!is_homing) + endstop_z_hit=true; + else + step_events_completed = current_block->step_event_count; + } + else + { + endstop_z_hit=false; } old_z_max_endstop = z_max_endstop; + #else + endstop_z_hit=false; #endif } } @@ -2953,24 +3205,52 @@ ISR(TIMER1_COMPA_vect) } } #endif //ADVANCE - + + counter_x += current_block->steps_x; if (counter_x > 0) { - WRITE(X_STEP_PIN, HIGH); + if(!endstop_x_hit) + { + if(virtual_steps_x) + virtual_steps_x--; + else + WRITE(X_STEP_PIN, HIGH); + } + else + virtual_steps_x++; + counter_x -= current_block->step_event_count; WRITE(X_STEP_PIN, LOW); } counter_y += current_block->steps_y; if (counter_y > 0) { - WRITE(Y_STEP_PIN, HIGH); + if(!endstop_y_hit) + { + if(virtual_steps_y) + virtual_steps_y--; + else + WRITE(Y_STEP_PIN, HIGH); + } + else + virtual_steps_y++; + counter_y -= current_block->step_event_count; WRITE(Y_STEP_PIN, LOW); } counter_z += current_block->steps_z; if (counter_z > 0) { - WRITE(Z_STEP_PIN, HIGH); + if(!endstop_z_hit) + { + if(virtual_steps_z) + virtual_steps_z--; + else + WRITE(Z_STEP_PIN, HIGH); + } + else + virtual_steps_z++; + counter_z -= current_block->step_event_count; WRITE(Z_STEP_PIN, LOW); } @@ -3130,6 +3410,9 @@ void st_synchronize() while(blocks_queued()) { manage_heater(); manage_inactivity(1); + #if (MINIMUM_FAN_START_SPEED > 0) + manage_fan_start_speed(); + #endif } } diff --git a/Sprinter/arc_func.cpp b/Sprinter/arc_func.cpp index 255129f..1446e30 100644 --- a/Sprinter/arc_func.cpp +++ b/Sprinter/arc_func.cpp @@ -50,6 +50,8 @@ void mc_arc(float *position, float *target, float *offset, uint8_t axis_0, uint8 float millimeters_of_travel = hypot(angular_travel*radius, fabs(linear_travel)); if (millimeters_of_travel < 0.001) { return; } uint16_t segments = floor(millimeters_of_travel/MM_PER_ARC_SEGMENT); + if(segments == 0) segments = 1; + /* // Multiply inverse feed_rate to compensate for the fact that this movement is approximated // by a number of discrete segments. The inverse feed_rate should be correct for the sum of diff --git a/Sprinter/heater.cpp b/Sprinter/heater.cpp index c02924c..7682516 100644 --- a/Sprinter/heater.cpp +++ b/Sprinter/heater.cpp @@ -32,6 +32,10 @@ void controllerFan(void); #endif +#ifdef EXTRUDERFAN_PIN + void extruderFan(void); +#endif + // Manage heater variables. For a thermistor or AD595 thermocouple, raw values refer to the // reading from the analog pin. For a MAX6675 thermocouple, the raw value is the temperature in 0.25 // degree increments (i.e. 100=25 deg). @@ -50,8 +54,8 @@ unsigned long previous_millis_heater, previous_millis_bed_heater, previous_milli #ifdef PIDTEMP volatile unsigned char g_heater_pwm_val = 0; - unsigned char PWM_off_time = 0; - unsigned char PWM_out_on = 0; + //unsigned char PWM_off_time = 0; + //unsigned char PWM_out_on = 0; int temp_iState = 0; int temp_dState = 0; @@ -67,6 +71,10 @@ unsigned long previous_millis_heater, previous_millis_bed_heater, previous_milli #endif +#if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + volatile unsigned char g_fan_pwm_val = 0; +#endif + #ifdef AUTOTEMP float autotemp_max=AUTO_TEMP_MAX; float autotemp_min=AUTO_TEMP_MIN; @@ -155,90 +163,339 @@ int read_max6675() #endif -#ifdef PID_SOFT_PWM +//------------------------------------------------------------------------ +// Soft PWM for Heater and FAN +//------------------------------------------------------------------------ +#if defined(PID_SOFT_PWM) || (defined(FAN_SOFT_PWM) && (FAN_PIN > -1)) void init_Timer2_softpwm(void) { // This is a simple SOFT PWM with 500 Hz for Extruder Heating - TIFR2 = (1 << TOV2); // clear interrupt flag TCCR2B = (1 << CS22) | (1 << CS20); // start timer (ck/128 prescalar) - TCCR2A = (1 << WGM21); // CTC mode - OCR2A = 128; // We want to have at least 30Hz or else it gets choppy - TIMSK2 = (1 << OCIE2A); // enable timer2 output compare match interrupt - + TCCR2A = 0;//(1 << WGM21); // Normal mode + + TIMSK2 |= (1 << TOIE2); + + #ifdef PID_SOFT_PWM + OCR2A = 128; // We want to have at least 500Hz or else it gets choppy + TIMSK2 |= (1 << OCIE2A); // enable timer2 output compare match interrupt + #endif + + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + OCR2B = 128; // We want to have at least 500Hz or else it gets choppy + TIMSK2 |= (1 << OCIE2B); // enable timer2 output compare match interrupt + #endif + } +#endif +#if defined(PID_SOFT_PWM) || (defined(FAN_SOFT_PWM) && (FAN_PIN > -1)) +ISR(TIMER2_OVF_vect) +{ + + //-------------------------------------- + // Soft PWM, Heater, start PWM cycle + //-------------------------------------- + #ifdef PID_SOFT_PWM + if(g_heater_pwm_val >= 2) + { + #if LED_PIN > -1 + WRITE(LED_PIN,HIGH); + #endif + WRITE(HEATER_0_PIN,HIGH); - ISR(TIMER2_COMPA_vect) - { - - - if(g_heater_pwm_val < 2) + if(g_heater_pwm_val <= 253) + OCR2A = g_heater_pwm_val; + else + OCR2A = 192; + } + else { #if LED_PIN > -1 WRITE(LED_PIN,LOW); #endif WRITE(HEATER_0_PIN,LOW); - PWM_out_on = 0; - OCR2A = 128; + OCR2A = 192; } - else if(g_heater_pwm_val > 253) + #endif + + //-------------------------------------- + // Soft PWM, Fan, start PWM cycle + //-------------------------------------- + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + if(g_fan_pwm_val >= 2) { - #if LED_PIN > -1 - WRITE(LED_PIN,HIGH); - #endif - WRITE(HEATER_0_PIN,HIGH); - PWM_out_on = 1; - OCR2A = 128; + #if (FAN_PIN > -1) + WRITE(FAN_PIN,HIGH); + #endif + + if(g_fan_pwm_val <= 253) + OCR2B = g_fan_pwm_val; + else + OCR2B = 128; } else { - - if(PWM_out_on == 1) - { - - #if LED_PIN > -1 - WRITE(LED_PIN,LOW); - #endif - WRITE(HEATER_0_PIN,LOW); - PWM_out_on = 0; - OCR2A = PWM_off_time; - } - else - { - - #if LED_PIN > -1 - WRITE(LED_PIN,HIGH); - #endif - WRITE(HEATER_0_PIN,HIGH); - PWM_out_on = 1; - - if(g_heater_pwm_val > 253) - { - OCR2A = 253; - PWM_off_time = 2; - } - else if(g_heater_pwm_val < 2) - { - OCR2A = 2; - PWM_off_time = 253; - } - else - { - OCR2A = g_heater_pwm_val; - PWM_off_time = 255 - g_heater_pwm_val; - } - - } + #if (FAN_PIN > -1) + WRITE(FAN_PIN,LOW); + #endif + + OCR2B = 128; } - + #endif + +} +#endif + + + #ifdef PID_SOFT_PWM + ISR(TIMER2_COMPA_vect) + { + + + if(g_heater_pwm_val > 253) + { + #if LED_PIN > -1 + WRITE(LED_PIN,HIGH); + #endif + WRITE(HEATER_0_PIN,HIGH); + } + else + { + #if LED_PIN > -1 + WRITE(LED_PIN,LOW); + #endif + WRITE(HEATER_0_PIN,LOW); + } + + } #endif + + #if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + ISR(TIMER2_COMPB_vect) + { + + + if(g_fan_pwm_val > 253) + { + #if (FAN_PIN > -1) + WRITE(FAN_PIN,HIGH); + #endif + } + else + { + #if (FAN_PIN > -1) + WRITE(FAN_PIN,LOW); + #endif + } + + + } + #endif + //--------------------END SOFT PWM--------------------------- + +//-------------------- START PID AUTOTUNE --------------------------- +// Based on PID relay test +// Thanks to Erik van der Zalm for this idea to use it for Marlin +// Some information see: +// http://brettbeauregard.com/blog/2012/01/arduino-pid-autotune-library/ +//------------------------------------------------------------------ +#ifdef PID_AUTOTUNE +void PID_autotune(int PIDAT_test_temp) +{ + float PIDAT_input = 0; + int PIDAT_input_help = 0; + unsigned char PIDAT_count_input = 0; + + float PIDAT_max, PIDAT_min; + unsigned char PIDAT_PWM_val = 255; + + unsigned char PIDAT_cycles=0; + bool PIDAT_heating = true; + + unsigned long PIDAT_temp_millis = millis(); + unsigned long PIDAT_t1=PIDAT_temp_millis; + unsigned long PIDAT_t2=PIDAT_temp_millis; + unsigned long PIDAT_T_check_AI_val = PIDAT_temp_millis; + + unsigned char PIDAT_cycle_cnt = 0; + + long PIDAT_t_high; + long PIDAT_t_low; + + long PIDAT_bias= 127; + long PIDAT_d = 127; + + float PIDAT_Ku, PIDAT_Tu; + float PIDAT_Kp, PIDAT_Ki, PIDAT_Kd; + + #define PIDAT_TIME_FACTOR ((HEATER_CHECK_INTERVAL*256.0) / 1000.0) + + showString(PSTR("PID Autotune start\r\n")); + + target_temp = PIDAT_test_temp; + + #ifdef BED_USES_THERMISTOR + WRITE(HEATER_1_PIN,LOW); + #endif + + for(;;) + { + + if((millis() - PIDAT_T_check_AI_val) > 100 ) + { + PIDAT_T_check_AI_val = millis(); + PIDAT_cycle_cnt++; + + #ifdef HEATER_USES_THERMISTOR + current_raw = analogRead(TEMP_0_PIN); + current_raw = 1023 - current_raw; + PIDAT_input_help += analog2temp(current_raw); + PIDAT_count_input++; + #elif defined HEATER_USES_AD595 + current_raw = analogRead(TEMP_0_PIN); + PIDAT_input_help += analog2temp(current_raw); + PIDAT_count_input++; + #elif defined HEATER_USES_MAX6675 + current_raw = read_max6675(); + PIDAT_input_help += analog2temp(current_raw); + PIDAT_count_input++; + #endif + } + + if(PIDAT_cycle_cnt >= 10 ) + { + + PIDAT_cycle_cnt = 0; + + PIDAT_input = (float)PIDAT_input_help / (float)PIDAT_count_input; + PIDAT_input_help = 0; + PIDAT_count_input = 0; + + PIDAT_max=max(PIDAT_max,PIDAT_input); + PIDAT_min=min(PIDAT_min,PIDAT_input); + + if(PIDAT_heating == true && PIDAT_input > PIDAT_test_temp) + { + if(millis() - PIDAT_t2 > 5000) + { + PIDAT_heating = false; + PIDAT_PWM_val = (PIDAT_bias - PIDAT_d); + PIDAT_t1 = millis(); + PIDAT_t_high = PIDAT_t1 - PIDAT_t2; + PIDAT_max = PIDAT_test_temp; + } + } + + if(PIDAT_heating == false && PIDAT_input < PIDAT_test_temp) + { + if(millis() - PIDAT_t1 > 5000) + { + PIDAT_heating = true; + PIDAT_t2 = millis(); + PIDAT_t_low = PIDAT_t2 - PIDAT_t1; + + if(PIDAT_cycles > 0) + { + PIDAT_bias += (PIDAT_d*(PIDAT_t_high - PIDAT_t_low))/(PIDAT_t_low + PIDAT_t_high); + PIDAT_bias = constrain(PIDAT_bias, 20 ,235); + if(PIDAT_bias > 127) PIDAT_d = 254 - PIDAT_bias; + else PIDAT_d = PIDAT_bias; + + showString(PSTR(" bias: ")); Serial.print(PIDAT_bias); + showString(PSTR(" d: ")); Serial.print(PIDAT_d); + showString(PSTR(" min: ")); Serial.print(PIDAT_min); + showString(PSTR(" max: ")); Serial.println(PIDAT_max); + + if(PIDAT_cycles > 2) + { + PIDAT_Ku = (4.0*PIDAT_d)/(3.14159*(PIDAT_max-PIDAT_min)); + PIDAT_Tu = ((float)(PIDAT_t_low + PIDAT_t_high)/1000.0); + + showString(PSTR(" Ku: ")); Serial.print(PIDAT_Ku); + showString(PSTR(" Tu: ")); Serial.println(PIDAT_Tu); + + PIDAT_Kp = 0.60*PIDAT_Ku; + PIDAT_Ki = 2*PIDAT_Kp/PIDAT_Tu; + PIDAT_Kd = PIDAT_Kp*PIDAT_Tu/8; + showString(PSTR(" Clasic PID \r\n")); + //showString(PSTR(" Kp: ")); Serial.println(PIDAT_Kp); + //showString(PSTR(" Ki: ")); Serial.println(PIDAT_Ki); + //showString(PSTR(" Kd: ")); Serial.println(PIDAT_Kd); + showString(PSTR(" CFG Kp: ")); Serial.println((unsigned int)(PIDAT_Kp*256)); + showString(PSTR(" CFG Ki: ")); Serial.println((unsigned int)(PIDAT_Ki*PIDAT_TIME_FACTOR)); + showString(PSTR(" CFG Kd: ")); Serial.println((unsigned int)(PIDAT_Kd*PIDAT_TIME_FACTOR)); + + PIDAT_Kp = 0.30*PIDAT_Ku; + PIDAT_Ki = PIDAT_Kp/PIDAT_Tu; + PIDAT_Kd = PIDAT_Kp*PIDAT_Tu/3; + showString(PSTR(" Some overshoot \r\n")); + showString(PSTR(" CFG Kp: ")); Serial.println((unsigned int)(PIDAT_Kp*256)); + showString(PSTR(" CFG Ki: ")); Serial.println((unsigned int)(PIDAT_Ki*PIDAT_TIME_FACTOR)); + showString(PSTR(" CFG Kd: ")); Serial.println((unsigned int)(PIDAT_Kd*PIDAT_TIME_FACTOR)); + /* + PIDAT_Kp = 0.20*PIDAT_Ku; + PIDAT_Ki = 2*PIDAT_Kp/PIDAT_Tu; + PIDAT_Kd = PIDAT_Kp*PIDAT_Tu/3; + showString(PSTR(" No overshoot \r\n")); + showString(PSTR(" CFG Kp: ")); Serial.println((unsigned int)(PIDAT_Kp*256)); + showString(PSTR(" CFG Ki: ")); Serial.println((unsigned int)(PIDAT_Ki*PIDAT_TIME_FACTOR)); + showString(PSTR(" CFG Kd: ")); Serial.println((unsigned int)(PIDAT_Kd*PIDAT_TIME_FACTOR)); + */ + } + } + PIDAT_PWM_val = (PIDAT_bias + PIDAT_d); + PIDAT_cycles++; + PIDAT_min = PIDAT_test_temp; + } + } + + #ifdef PID_SOFT_PWM + g_heater_pwm_val = PIDAT_PWM_val; + #else + analogWrite_check(HEATER_0_PIN, PIDAT_PWM_val); + #if LED_PIN>-1 + analogWrite_check(LED_PIN, PIDAT_PWM_val); + #endif + #endif + } + + if(PIDAT_input > (PIDAT_test_temp + 20)) + { + showString(PSTR("PID Autotune failed! Temperature to high\r\n")); + return; + } + + if(millis() - PIDAT_temp_millis > 2000) + { + PIDAT_temp_millis = millis(); + showString(PSTR("ok T:")); + Serial.print(PIDAT_input); + showString(PSTR(" @:")); + Serial.println((unsigned char)PIDAT_PWM_val*1); + } + + if(((millis() - PIDAT_t1) + (millis() - PIDAT_t2)) > (10L*60L*1000L*2L)) + { + showString(PSTR("PID Autotune failed! timeout\r\n")); + return; + } + + if(PIDAT_cycles > 5) + { + showString(PSTR("PID Autotune finished ! Place the Kp, Ki and Kd constants in the configuration.h\r\n")); + return; + } + } +} +#endif +//---------------- END AUTOTUNE PID ------------------------------ void manage_heater() { @@ -247,6 +504,8 @@ int read_max6675() if((millis() - previous_millis_monitor) > 250 ) { previous_millis_monitor = millis(); + + if(manage_monitor <= 1) { showString(PSTR("MTEMP:")); @@ -491,6 +750,10 @@ int read_max6675() controllerFan(); //Check if fan should be turned on to cool stepper drivers down #endif +#ifdef EXTRUDERFAN_PIN + extruderFan(); //Check if fan should be turned on to cool extruder down +#endif + } #if defined (HEATER_USES_THERMISTOR) || defined (BED_USES_THERMISTOR) @@ -601,3 +864,24 @@ void controllerFan() } #endif +#ifdef EXTRUDERFAN_PIN +unsigned long lastExtruderCheck = 0; + +void extruderFan() +{ + if ((millis() - lastExtruderCheck) >= 2500) //Not a time critical function, so we only check every 2500ms + { + lastExtruderCheck = millis(); + + if (analog2temp(current_raw) < EXTRUDERFAN_DEC) + { + WRITE(EXTRUDERFAN_PIN, LOW); //... turn the fan off + } + else + { + WRITE(EXTRUDERFAN_PIN, HIGH); //... turn the fan on + } + } +} +#endif + diff --git a/Sprinter/heater.h b/Sprinter/heater.h index a1d2917..87b6b4d 100644 --- a/Sprinter/heater.h +++ b/Sprinter/heater.h @@ -90,6 +90,9 @@ extern unsigned char manage_monitor; extern int heater_duty; #endif +#if defined(FAN_SOFT_PWM) && (FAN_PIN > -1) + extern volatile unsigned char g_fan_pwm_val; +#endif #ifdef AUTOTEMP extern float autotemp_max; @@ -112,8 +115,12 @@ extern unsigned char manage_monitor; -#ifdef PID_SOFT_PWM +#if defined(PID_SOFT_PWM) || (defined(FAN_SOFT_PWM) && (FAN_PIN > -1)) void init_Timer2_softpwm(void); #endif +#ifdef PID_AUTOTUNE + void PID_autotune(int PIDAT_test_temp); +#endif + void manage_heater(); diff --git a/Sprinter/pins.h b/Sprinter/pins.h index 63ea464..946118f 100644 --- a/Sprinter/pins.h +++ b/Sprinter/pins.h @@ -568,6 +568,11 @@ * Gen6 pin assignment * ****************************************************************************************/ +#if MOTHERBOARD == 51 + #define MOTHERBOARD 5 + #define GEN6_DELUXE +#endif + #if MOTHERBOARD == 5 #define KNOWN_BOARD 1 @@ -602,13 +607,18 @@ #define E_ENABLE_PIN 3 //Added @ EJE Electronics 20100715 #define TEMP_0_PIN 5 //changed @ rkoeppl 20110410 #define HEATER_0_PIN 14 //changed @ rkoeppl 20110410 - #define HEATER_1_PIN -1 //changed @ rkoeppl 20110410 + #ifdef GEN6_DELUXE + #define HEATER_1_PIN 1 + #define TEMP_1_PIN 0 + #else + #define HEATER_1_PIN -1 + #define TEMP_1_PIN -1 + #endif #define SDPOWER -1 #define SDSS 17 #define LED_PIN -1 //changed @ rkoeppl 20110410 - #define TEMP_1_PIN -1 //changed @ rkoeppl 20110410 #define FAN_PIN -1 //changed @ rkoeppl 20110410 #define PS_ON_PIN -1 //changed @ rkoeppl 20110410 //our pin for debugging. diff --git a/Sprinter/store_eeprom.cpp b/Sprinter/store_eeprom.cpp index c2cd353..a474e22 100644 --- a/Sprinter/store_eeprom.cpp +++ b/Sprinter/store_eeprom.cpp @@ -99,7 +99,7 @@ void EEPROM_printSettings() Serial.println(axis_steps_per_unit[3]); showString(PSTR("Maximum feedrates (mm/s):\r\n")); - showString(PSTR(" M203 X")); + showString(PSTR(" M202 X")); Serial.print(max_feedrate[0]); showString(PSTR(" Y")); Serial.print(max_feedrate[1]); diff --git a/Sprinter/thermistortables.h b/Sprinter/thermistortables.h index eccfe88..8496b6d 100644 --- a/Sprinter/thermistortables.h +++ b/Sprinter/thermistortables.h @@ -280,8 +280,8 @@ const short temptable_6[NUMTEMPS_6][2] = { {49, 220}, {53, 215}, {62, 210}, - {73, 205}, - {72, 200}, + {71, 205}, //fitted graphically + {78, 200}, //fitted graphically {94, 190}, {102, 185}, {116, 170}, |