diff --git a/Marlin/src/gcode/bedlevel/M420.cpp b/Marlin/src/gcode/bedlevel/M420.cpp index 680d99fe469c..bfc2cf39f8df 100644 --- a/Marlin/src/gcode/bedlevel/M420.cpp +++ b/Marlin/src/gcode/bedlevel/M420.cpp @@ -74,7 +74,7 @@ void GcodeSuite::M420() { start.set(x_min, y_min); spacing.set((x_max - x_min) / (GRID_MAX_CELLS_X), (y_max - y_min) / (GRID_MAX_CELLS_Y)); - bedlevel.set_grid(spacing, start); + bedlevel.set_grid(spacing, Probe::convert_to_nozzle_xy(start)); #endif GRID_LOOP(x, y) { bedlevel.z_values[x][y] = 0.001 * random(-200, 200); diff --git a/Marlin/src/gcode/bedlevel/abl/G29.cpp b/Marlin/src/gcode/bedlevel/abl/G29.cpp index 77809605a4ac..5da442efb4bc 100644 --- a/Marlin/src/gcode/bedlevel/abl/G29.cpp +++ b/Marlin/src/gcode/bedlevel/abl/G29.cpp @@ -520,7 +520,9 @@ G29_TYPE GcodeSuite::G29() { #endif #if ENABLED(AUTO_BED_LEVELING_BILINEAR) - if (!abl.dryrun && (abl.gridSpacing != bedlevel.grid_spacing || abl.probe_position_lf != bedlevel.grid_start)) { + // Convert the probe-space grid origin to the motion/nozzle coordinate + const xy_pos_t grid_start = Probe::convert_to_nozzle_xy(abl.probe_position_lf); + if (!abl.dryrun && (abl.gridSpacing != bedlevel.grid_spacing || grid_start != bedlevel.grid_start)) { reset_bed_level(); // Reset grid to 0.0 or "not probed". (Also disables ABL) abl.reenable = false; // Can't re-enable (on error) until the new grid is written } @@ -883,7 +885,7 @@ G29_TYPE GcodeSuite::G29() { if (abl.dryrun) bedlevel.print_leveling_grid(&abl.z_values); else { - bedlevel.set_grid(abl.gridSpacing, abl.probe_position_lf); + bedlevel.set_grid(abl.gridSpacing, Probe::convert_to_nozzle_xy(abl.probe_position_lf)); COPY(bedlevel.z_values, abl.z_values); TERN_(IS_KINEMATIC, bedlevel.extrapolate_unprobed_bed_level()); bedlevel.refresh_bed_level(); diff --git a/Marlin/src/module/probe.h b/Marlin/src/module/probe.h index 4f2a10eb1aac..3f4cde94b472 100644 --- a/Marlin/src/module/probe.h +++ b/Marlin/src/module/probe.h @@ -244,6 +244,11 @@ class Probe { static constexpr xy_pos_t offset_xy = xy_pos_t({ 0, 0 }); // See #16767 #endif + // Convert a probe-space XY point to the active nozzle's motion-space coordinates. + static xy_pos_t convert_to_nozzle_xy(const xy_pos_t &probe_xy) { + return probe_xy - DIFF_TERN(HAS_HOTEND_OFFSET, offset_xy, xy_pos_t(motion.active_hotend_offset())); + } + static bool deploy(const bool no_return=false) { return set_deployed(true, no_return); } static bool stow(const bool no_return=false) { return set_deployed(false, no_return); }