⚡️ Improve Sensorless homing/probing for G28, G33 (#21899)
This commit is contained in:
@ -254,6 +254,7 @@ void home_delta() {
|
||||
current_position.z = DIFF_TERN(HAS_BED_PROBE, delta_height + 10, probe.offset.z);
|
||||
line_to_current_position(homing_feedrate(Z_AXIS));
|
||||
planner.synchronize();
|
||||
TERN_(SENSORLESS_PROBING,endstops.report_states());
|
||||
|
||||
// Re-enable stealthChop if used. Disable diag1 pin on driver.
|
||||
#if ENABLED(SENSORLESS_HOMING) && DISABLED(ENDSTOPS_ALWAYS_ON_DEFAULT)
|
||||
|
@ -595,9 +595,15 @@ void _O2 Endstops::report_states() {
|
||||
// The following routines are called from an ISR context. It could be the temperature ISR, the
|
||||
// endstop ISR or the Stepper ISR.
|
||||
|
||||
#define _ENDSTOP(AXIS, MINMAX) AXIS ##_## MINMAX
|
||||
#define _ENDSTOP_PIN(AXIS, MINMAX) AXIS ##_## MINMAX ##_PIN
|
||||
#define _ENDSTOP_INVERTING(AXIS, MINMAX) AXIS ##_## MINMAX ##_ENDSTOP_INVERTING
|
||||
#if BOTH(DELTA, SENSORLESS_PROBING)
|
||||
#define _ENDSTOP(AXIS, MINMAX) AXIS ##_MAX
|
||||
#define _ENDSTOP_PIN(AXIS, MINMAX) AXIS ##_MAX_PIN
|
||||
#define _ENDSTOP_INVERTING(AXIS, MINMAX) AXIS ##_MAX_ENDSTOP_INVERTING
|
||||
#else
|
||||
#define _ENDSTOP(AXIS, MINMAX) AXIS ##_## MINMAX
|
||||
#define _ENDSTOP_PIN(AXIS, MINMAX) AXIS ##_## MINMAX ##_PIN
|
||||
#define _ENDSTOP_INVERTING(AXIS, MINMAX) AXIS ##_## MINMAX ##_ENDSTOP_INVERTING
|
||||
#endif
|
||||
|
||||
// Check endstops - Could be called from Temperature ISR!
|
||||
void Endstops::update() {
|
||||
|
@ -1527,6 +1527,34 @@ void Planner::check_axes_activity() {
|
||||
}
|
||||
#endif
|
||||
|
||||
#if ENABLED(IMPROVE_HOMING_RELIABILITY)
|
||||
|
||||
void Planner::enable_stall_prevention(const bool onoff) {
|
||||
static motion_state_t saved_motion_state;
|
||||
if (onoff) {
|
||||
saved_motion_state.acceleration.x = settings.max_acceleration_mm_per_s2[X_AXIS];
|
||||
saved_motion_state.acceleration.y = settings.max_acceleration_mm_per_s2[Y_AXIS];
|
||||
settings.max_acceleration_mm_per_s2[X_AXIS] = settings.max_acceleration_mm_per_s2[Y_AXIS] = 100;
|
||||
#if ENABLED(DELTA)
|
||||
saved_motion_state.acceleration.z = settings.max_acceleration_mm_per_s2[Z_AXIS];
|
||||
settings.max_acceleration_mm_per_s2[Z_AXIS] = 100;
|
||||
#endif
|
||||
#if HAS_CLASSIC_JERK
|
||||
saved_motion_state.jerk_state = max_jerk;
|
||||
max_jerk.set(0, 0 OPTARG(DELTA, 0));
|
||||
#endif
|
||||
}
|
||||
else {
|
||||
settings.max_acceleration_mm_per_s2[X_AXIS] = saved_motion_state.acceleration.x;
|
||||
settings.max_acceleration_mm_per_s2[Y_AXIS] = saved_motion_state.acceleration.y;
|
||||
TERN_(DELTA, settings.max_acceleration_mm_per_s2[Z_AXIS] = saved_motion_state.acceleration.z);
|
||||
TERN_(HAS_CLASSIC_JERK, max_jerk = saved_motion_state.jerk_state);
|
||||
}
|
||||
reset_acceleration_rates();
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if HAS_LEVELING
|
||||
|
||||
constexpr xy_pos_t level_fulcrum = {
|
||||
|
@ -281,6 +281,15 @@ typedef struct {
|
||||
min_travel_feedrate_mm_s; // (mm/s) M205 T - Minimum travel feedrate
|
||||
} planner_settings_t;
|
||||
|
||||
#if ENABLED(IMPROVE_HOMING_RELIABILITY)
|
||||
struct motion_state_t {
|
||||
TERN(DELTA, xyz_ulong_t, xy_ulong_t) acceleration;
|
||||
#if HAS_CLASSIC_JERK
|
||||
TERN(DELTA, xyz_float_t, xy_float_t) jerk_state;
|
||||
#endif
|
||||
};
|
||||
#endif
|
||||
|
||||
#if DISABLED(SKEW_CORRECTION)
|
||||
#define XY_SKEW_FACTOR 0
|
||||
#define XZ_SKEW_FACTOR 0
|
||||
@ -532,6 +541,10 @@ class Planner {
|
||||
}
|
||||
#endif
|
||||
|
||||
#if ENABLED(IMPROVE_HOMING_RELIABILITY)
|
||||
void enable_stall_prevention(const bool onoff);
|
||||
#endif
|
||||
|
||||
#if DISABLED(NO_VOLUMETRICS)
|
||||
|
||||
// Update multipliers based on new diameter measurements
|
||||
|
@ -68,7 +68,7 @@
|
||||
#include "servo.h"
|
||||
#endif
|
||||
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
#if EITHER(SENSORLESS_PROBING, SENSORLESS_HOMING)
|
||||
#include "stepper.h"
|
||||
#include "../feature/tmc_util.h"
|
||||
#endif
|
||||
@ -92,6 +92,10 @@ xyz_pos_t Probe::offset; // Initialized by settings.load()
|
||||
const xy_pos_t &Probe::offset_xy = Probe::offset;
|
||||
#endif
|
||||
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
Probe::sense_bool_t Probe::test_sensitivity;
|
||||
#endif
|
||||
|
||||
#if ENABLED(Z_PROBE_SLED)
|
||||
|
||||
#ifndef SLED_DOCKING_OFFSET
|
||||
@ -493,11 +497,12 @@ bool Probe::probe_down_to_z(const_float_t z, const_feedRate_t fr_mm_s) {
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
sensorless_t stealth_states { false };
|
||||
#if ENABLED(DELTA)
|
||||
stealth_states.x = tmc_enable_stallguard(stepperX);
|
||||
stealth_states.y = tmc_enable_stallguard(stepperY);
|
||||
if (probe.test_sensitivity.x) stealth_states.x = tmc_enable_stallguard(stepperX); // Delta watches all DIAG pins for a stall
|
||||
if (probe.test_sensitivity.y) stealth_states.y = tmc_enable_stallguard(stepperY);
|
||||
#endif
|
||||
stealth_states.z = tmc_enable_stallguard(stepperZ);
|
||||
if (probe.test_sensitivity.z) stealth_states.z = tmc_enable_stallguard(stepperZ); // All machines will check Z-DIAG for stall
|
||||
endstops.enable(true);
|
||||
set_homing_current(true); // The "homing" current also applies to probing
|
||||
#endif
|
||||
|
||||
TERN_(HAS_QUIET_PROBING, set_probing_paused(true));
|
||||
@ -520,10 +525,11 @@ bool Probe::probe_down_to_z(const_float_t z, const_feedRate_t fr_mm_s) {
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
endstops.not_homing();
|
||||
#if ENABLED(DELTA)
|
||||
tmc_disable_stallguard(stepperX, stealth_states.x);
|
||||
tmc_disable_stallguard(stepperY, stealth_states.y);
|
||||
if (probe.test_sensitivity.x) tmc_disable_stallguard(stepperX, stealth_states.x);
|
||||
if (probe.test_sensitivity.y) tmc_disable_stallguard(stepperY, stealth_states.y);
|
||||
#endif
|
||||
tmc_disable_stallguard(stepperZ, stealth_states.z);
|
||||
if (probe.test_sensitivity.z) tmc_disable_stallguard(stepperZ, stealth_states.z);
|
||||
set_homing_current(false);
|
||||
#endif
|
||||
|
||||
if (probe_triggered && TERN0(BLTOUCH_SLOW_MODE, bltouch.stow())) // Stow in LOW SPEED MODE on every trigger
|
||||
@ -815,4 +821,93 @@ float Probe::probe_at_point(const_float_t rx, const_float_t ry, const ProbePtRai
|
||||
|
||||
#endif // HAS_Z_SERVO_PROBE
|
||||
|
||||
#if EITHER(SENSORLESS_PROBING, SENSORLESS_HOMING)
|
||||
|
||||
sensorless_t stealth_states { false };
|
||||
|
||||
/**
|
||||
* Disable stealthChop if used. Enable diag1 pin on driver.
|
||||
*/
|
||||
void Probe::enable_stallguard_diag1() {
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
#if ENABLED(DELTA)
|
||||
stealth_states.x = tmc_enable_stallguard(stepperX);
|
||||
stealth_states.y = tmc_enable_stallguard(stepperY);
|
||||
#endif
|
||||
stealth_states.z = tmc_enable_stallguard(stepperZ);
|
||||
endstops.enable(true);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* Re-enable stealthChop if used. Disable diag1 pin on driver.
|
||||
*/
|
||||
void Probe::disable_stallguard_diag1() {
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
endstops.not_homing();
|
||||
#if ENABLED(DELTA)
|
||||
tmc_disable_stallguard(stepperX, stealth_states.x);
|
||||
tmc_disable_stallguard(stepperY, stealth_states.y);
|
||||
#endif
|
||||
tmc_disable_stallguard(stepperZ, stealth_states.z);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* Change the current in the TMC drivers to N##_CURRENT_HOME. And we save the current configuration of each TMC driver.
|
||||
*/
|
||||
void Probe::set_homing_current(const bool onoff) {
|
||||
#define HAS_CURRENT_HOME(N) (defined(N##_CURRENT_HOME) && N##_CURRENT_HOME != N##_CURRENT)
|
||||
#if HAS_CURRENT_HOME(X) || HAS_CURRENT_HOME(Y) || HAS_CURRENT_HOME(Z)
|
||||
#if ENABLED(DELTA)
|
||||
static int16_t saved_current_X, saved_current_Y;
|
||||
#endif
|
||||
#if HAS_CURRENT_HOME(Z)
|
||||
static int16_t saved_current_Z;
|
||||
#endif
|
||||
auto debug_current_on = [](PGM_P const s, const int16_t a, const int16_t b) {
|
||||
if (DEBUGGING(LEVELING)) { DEBUG_ECHOPGM_P(s); DEBUG_ECHOLNPAIR(" current: ", a, " -> ", b); }
|
||||
};
|
||||
if (onoff) {
|
||||
#if ENABLED(DELTA)
|
||||
#if HAS_CURRENT_HOME(X)
|
||||
saved_current_X = stepperX.getMilliamps();
|
||||
stepperX.rms_current(X_CURRENT_HOME);
|
||||
debug_current_on(PSTR("X"), saved_current_X, X_CURRENT_HOME);
|
||||
#endif
|
||||
#if HAS_CURRENT_HOME(Y)
|
||||
saved_current_Y = stepperY.getMilliamps();
|
||||
stepperY.rms_current(Y_CURRENT_HOME);
|
||||
debug_current_on(PSTR("Y"), saved_current_Y, Y_CURRENT_HOME);
|
||||
#endif
|
||||
#endif
|
||||
#if HAS_CURRENT_HOME(Z)
|
||||
saved_current_Z = stepperZ.getMilliamps();
|
||||
stepperZ.rms_current(Z_CURRENT_HOME);
|
||||
debug_current_on(PSTR("Z"), saved_current_Z, Z_CURRENT_HOME);
|
||||
#endif
|
||||
TERN_(IMPROVE_HOMING_RELIABILITY, planner.enable_stall_prevention(true));
|
||||
}
|
||||
else {
|
||||
#if ENABLED(DELTA)
|
||||
#if HAS_CURRENT_HOME(X)
|
||||
stepperX.rms_current(saved_current_X);
|
||||
debug_current_on(PSTR("X"), X_CURRENT_HOME, saved_current_X);
|
||||
#endif
|
||||
#if HAS_CURRENT_HOME(Y)
|
||||
stepperY.rms_current(saved_current_Y);
|
||||
debug_current_on(PSTR("Y"), Y_CURRENT_HOME, saved_current_Y);
|
||||
#endif
|
||||
#endif
|
||||
#if HAS_CURRENT_HOME(Z)
|
||||
stepperZ.rms_current(saved_current_Z);
|
||||
debug_current_on(PSTR("Z"), Z_CURRENT_HOME, saved_current_Z);
|
||||
#endif
|
||||
TERN_(IMPROVE_HOMING_RELIABILITY, planner.enable_stall_prevention(false));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif // SENSORLESS_PROBING
|
||||
|
||||
#endif // HAS_BED_PROBE
|
||||
|
@ -56,6 +56,11 @@
|
||||
class Probe {
|
||||
public:
|
||||
|
||||
#if ENABLED(SENSORLESS_PROBING)
|
||||
typedef struct { bool x:1, y:1, z:1; } sense_bool_t;
|
||||
static sense_bool_t test_sensitivity;
|
||||
#endif
|
||||
|
||||
#if HAS_BED_PROBE
|
||||
|
||||
static xyz_pos_t offset;
|
||||
@ -256,6 +261,13 @@ public:
|
||||
static bool tare();
|
||||
#endif
|
||||
|
||||
// Basic functions for Sensorless Homing and Probing
|
||||
#if EITHER(SENSORLESS_HOMING, SENSORLESS_PROBING)
|
||||
static void enable_stallguard_diag1();
|
||||
static void disable_stallguard_diag1();
|
||||
static void set_homing_current(const bool onoff);
|
||||
#endif
|
||||
|
||||
private:
|
||||
static bool probe_down_to_z(const_float_t z, const_feedRate_t fr_mm_s);
|
||||
static void do_z_raise(const float z_raise);
|
||||
|
Reference in New Issue
Block a user