MarlinFirmware / Marlin

Marlin is an optimized firmware for RepRap 3D printers based on the Arduino platform. Many commercial 3D printers come with Marlin installed. Check with your vendor if you need source code for your specific machine.
https://marlinfw.org
GNU General Public License v3.0
16.14k stars 19.2k forks source link

G29 UBL issue with the extrapolation beyond the probe area ? #7508

Closed dagnall53 closed 7 years ago

dagnall53 commented 7 years ago

I suspect I am seeing an interpolation issue when the head goes beyond the probed area. In summary, my z offset increases dramatically ( about 10mm increase in height for 1mm lateral movement) at "corners" beyond my probed area. The effect does not appear in all corners. Some areas beyond the probed area are fine.

I have tried some tests to explore the issue, they are below. The issues appear mainly in the "bottom right" area of the bed. Bed Topography Report: (0,4) (4,4) (-60,60) (60,60) -0.011 -0.005 -0.001 -0.025 -0.006

-0.041 -0.015 -0.004 0.045 -0.026

-0.021 -0.004 [ 0.060] 0.041 0.019

0.024 0.025 0.100 0.068 0.067

0.022 0.013 0.065 -0.026 0.024 (-60,-60) (60,-60) (0,0) (4,0) Is it possible that the extrapolation algorithm outside the probed area is badly behaved or has a bug?

Any suggestions? I would consider increasing the probe bed size, but with the issue of magnetic joints disconnecting at extreme positions, would prefer if I can avoid attempted probes at the extremes.. Thanks!

Details ... I have a large magnetic jointed delta, bed diameter 260. I use a (rectangular) probe area of +-60, as sometimes the magnetic joints can disconnect at extreme angles. (I am working on this) With UBL I find that when I move (after a G29 P1 /P3 calibration) some movements outside the probed bed react as though there were additional calibration settings (but very wrong). I move for example to : x0, Y-110 and the head is at a well calibrated z. However as I move X positive beyond x=61 the head starts to increase z offset dramatically. However, when moving X negative at the same Y I can reach the edge of the printable area without z offset.

At Y=100, the offset starts when X> 30, but there is no offset when x goes negative...

Setting X+ 100, I get z offsets when y goes negative beyond -30, and when y goes positive beyond 0 (!) With X at -100, there are no z offsets with negative y, or positive y to the extent of the printable area.

To me this looks like the levelling algorithm is making some assumptions about the "beyond print bed" z offsets that are incorrect.

FHeilmann commented 7 years ago

Which version of Marlin are you using? If it's not the latest bugfix-1.1.x, try that.

@Roxy-3D pushed a fix to that branch 13 days ago under pull request #7415

oldmcg commented 7 years ago

For UBL on delta, the extroplation beyond outer UBL grid points is simply bilinear from the adjacent grid square. However, if you're trying to reach a point outside a grid corner (no adjacent grid square), I'm not really sure what would happen. I'll look at adding a check to make sure that doesn't happen.

Sounds like you're using a UBL grid of +/- 60mm but attempting to print or reach points at +/- 100? I would not expect any point outside of around +/- 10% of the outer grid to be accurate enough to print.

The UBL on delta is designed to allow a UBL grid size with mesh inset of zero, meaning the UBL corner points are physically unreachable. This ensures all the printable points are within the UBL grid. That doesn't mean you have to probe those unreachable points. UBL on delta will only probe points that are within the DELTA_PRINTABLE_RADIUS. Your DELTA_PRINTABLE_RADIUS should define a circle that your mechanics can reach without binding, and then the UBL grid should cover that square with the UBL "corners" outside of the reachable radius. Probing will skip those locations that cannot be reached (as defined by DELTA_PRINTABLE_RADIUS), and then after G29 P1 and P2, you extrapolate those unreachable grid points using G29 P3.1 (not very well documented, I know).

If you need more help getting the #defines right, please attach your configuration.h and I'll take a look and offer some suggestions.

And as @FHeilmann mentioned, make sure you're running latest bugfix-1.1.x branch.

FHeilmann commented 7 years ago

I was wondering if it would make sense for UBL in general, during mesh generation, to generate additional (virtual) mesh cells that go beyond the travel limits of the printer.

(e.g. if I have a 300x300 build plate and create a 7x7 mesh that spans (0,0) - (280, 280) the resulting stored mesh will be 9x9 and span (-40,-40) - (320, 320) where the outermost mesh points are either replicated from their closest inner neighbours or interpolated from the shape of the inner mesh points)

While this will result in significant storage overheads it would make the whole nozzle-goes-out-of-mesh-bounds issue much easier and require less code to catch all the edge cases.

Roxy-3D commented 7 years ago

I would also suggest a more dense mesh. Maybe 10x10 instead of 5x5. Delta's have a number of places in the calculations where various errors creep in and start a ripple pattern that goes across the bed much like dropping a pebble in a pond. Except the wave height gets bigger as you get away from the center.

Roxy-3D commented 7 years ago

While this will result in significant storage overheads it would make the whole nozzle-goes-out-of-mesh-bounds issue much easier and require less code to catch all the edge cases.

Well... I'm not sure everybody will agree. But the mesh should be defined such that you never go off of it. But even so... With that latest update, if the nozzle goes off the mesh (at least for the Cartesian machines), the correction returned is 0.000.

oldmcg commented 7 years ago

@Roxy-3D, I have the code the written from before the freeze to extrapolate outside the mesh for cartesian, it's actually LESS code than checking for the edge cases of outside the grid and returning zero. But I think in general the mesh inset shouldn't exceed a cell width.

@FHeilmann, forcing the grid size to be superset of printable area is definitely an option at the expense of storage, but I'm not sure if it is necessary as long as the area outside the outer mesh points aren't significantly far, preferably less than half a cell width. The code to extrapolate is not really any additional code at all -- it is just allowing the interpolation of the adjacent cell to extrapolate outside the cell.

FHeilmann commented 7 years ago

@Roxy-3D what do you mean by "return 0.0", 0.0 w.r.t. the nozzle position at the mesh-boundaries or 0.0 w.r.t. to the Z0 point? The latter sounds dangerous for a concave bed where one edge is higher than the Z0 point. If the nozzle goes outside the mesh over such an edge the nozzle would get smashed into the bed in an attempt to go back to Z0.

Sorry if my incomplete view of the UBL system causes me to ask redundant questions.

Roxy-3D commented 7 years ago

or 0.0 w.r.t. to the Z0 point? The latter sounds dangerous for a concave bed where one edge is higher than the Z0 point. If the nozzle goes outside the mesh over such an edge the nozzle would get smashed into the bed in an attempt to go back to Z0.

Yes... The fact is without mesh points to define what the correction is supposed to be, the best you can do is guess. Is it dangerous? Well that is part of the reason I try to get people to physically level their bed as much as possible.

Also... Both the Auto Probing and the G26 are setup such that they expand outward from the starting point. This is deliberate. It results in a lot of extra movement of the nozzle but it is moving across areas of the bed that have already been used and are 'safe'. If the user is concerned (because the nozzle is getting too close to the glass), they can stop the command and make edits to the mesh in that area of the bed.

A lot of effort was put into not doing things that will damage a user's machine. But with that said, if the user sets up the machine wrong, there is only so much that can be done to protect them from themselves.

And seriously... with the ability to do a 15 x 15 mesh, there are plenty of mesh points available. Doesn't it just make sense for the mesh to cover the entire printable area of the bed?

FHeilmann commented 7 years ago

Absolutely not, but people may be drawn to using a smaller mesh in order to make all mesh points reachable by their probe and removing the need to either manually probe unreachable points or figuring out fill values, expecting that the leveling will still be "good enough" even when moving outside of the mesh (as is the case with bilinear leveling, for example).

I'm just playing devils advocate here. Personally (except for some misunderstandings on my part - sorry for that overhead) I have used UBL without problems and am grateful for all the work that went into it.

dagnall53 commented 7 years ago

Wow lots of comments, thanks.

I am using the version uploaded 5/07/2017.. simple subsidiary question, is there a comment somewhere other than in the configuration.h that has the version number? .. Its all very well having "#define CONFIGURATION_H_VERSION 010100" in the configuration, but I, like many, I expect copy my old config across when trying out new code.. and soon forget which version i'm now using.

My DELTA_PRINTABLE_RADIUS is 125, which I "should" be able to print to without binding... Mostly this is fine, just that at some extremes the magnetic joints are only just holding on (read they pop out!) The only time this occurs in normal use is during the bed probe at the outside edges (!)....

@oldmcg .. Could you explain the comment "G29 P3.1 (not very well documented, I know)." I would have assumed G29 P3 0 was the correct form to get the unpopulated parts set to zero?... Some sage advice on this would be much appreciated...

Configuration".h" is attached in case anyone can spot anything else stupid I may have done.. Or you may like my allen key stow/extend code, which tries to reference most movements to the plunger retract position. (Where I have a 40mm m3 hex bolt sticking up. The probe brushes this to extend, rather than trying to brush against the Z drive belt. To retract, the same bolt pushes the probe back up). Thanks all for the comments.

Configuration.txt

oldmcg commented 7 years ago

G29 P3.1 is not documented along with the regular G29 P3 comments -- it is mentioned further down in the source code in ubl_g29.cpp. I need to fix that.

Your config shows printable (reachable) radius of 125 but mesh inset of 65.

I recommend you try first shrinking the printable radius to 120 or smaller just to make sure you're not binding. Move the head to Z height of 50 and then move X/Y to the extremes and see if mechanics bind. If it looks like more room to move the head in all directions without binding or overflying a bed clamp, expand the radius and try again until you are comfortable with it.

Once you have printable radius set that won't exceed your mechanical limits, I recommend UBL_MESH_INSET of 1 and a grid size of 9x9 or 11x11 (use an odd size to get a point in the center). This results in a grid with corners that are outside the DELTA_PRINTABLE_RADIUS, but that is by design.

If your X/Y_PROBE_OFFSET_FROM_EXTRUDER are set correctly, G29 P1 will probe only those grid points within the mesh grid that keep both the printhead and the probe within the DELTA_PRINTABLE_RADIUS (it looks like a 3/4 moon). Then you can run G29 P2 to fill in the crescent moon that the head can reach but the probe can't, or you can skip P2 and go straight to G29 P3.1. Unlike the regular G29 P3 that fills only a few unprobed points at a time, G29 P3.1 fills all the unreachable grid points in single pass, using the average bed tilt (least squares fit). Because delta geometry frequently results in an apparent cup/bowl bed (even if glass is perfectly flat), I recommend using G29 P3.15 to give extra weight to the nearest probed points when extrapolating unreachable points (again, not documented in the correct place yet, still new code). Use G29 T at each stage to see which points are filled in and remain to be filled in.

No matter what size mesh or inset you specify, delta printer should NEVER attempt to move head outside the DELTA_PRINTABLE_RADIUS, no matter what command you give it. So it should never bind the rods/connectors if you have that defined correctly. If you ever find the printhead going outside the DELTA_PRINTABLE_RADIUS then I'd definitely like to know about it so I can find/fix it in the code. By the way, DELTA_PROBEABLE_RADIUS is only used by G33, not by UBL P1. UBL P1 uses DELTA_PRINTABLE_RADIUS and X/Y_PROBE_OFFSET_FROM_EXTRUDER to determine where the head and probe can move to avoid going outside DELTA_PRINTABLE_RADIUS.

If you change anything in the delta geometry (like G33) then be sure to re-run G29 P1/P2/P3.15.

Happy to help you with any problems with UBL on delta.

dagnall53 commented 7 years ago

@oldmcg Thanks, most helpful. I think the answer for my situation is actually to have a negative UBL_MESH_INSET. I guess this was not originally anticipated, but it effectively means I can set a mesh larger than the printable area, and trust the DELTA_PRINTABLE_RADIUS check to only probe the elements inside my print area. This effectively gives me an inset probed area, but also allows P3 to add nice points outside those probed, avoiding (so far) any undesired Z corrections. I am not sure if I should do two P3's to fill all the points or if one is adequate. I have appended the results at the end for you to see.

I used UBL_MESH_INSET -15 and GRID_MAX_POINTS_X 7 to get a nice set of points inside the printable area, avoiding the extremes where the magnetic ball joints are problematic. The issue with these magnetic ball joints is not so much "binding", but that at some extreme angles, some of them (not all!) are prone to sliding out of joint. This is repeatable, and only at some extremes of the print area that I can usually avoid when printing (but which the original probe set used if I did not use the large inset....) ..

PS I found the notes about P3.1xx... I have just used P3 so far, but may see what the various 3.1xx options do. (copied here so others can find them..) // P3.1 use least squares fit to fill missing mesh values // P3.10 zero weighting for distance, all grid points equal, best fit tilted plane // P3.11 10X weighting for nearest grid points versus farthest grid points // P3.12 100X distance weighting // P3.13 1000X distance weighting, approaches simple average of nearest points

Many thanks Dagnall

Attached example from pronterface of P1, T0 P3 T0 P3 T0.... P1 example.txt

Roxy-3D commented 7 years ago

I think the answer for my situation is actually to have a negative UBL_MESH_INSET. I guess this was not originally anticipated, but it effectively means I can set a mesh larger than the printable area, and trust the DELTA_PRINTABLE_RADIUS check to only probe the elements inside my print area.

This is an interesting idea. You are correct. It was not originally intended. But it is good idea to support!

dagnall53 commented 7 years ago

Thanks, I will close the issue now there is a good solution!

github-actions[bot] commented 3 years ago

This issue has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.