From b72238f4063fcf67f3155fdf732d50f4860d795c Mon Sep 17 00:00:00 2001 From: Scott Lahteine Date: Sat, 9 Jul 2016 19:47:11 -0700 Subject: [PATCH] Invariant get_pid_output with HOTENDS < 2 --- Marlin/temperature.cpp | 84 +++++++++++++++++++++--------------------- Marlin/temperature.h | 27 +++++++++----- 2 files changed, 59 insertions(+), 52 deletions(-) diff --git a/Marlin/temperature.cpp b/Marlin/temperature.cpp index fb9b40cf0..2fa6074b2 100644 --- a/Marlin/temperature.cpp +++ b/Marlin/temperature.cpp @@ -514,88 +514,86 @@ void Temperature::min_temp_error(uint8_t e) { } float Temperature::get_pid_output(int e) { + #if HOTENDS == 1 + UNUSED(e); + #define _HOTEND_TEST true + #define _HOTEND_EXTRUDER active_extruder + #else + #define _HOTEND_TEST e == active_extruder + #define _HOTEND_EXTRUDER e + #endif float pid_output; #if ENABLED(PIDTEMP) #if DISABLED(PID_OPENLOOP) - pid_error[e] = target_temperature[e] - current_temperature[e]; - dTerm[e] = K2 * PID_PARAM(Kd, e) * (current_temperature[e] - temp_dState[e]) + K1 * dTerm[e]; - temp_dState[e] = current_temperature[e]; - if (pid_error[e] > PID_FUNCTIONAL_RANGE) { + pid_error[HOTEND_INDEX] = target_temperature[HOTEND_INDEX] - current_temperature[HOTEND_INDEX]; + dTerm[HOTEND_INDEX] = K2 * PID_PARAM(Kd, HOTEND_INDEX) * (current_temperature[HOTEND_INDEX] - temp_dState[HOTEND_INDEX]) + K1 * dTerm[HOTEND_INDEX]; + temp_dState[HOTEND_INDEX] = current_temperature[HOTEND_INDEX]; + if (pid_error[HOTEND_INDEX] > PID_FUNCTIONAL_RANGE) { pid_output = BANG_MAX; - pid_reset[e] = true; + pid_reset[HOTEND_INDEX] = true; } - else if (pid_error[e] < -(PID_FUNCTIONAL_RANGE) || target_temperature[e] == 0) { + else if (pid_error[HOTEND_INDEX] < -(PID_FUNCTIONAL_RANGE) || target_temperature[HOTEND_INDEX] == 0) { pid_output = 0; - pid_reset[e] = true; + pid_reset[HOTEND_INDEX] = true; } else { - if (pid_reset[e]) { - temp_iState[e] = 0.0; - pid_reset[e] = false; + if (pid_reset[HOTEND_INDEX]) { + temp_iState[HOTEND_INDEX] = 0.0; + pid_reset[HOTEND_INDEX] = false; } - pTerm[e] = PID_PARAM(Kp, e) * pid_error[e]; - temp_iState[e] += pid_error[e]; - temp_iState[e] = constrain(temp_iState[e], temp_iState_min[e], temp_iState_max[e]); - iTerm[e] = PID_PARAM(Ki, e) * temp_iState[e]; + pTerm[HOTEND_INDEX] = PID_PARAM(Kp, HOTEND_INDEX) * pid_error[HOTEND_INDEX]; + temp_iState[HOTEND_INDEX] += pid_error[HOTEND_INDEX]; + temp_iState[HOTEND_INDEX] = constrain(temp_iState[HOTEND_INDEX], temp_iState_min[HOTEND_INDEX], temp_iState_max[HOTEND_INDEX]); + iTerm[HOTEND_INDEX] = PID_PARAM(Ki, HOTEND_INDEX) * temp_iState[HOTEND_INDEX]; - pid_output = pTerm[e] + iTerm[e] - dTerm[e]; - - #if ENABLED(SINGLENOZZLE) - #define _NOZZLE_TEST true - #define _NOZZLE_EXTRUDER active_extruder - #define _CTERM_INDEX 0 - #else - #define _NOZZLE_TEST e == active_extruder - #define _NOZZLE_EXTRUDER e - #define _CTERM_INDEX e - #endif + pid_output = pTerm[HOTEND_INDEX] + iTerm[HOTEND_INDEX] - dTerm[HOTEND_INDEX]; #if ENABLED(PID_ADD_EXTRUSION_RATE) - cTerm[_CTERM_INDEX] = 0; - if (_NOZZLE_TEST) { + cTerm[HOTEND_INDEX] = 0; + if (_HOTEND_TEST) { long e_position = stepper.position(E_AXIS); - if (e_position > last_position[_NOZZLE_EXTRUDER]) { - lpq[lpq_ptr++] = e_position - last_position[_NOZZLE_EXTRUDER]; - last_position[_NOZZLE_EXTRUDER] = e_position; + if (e_position > last_position[_HOTEND_EXTRUDER]) { + lpq[lpq_ptr++] = e_position - last_position[_HOTEND_EXTRUDER]; + last_position[_HOTEND_EXTRUDER] = e_position; } else { lpq[lpq_ptr++] = 0; } if (lpq_ptr >= lpq_len) lpq_ptr = 0; - cTerm[_CTERM_INDEX] = (lpq[lpq_ptr] / planner.axis_steps_per_mm[E_AXIS]) * PID_PARAM(Kc, e); - pid_output += cTerm[e]; + cTerm[HOTEND_INDEX] = (lpq[lpq_ptr] / planner.axis_steps_per_mm[E_AXIS]) * PID_PARAM(Kc, HOTEND_INDEX); + pid_output += cTerm[HOTEND_INDEX]; } #endif //PID_ADD_EXTRUSION_RATE if (pid_output > PID_MAX) { - if (pid_error[e] > 0) temp_iState[e] -= pid_error[e]; // conditional un-integration + if (pid_error[HOTEND_INDEX] > 0) temp_iState[HOTEND_INDEX] -= pid_error[HOTEND_INDEX]; // conditional un-integration pid_output = PID_MAX; } else if (pid_output < 0) { - if (pid_error[e] < 0) temp_iState[e] -= pid_error[e]; // conditional un-integration + if (pid_error[HOTEND_INDEX] < 0) temp_iState[HOTEND_INDEX] -= pid_error[HOTEND_INDEX]; // conditional un-integration pid_output = 0; } } #else - pid_output = constrain(target_temperature[e], 0, PID_MAX); + pid_output = constrain(target_temperature[HOTEND_INDEX], 0, PID_MAX); #endif //PID_OPENLOOP #if ENABLED(PID_DEBUG) SERIAL_ECHO_START; - SERIAL_ECHOPAIR(MSG_PID_DEBUG, e); - SERIAL_ECHOPAIR(MSG_PID_DEBUG_INPUT, current_temperature[e]); + SERIAL_ECHOPAIR(MSG_PID_DEBUG, HOTEND_INDEX); + SERIAL_ECHOPAIR(MSG_PID_DEBUG_INPUT, current_temperature[HOTEND_INDEX]); SERIAL_ECHOPAIR(MSG_PID_DEBUG_OUTPUT, pid_output); - SERIAL_ECHOPAIR(MSG_PID_DEBUG_PTERM, pTerm[e]); - SERIAL_ECHOPAIR(MSG_PID_DEBUG_ITERM, iTerm[e]); - SERIAL_ECHOPAIR(MSG_PID_DEBUG_DTERM, dTerm[e]); + SERIAL_ECHOPAIR(MSG_PID_DEBUG_PTERM, pTerm[HOTEND_INDEX]); + SERIAL_ECHOPAIR(MSG_PID_DEBUG_ITERM, iTerm[HOTEND_INDEX]); + SERIAL_ECHOPAIR(MSG_PID_DEBUG_DTERM, dTerm[HOTEND_INDEX]); #if ENABLED(PID_ADD_EXTRUSION_RATE) - SERIAL_ECHOPAIR(MSG_PID_DEBUG_CTERM, cTerm[e]); + SERIAL_ECHOPAIR(MSG_PID_DEBUG_CTERM, cTerm[HOTEND_INDEX]); #endif SERIAL_EOL; #endif //PID_DEBUG #else /* PID off */ - pid_output = (current_temperature[e] < target_temperature[e]) ? PID_MAX : 0; + pid_output = (current_temperature[HOTEND_INDEX] < target_temperature[HOTEND_INDEX]) ? PID_MAX : 0; #endif return pid_output; @@ -672,7 +670,7 @@ void Temperature::manage_heater() { #endif // Loop through all hotends - for (int e = 0; e < HOTENDS; e++) { + for (uint8_t e = 0; e < HOTENDS; e++) { #if ENABLED(THERMAL_PROTECTION_HOTENDS) thermal_runaway_protection(&thermal_runaway_state_machine[e], &thermal_runaway_timer[e], current_temperature[e], target_temperature[e], e, THERMAL_PROTECTION_PERIOD, THERMAL_PROTECTION_HYSTERESIS); diff --git a/Marlin/temperature.h b/Marlin/temperature.h index 60aa80d6a..f8b190800 100644 --- a/Marlin/temperature.h +++ b/Marlin/temperature.h @@ -38,6 +38,16 @@ #define SOFT_PWM_SCALE 0 #endif +#if HOTENDS == 1 + #define HOTEND_ARG 0 + #define HOTEND_INDEX 0 + #define EXTRUDER_ARG 0 +#else + #define HOTEND_ARG hotend + #define HOTEND_INDEX e + #define EXTRUDER_ARG active_extruder +#endif + class Temperature { public: @@ -112,7 +122,12 @@ class Temperature { #if ENABLED(PREVENT_DANGEROUS_EXTRUDE) static float extrude_min_temp; - static bool tooColdToExtrude(uint8_t e) { return degHotend(e) < extrude_min_temp; } + static bool tooColdToExtrude(uint8_t e) { + #if HOTENDS == 1 + UNUSED(e); + #endif + return degHotend(HOTEND_INDEX) < extrude_min_temp; + } #else static bool tooColdToExtrude(uint8_t e) { UNUSED(e); return false; } #endif @@ -230,12 +245,6 @@ class Temperature { //inline so that there is no performance decrease. //deg=degreeCelsius - #if HOTENDS == 1 - #define HOTEND_ARG 0 - #else - #define HOTEND_ARG hotend - #endif - static float degHotend(uint8_t hotend) { #if HOTENDS == 1 UNUSED(hotend); @@ -329,8 +338,8 @@ class Temperature { #if ENABLED(AUTOTEMP) if (planner.autotemp_enabled) { planner.autotemp_enabled = false; - if (degTargetHotend(active_extruder) > planner.autotemp_min) - setTargetHotend(0, active_extruder); + if (degTargetHotend(EXTRUDER_ARG) > planner.autotemp_min) + setTargetHotend(0, EXTRUDER_ARG); } #endif }