Linear delta machines such as the Rostock and the Kossel use three linear axes in a triangular configuration, arms, and some clever math to move a tool in three dimensions.

They can be quite fast due to the low moving mass, in particular in the Z direction, which is usually slower in typical Cartesian 3D printer designs.

Enabling the arm solution

To setup your Smoothieboard for control of a linear delta machine, you must select the linear_delta arm solution ( this is true for all linear delta type bots - older versions of the firmware included separate configurations for Rostock and Kossel printers).

Example file

You can find an example linear delta configuration on github here.

It is recommended you start from this example configuration file instead of modifying the default cartesian configuration file.

To modify your configuration file for a linear delta arm solution ( we just said you shouldn't do that ), change/add the following :

arm_solution                                 linear_delta
arm_length                                   250.0            # this is the length of an arm from hinge to hinge
arm_radius                                   124.0            # this is the horizontal distance from hinge to hinge when the effector is centered

Base parameters

Here is a labelled schematic of a normal linear delta :


The two most important parameters are as follow : 

You need to set arm_radius to be the horizontal distance between the joints on the arm rod when in the home position. An incorrect value for arm_radius will cause the effector's height above the bed to change as it moves around on the X-Y plane.

Set arm_length to the length between joints of the arms. An incorrect value for arm_length will affect the scaling of movements in the X-Y plane - printed parts will come out smaller (arm_length needs to be reduced) or larger (arm_length needs to be increased) than intended.

These are the two main parameters you must get right for Smoothie to move your extruder around precisely. Beyond that, precise construction of your delta printer is critical - in particular, the towers need to be 120° apart and perfectly vertical, and the three arms (including their carriages) must all be the same length to the center of the effector platform.

Coming from Marlin ?

These two parameters correspond to the following in your Marlin configuration :

  • arm_length is DELTA_DIAGONAL_ROD


The linear delta arm solution is pretty much useless without homing.

Do not try to set up a printer without endstops, and do not try to do anything with your printer before you home it.

Test the endstops with M119, and make sure the X endstop triggers when the endstop on the X tower is activated, and same for Y and Z towers.

Here is a generic delta homing configuration:

# Endstops
endstops_enable                              true             # the endstop module is enabled by default and can be disabled here
delta_homing                                 true             # forces all three axis to home a the same time regardless of what is specified in G28
alpha_min_endstop                            nc               #
alpha_max_endstop                            1.25^            # add ! to invert pullup if switch is NO to ground
alpha_homing_direction                       home_to_max      # Home up
alpha_max                                    0                #
beta_min_endstop                             nc               #
beta_max_endstop                             1.27^            #
beta_homing_direction                        home_to_max      #
beta_max                                     0                #
gamma_min_endstop                            nc               #
gamma_max_endstop                            1.29^            #
gamma_homing_direction                       home_to_max      #
gamma_max                                    300              #

alpha_fast_homing_rate_mm_s                  200              # homing feedrates in mm/second
beta_fast_homing_rate_mm_s                   200              #
gamma_fast_homing_rate_mm_s                  200              #
alpha_slow_homing_rate_mm_s                  20               #
beta_slow_homing_rate_mm_s                   20               #
gamma_slow_homing_rate_mm_s                  20

alpha_homing_retract_mm                      5                # retract/bounce distance after homing in mm
beta_homing_retract_mm                       5                #
gamma_homing_retract_mm                      5                #

alpha_trim                                   0                 # software trim for alpha stepper endstop (in mm) (negative values move endstop down)
beta_trim                                    0                 # software trim for beta stepper endstop (in mm)
gamma_trim                                   0                 # software trim for gamma stepper endstop (in mm)

Gamma max

gamma_max is the height the head is above the bed when homed to the top endstops.

Homing the printer to the endstops establishes your printer's maximum Z position, as well as establishing the origin of the XY plane. Ideally, this should also coincide with the exact center of your printer's physical build surface.

alpha_max and beta_max should be left at 0.

alpha_max_travel, beta_max_travel, gamma_max_travel is the max distance the carriage will travel while homing, these MUST be set to at least the total height of your towers and NOT the same as gamma_max, usually it is at least twice gamma_max


The alpha_trim, beta_trim and gamma_trim settings are a way to tweak endstop positions in software and simplify the process of tramming the effector (making sure that moves in the XY plane remain parallel to the print surface).

The trim values are the distance in millimeters from the point where your endstop is triggered.

Note: if you are migrating a printer from Repetier-Firmware, your endstop offsets are defined in terms of steps for your stepper motors. To convert, divide the number of steps by your steps_per_mm for that axis.

M666 Xnnn Ynnn Znnn allow you to adjust the trim values on a live system.

You need to home after setting M666.

Negative values adjust the endstops down by that number of mm. Positive values are up.

When you have found the correct values for your endstop settings (see the suggested workflow near the bottom of this page for one process to adjust the trim values), edit the config file and reboot, or save the M666 values with M500.

Note for Deltas using M666 to set soft trim

The latest edge now uses soft trim, this allows positive and negative trim values without crashing your endstops.
(Note the old suggestion of adding -5 to all your trim values is no longer valid and will do nothing other than lose 5mm from your build height).

When you home a delta that has non zero trim values, you will find that X and Y are not 0 after homing. This is normal.
If you want X0 Y0 after homing you can set `move_to_origin_after_home true` in the config (thi sis the default now), this will move the effector to 0,0 after it homes and sets the trim. Note that the carriages will move off the endstops a little bit after homing so the head can move without crashing into the endstops.

Arm parameters

arm_length and arm_radius can be set live using : 

M665 L340.0 R240.5

Where L is the arm_length and R is the arm_radius

Home must be called after setting these.

Simply doing :


On its own will just report the current settings.

These can also be saved with M500.

It's all relative

Changing arm_radius actually changes the relative height of the center to the edges, so after changing the arm_radius you MUST measure both the outer edges and the center, the center alone will appear to not change.

This is NOT a bug.

A suggested workflow for calibrating arm_radius and gamma_max when you first set up a delta printer would be:

  1. Home, then adjust gamma_max until the z-height is correct at the center of the print bed (lightly holding down a sheet of paper).
  2. Re-home, then jog the effector platform near the alpha tower. Adjust alpha_trim using M666 or a physical endstop screw, re-home, and repeat until the paper is held down with equal force at Z=0. (tip: you may want to write some G-code snippets to automate this process, or else you may find yourself doing a lot of jogging - sample scripts developed by Gene Buckle (author of the Rostock Max assembly manual) are at the bottom of this page.)
  3. Repeat step #2 to set beta_trim and gamma_trim (or physical endstop screws) appropriately near the beta and gamma towers.
  4. Re-check the z-height at the center of the bed. If the effector is too high, increase arm_radius slightly, and return to step 1 of this sequence. If the effector is too low, decrease arm_radius slightly, and return to step 1.

Once the z-height is correct, your printer should be well-calibrated. You should not need to re-do these calibration steps unless you change hardware on your printer.

Height calibration

Your printer homes by "seeking" the endstops at the top.

When that is done, your printer is always at the same position, every time : The Z axis is at it's maximal position, and the X and Y axes are at the center of the work area ( 0,0 ).

But it doesn't know how high above the bed it is, unless you tell it. And it needs to know this, so that when you tell it to go to Z 0 ( the bed ), it knows how much to move from it's position at the Z maximum.


There are several ways to tell Smoothie how high the hotend is from the bed after homing :

Configuring Z height

After homing, the machine knows it is at X position 0, Y position 0, and Z maximum position.

Because of this, it will read the configuration option gamma_max and set the current Z position to that value.

So after homing, the Z position is set to gamma_max.

This means that if your hotend is 300mm above your bed after homing, and you set gamma_max to 300, after homing, you can just tell the machine to go to Z position 0, and it will go to the bed's height.

To find the right value for gamma_max do one of the following :

Finding gamma_max manually

First home the machine


Then set the current Z position to 0

G92 Z0

Then move the head to the bed, using G0 Z(position) or Pronterface or the web interface.

Once the head is exactly at the bed, issue this command


This will return the position of all axes. The current position of the Z axis is your gamma_max value.

Simply edit the configuration file to set this value, and reset the board.

Alternatively you can use the M665 Z(distance) command to set the value in the config override system, and M500 to save that value to the SD card.

The gamma_max value in the configuration file is ignored if M665 is set and saved.

Next time you home, the machine will know how high above the bed it is.

Simplified manual adjustment method

First home the machine


Then move to the point the machine currently thinks is Z 0

G0 Z0

Then move the head to the bed by jogging, using Pronterface's arrows, the panel or the web interface.

Finally issue the M306 Z0 command which will use the current Z position as a homing offset.

Then save to the SD card with M500.

Next time you home, the machine will know how high above the bed it is.

Finding gamma_max with a probe

If you have some sort of probe attached to your head ( or bellow your bed ), which triggers when the hotend gets close to the bed, then you can use this to find your gamma_max value without manually jogging.

Now there are two different cases here :

  • Either when the probe is triggered, the hotend is exactly at bed level
  • Or, when the probe is triggered, the hotend is above the bed by a given distance, which we will call the z probe offset.

First home the machine


Then ask the probe to go find the bed


This will report the distance travelled by the probe.

Your gamma_max value is that reported distance, plus the z probe offset ( distance between the probe triggering point, and the bed ).

Simply edit the configuration file to set this value, and reset the board.

Alternatively you can use the M665 Z(distance) command to set the value in the config override system, and M500 to save that value to the SD card.

The gamma_max value in the configuration file is ignored if M665 is set and saved.

Next time you home, the machine will know how high above the bed it is.

Automatically finding the bed with a probe

Smoothie allows you to save both the Z height, and the delta calibration data, to the SD card.

This means you do not need to probe every time you start the machine, you only need to do it once, and save the values, which will then stay valid as long as your machine's geometry doesn't change.

This means you can have a removable probe that you only connect and attach to the head at the rare occasions when you need it.

However, if for whatever reason you have a fixed ( or retractable ) probe on your head ( or sensors bellow your bed ), then you might want to automatically probe at the beginning of each print.

To do so, simply change your slicing program's "beginning of file" G-code sequence, and replace


with :

G30 Znnn

When nnn is the distance between your probe's triggering point, and the bed.

The G30 Znnn command moves the head until the probe triggers, then sets the current Z height to nnn

So for example if your probe triggers when the hotend is 5mm above the bed, do G30 Z5, and if your probe triggers exactly when the hotend touches the bed, do G30 Z0.

Automated calibration

See ZProbe for how to use zprobe to calibrate a delta.

Here is a common sequence that you may do to auto calibrate the delta for the first time, this need not be repeated unless the bed changes.

; do endstop and delta radius calibration
; Home
; move to 5mm above bed
G0 Z5
;  then manually jog down until nozzle is on bed or just traps a sheet of thin paper
; sets the Z homing offset based on current position
M306 Z0
G0 Z1
; check nozzle is 1mm above bed
; saves the results in EEPROM equivalent

Full example configurations ( including zprobe ) can be found at

See for more details of manually calibrating a delta.

Manual Calibration.

After setting gamma_max to 20 mm above bed, home, then move to a point at the edge of the bed in front of tower X. get the head set just right (paper width or whatever) do M306 Z0 then Home.
Do it again and test it is the same. Then move to the spot in front of tower Y, adjust M666 Ynnn until it is the same height, home between each test and setting of M666.
Then do the same for the Z tower using M666 Znnn
Then home and check all three, repeat until they are all the same
Once they are the same save M666 with M500.
Then test the edge vs the center
adjust arm radius (M665 Rnnn) until they are the same, home between each setting. then save with M500.
Then test the three towerpoints and the center again after homing, repeat above until they are all the same.
Lastly set the z height at the center with M306 Z0 and save with M500.

Or use the auto calibration which does exactly that procedure automatically. (Except for the Z height which you still need to do after calibration).

Manual calibration scripts

The following scripts were written for a Rostock Max (280mm diameter bed). If your printer's bed is much larger or smaller than that, adjust the X/Y parameters in each script as needed to put the effector near each tower (so that one arm is nearly vertical). These scripts can be copy/pasted repeatedly into a terminal window, or run from your host program of choice (Pronterface, Repetier-Host, Octoprint, etc.)

Script 1: Center of bed

G0 Z0 F3500

Script 2: Alpha tower

G0 Z0 X-77.94 Y-45 F3500

Script 3: Beta tower

G0 Z0 X77.94 Y-45 F3500

Script 4: Gamma tower

G0 Z0 X0 Y90 F3500

Here's a manual calibration tutorial video : (NOTE the second video mentioned in this video has a technique which IMO is NOT a good fine tuning method, the one where he measures the first layer thickness, this is not a good way to adjust trim).

Advanced settings

The following settings can be set in the config, or via M665. They are used to compensate for a frame that is not perfectly aligned, it is recommended the frame be fixed rather than using these to compensate. Generally speaking adjusting any of these to anything other than 0.0 will fix one thing but throw another thing off. NOTE these are usually used with an offline program that calculates the values by doing some form of error minimization.


alternatively the values can be changed live (and saved with M500):-

M665 Axxx Bxxx Cxxx Dxxx Exxx Hxxx

where A is delta_tower1_offset, B is delta_tower2_offset, C is delta_tower3_offset
where D is delta_tower1_angle, E is delta_tower2_angle, H is delta_tower3_angle