Now you finally decided to order and install a BLTouch sensor for your Anycubic Mega S 3D printer and enjoy the laziness of no longer having to care for a misaligned printing bed and resulting non-sticking prints. Following the available comprehensive installation instructions, you installed and calibrated everything and now watch the sensor probing your bed. So satisfying.

Next you want to print the first time with your new exact measured compensation mesh, but the disappointment comes early. The left side prints well, but towards the right side nothing will stick any longer.
Using OctoPrints Mesh Visualizer (setup with M420 V parameter to only read the existing mesh), your bed might look like mine right after the probing (see picture). It’s actually tilted to the right. So when the mesh is used to compensate z-values, the printhead is wrongly lifted above the actual bed surface, in my case even more than 0.5mm on the right side. So I am basically printing in the air only there.
> M420 V
Recv: Bilinear Leveling Grid:
Recv: 0 1 2 3 4
Recv: 0 +0.027 +0.043 +0.168 +0.360 +0.597
Recv: 1 -0.058 +0.000 +0.128 +0.322 +0.585
Recv: 2 -0.078 -0.030 +0.120 +0.320 +0.575
Recv: 3 -0.017 +0.043 +0.168 +0.332 +0.590
Recv: 4 +0.075 +0.092 +0.220 +0.378 +0.582
So what went wrong? It seems like all values grow steadily to the right side. But of course I did a perfect manual levelling before the measurement, so how can that even be? It turns out that the X-carriage rails (where the hot-end sled moves across the x-axis) is not 100% perfectly aligned, but rather slightly twisted. While you compensate for that with a manual bed levelling for the nozzle height, the BLTouch probe is farther away from the rails and will experience a bigger impact of the twist than the nozzle. See the below (exaggerated) schema image:

You won’t see that with your eyes and can even hardly measure it in any way (in my case it was just 0.5mm at the probe), but it’s enough to no longer create proper prints at all. It’s almost 3 layers above the surface for me. Unfortunately, there are no ways to properly re-align these rails (like dedicated adjustment screws). You can try to counter-bend the scaffolding, but given how tiny the deviation actually is, you can hardly really succeed that way.
One option would be to put the BLTouch on the side of the hot-end housing and make sure that it has a zero Y-offset from the nozzle. That way it would experience the same error than the nozzle that you already compensated for during manual levelling. However, as you would have to attach it a bit away to not block the fan intakes on either side, you would really lose a lot of X-space for printing. And it looks ugly ??. The best place for the BLTouch is really within the housing at Y-25.
The Solution!

But as the whole compensation mesh is anyway merely about mathematics, we can also apply some more of it to exactly compensate for this deviation. Fortunately, that twist is a systematic error (it applies constantly all the time), and has a simple linear impact. During your initial BLTouch calibration, you just measure a second probe on the right side, and I wrote a little tool to create a list of proper compensation values that you apply right afterwards. Once applied, I now end up with the mesh shown on the right. Not only it turns out my bed is very even anyway, I can now also install another build plate on top, run another automatic bed levelling, apply those fixes again and print right away, getting perfectly sticking prints as shown below. And also adjust easily for different bed and nozzle temperatures when printing different materials.

I added the generated compensation GCodes to a printer profile (PrusaSlicer in my case) that I choose when I want to execute a bed levelling ahead of printing (e.g. after switching filament type). It does a G29 bed leveling, applies the produced GCodes generated by the tool after the very first BLTouch calibration and ist instantly good to go, nothing else needed any more.
G90 ; use absolute coordinates
M83 ; extruder relative mode
M204 S[machine_max_acceleration_extruding] T[machine_max_acceleration_retracting]
M140 S[first_layer_bed_temperature] ; set bed temp
M104 S[first_layer_temperature] ; set extruder temp
G28 ;home all axis
M190 S[first_layer_bed_temperature] ;wait for bed temperature
G29 ;auto bed leveling
; apply x-carriage twist fixes
M421 I0 J0 Q+0.09
M421 I0 J1 Q+0.09
<...and all the others from the tool...>
M421 I4 J3 Q-0.54
M421 I4 J4 Q-0.54
M500 ; save it
G1 X0 Y5 F4000 ; go to start pos
G1 Z1.5 F1000 ; lift print head
M420 S1 Z1 ;use mesh leveling on first 1mm
G1 Y0 Z1 F100 ; move print head up
M109 S[first_layer_temperature] ; wait for extruder temp
G92 E0
G1 E38 F1000; deretract filament
G92 E0
G1 X60 Z0 E9 ; intro line
G1 X100 E12.5 ; intro line
G92 E0
So, if you are facing a similar issue, it’s worth to try it out. Hop over to my tools page, do a new BLTouch calibration run according to the instructions there, enter the measured values in the form and generate the appropriate fix GCodes. If the bed visualizer now shows an almost clean slate (of course showing possibly your bed bumps, but no side particularly tilted), or the values printed after a M420 V command are more or less +/- around the same value (they shouldn’t constantly grow to one side), then you should be happy ever after with your new BLTouch!
Hi vielen dank f
Die Daten beziehen sich insgesamt ja auf den Anycubic Mega S. Wenn Dein Druckbett eine andere Gr
ich habs mal so ausprobiert undzwar mit G1 X170 Y40 F4000 und es funktioniert ich hab mir das Pugin Bed visualizer runtergeladen und im plugin die korrekturwerte im g code nachdem leveln eingef
Prima! ??
Mir f
Hello! First, I want to congratulate your solution for this problem. I also have the exact same problem, but on a different printer, and firmware. I am running Klipper on mine, and Klipper does not support M421 gcode natively. Do you know if there is a way to make it work in Klipper?
Best Regards,
Altay
By the way, this is how Klipper saves the mesh if its useful to you:
#*# points =
#*# 0.091318, 0.093818, 0.133818, 0.148818
#*# 0.056318, 0.013818, -0.001182, -0.021182
#*# 0.043818, 0.006318, -0.016182, 0.018818
#*# -0.026182, -0.096182, -0.121182, -0.053682
Hm…tbh I don’t know Klipper. The Marlin adjustment codes are relative to the initially measured bed, so they are just additional offsets. In case you know the correct offset format, maybe you can just use a text editor to mass replace them from the tool output accordingly (probably using Regex-search/replace). Or you might want to automate it with a batch script (using SED/AWK tools).
Hallo
Vielen Dank f