DIY Motorized Macro Rail

by mattwach in Circuits > Cameras

79 Views, 2 Favorites, 0 Comments

DIY Motorized Macro Rail

DIY Motorized Macro Rail
20241228_StackedBlueberry_0006.jpg
20241228_StackedBlueberry_0034.jpg

Motorized Macro Rail


This is a project for a motorized macro focusing rail. It is used with special "stacking" software to increase the depth of field of macro images. This project is presented as a modification to an existing commercial rail, but could be extended to use a custom built rail (using steel rods and linear bearings commonly used in at-home 3D printers and CNC machines).


The code and 3D model files for this project are located here: https://github.com/mattwach/motorized_macro_rail


Background


Taking images of very small objects is known as macro photography. Using a specialized lens, or an attachable modifier makes this type of photography possible.

Due to the physics of photographic lenses, taking photos of very small objects typically has a very low depth of field, where only a thin plane of the object appears in focus, often much less than 1 mm.

In general photography, it is possible to "stop down" the aperture to increase the depth of field. That is true in macro photography as well, but even stopping down often does not sufficiently address the depth of field problem.

A modern solution is to take many photos where the focus point is slightly shifted, then combine these using software to combine them into a single "stacked" image:

Note that taking these photos requires either a specialized lens, an attachable lens filter or an extension tube. There are endless resources on the web on getting started. Here is one for the basics. Here is one for extreme macro. The amount of detail in this article is impressive and seems beyond what you'll need to know to start experimenting, but a useful reference as you progress.


Alternatives


Manual Approaches


  1. You can use manual focus on your lens to vary the focus distance. It can be challenging to get the step size correct and consistent (especially on a lens not designed primarily for manual focus). The final stacked image will thus often have "blurry" areas where there was no in-focus source image to use. There is also the risk of moving the camera every time you touch it. Still, this can be a great way to start and get familiar with the process. Adjusting focus manually also does not limit you to small objects as stacking larger scenes can be useful too.
  2. You can buy a manual focus rail at many different qualities and price points. That is the starting point for this project. The nice thing about these rails is that they simple to use and easy to bring to the field. The downside is that using them manually can feel like tedious work and you risk moving the camera and introducing vibrations as you interact with the rail.


Automated approaches


  1. You can buy commercial rails at different price points. Here is one and here is another. Price aside, I think a downside of these solutions is the interface. One uses buttons and the other uses a phone app - both seem a bit cumbersome compared to an analog stick when it comes to positioning the camera.
  2. Some cameras have built in focus stacking features while others support remote control phone/computer apps that add the feature. A limitation here is that you will be limited to autofocus lenses and higher-magnification lenses usually do not offer autofocus as an option.

Supplies

assembled_pcb.jpg

These are the parts and equipment I used. Of course, any of them could be swapped with alternatives with varying degrees of challenge:


Parts


Prices are what I found in late 2024. I am mostly suggesting Digikey here because they let you build a single order that contains a mix of low individual part counts.

  1. Stepper motor ($11) Any Nema 17 motor designed for 3D printers will work well. I'm using a lower power pancake style motor, which is still sufficient for the job (as the leverage on a macro rail knob is very high)
  2. Raspberry PI Pico ($4). You could opt for the unit with Wifi/Bluetooth if you want to try and trigger your camera wirelessly but note that this enhancement will require firmware changes and could be a challenge.
  3. 128x128 OLED ($12). The UI is designed for this resolution using a 8x16 font. With some firmware changes, you could go with a 128x64 and switch to an 8x8 font. See src/firmware/README.md for more details.
  4. 4 push-buttons ($1).
  5. Joystick ($6). I'm using an RC gimbal (pitch-roll type) which gives a feeling of precise control. You an get these new or salvage one from an old RC radio. Alternatively, you can opt for a commonly-available "PS2 stick" that will be less precise but possibly good-enough.
  6. Voltage Regulator ($2) most stepper motors need a minimum of 12V, which is beyond what the PI Pico onboard regulator can accept as input, thus you'll need a regulator to help it out. I went with the famous LM7805 which will be powering everything but the motor. Anything between 3.3V and 5V which can deliver > 200 mA should be well into the sufficiency range.
  7. A4988 Stepper Motor Driver ($2). A Pico microcontroller is not designed to power a motor directly and you will need power electronics. The A4988 gives you both the power delivery and an easy-to-use interface which make the motor run smooth and quiet (using microstepping) and provides a number of protections (such as overcurrent protection).
  8. Power connector ($2). I went with a XT-60 connector used with RC LIPO batteries but it's really up to you. The design will support between 12V and around 30V but you'll want to double check the limits of your chosen motor and voltage regulators.
  9. Camera remote shutter release ($1). I went with a 2.5mm jack for this but, since it's the not the camera side, your options are flexible. Many cameras support a simple electronic shutter release. If yours doesn't, you can probably improvise something or go with the manual shutter release option the firmware provides (more on that later).
  10. 4N25 Optocoupler (<$1) This is used to trigger the camera. An optocoupler triggers the camera using light, meaning that the electrical system of the camera and focus rail are fully isolated. This electrical isolation can bring some peace-of-mind about connecting your camera.
  11. 100 Ohm resistor (<$1) The optocoupler needs one of these.
  12. 470 uF capacitor (<$1) The a4988 motor driver requests one of these on the motor voltage input to smooth out voltage transients that are occur when powering motors.
  13. 2x 10 uF capacitor (<$1) These help smooth the 5V power supply.

You will also need a rail. I went with the NM-200s which I acquired on sale for $150. I'd say the NM-180s is likely as good for $130 retail. There are also a number of cheaper options that I have no direct experience with, such as this one for $89. If you go with a NM-XX0s rail as I used, you can use the provided .STL files directly. For other rails you will need to resize the adapter using the free OpenSCAD and instructions provided later in this document.

Equipment

  1. 3D printer. This is used to create the motor-to-rail interface and the housing for the electronics. There are many techniques with wood working, metalworking, CNC, etc, that could be alternatively used if you have the needed skills and equipment.
  2. Camera gear. More on that in the process walkthrough later. In short, just about any camera with interchangeable lenses can be used.

Electronics Build

schematic.png
breadboard.jpg
kicad_pcb.png
cnc_pcb.jpg

See the schematic for the needed connections between components. There are around 2 dozen connections to be made here which makes most assembly methods possible. The second image shows the whole project implemented on a breadboard for testing.


You could transfer the electronics to a perf board and be done with this step. Since I have a 3018 CNC machine, I decided to go a little farther and cut out a PCB: If you want to use a CNC, chemical etch, or order a manufactured board, you can find the needed files in the motor_rail_kicad/ directory.

Code Build

Here you have the "easy" option of uploading a precompiled motorized_macro_rail.uf2 file to your Pico or the "flexible" option of building the binary yourself. Both options are free.


Precompiled


There are many guides for how to do this, just a Google search away. Here is my version.

  1. While holding down the BOOTSEL button, plug in the Pico via USB
  2. It should mount as a USB drive
  3. Copy the firmware/motorized_macro_rail.uf2 file to the USB drive
  4. Unplug and replug the Pico

There are alternatives you can explore as well:

  1. There is a picotool program which allows you to load the macro_rail_automater.uf2 file directly. I prefer it.
  2. Pin 30 on the Pico is named RUN. If you drive it to 0V, it will reset the PICO. If you do this while holding BOOTSEL, you can upload firmware which is ergonomically easier and with less USB port wear-and-tear. I put a switch between RUN and ground (battery negative) whenever I go with a Pico for this reason (as is done in the schematic above).


Build firmware yourself [Optional]


To start, you'll need a working development environment. I'll point you to the official docs if you are not there yet. I personally prefer following Appendix C "Manually configure your environment" first over the VS Code docs, then add VS Code later so I have both options available.

Once your blinking light project is working, your should be close to done. Here are the command line instructions (use the official Pico docs as a guide for VS Code)

  1. First, go into the src/ directory.
  2. In Linux, type ./bootstrap.sh. In Windows, you'll need to follow the steps listed in ./bootstrap.sh which are identical to the official docs.
  3. cd build
  4. make

At this point, you'll hopefully have your own motorized_macro_rail.uf2 file that you can load on your Pico.

Macro Rail Physical Interface

motor_mount.png
flange.png

The goal is to interface your chosen stepper motor with your chosen macro rail. I ended up going with the NM-200s focusing rail which I find sufficient but not amazing. It has some flex which leads to some shifts between photos but the stacking software compensates for this. I might try a cheaper one or potentially DIY one with some steel rods and linear bearings, if I find the time/motivation.

For the route I took, only two printed parts are needed. One interfaces the rail to the motor using a clamping interface. The other printed part interfaces the motor shaft to the finger adjustment knob:

I have included rendered .stl files in the 3d_models/stl directory that you make be able to use directly if you have a compatible rail.

If you do not have a a matching rail, you can probably make a few tweaks to the model and have a working result. By using the freely-available OpenSCAD, you can adapt the clamp interface to various different rails by editing motor_mount/focus_rail.scad and changing the following parameters to match your rail:


RAIL_BODY_WIDTH = 37.8;
RAIL_BODY_HEIGHT = 20;


The numbers above (in mm) are for the NM-200s.

The knob interface design should be adaptable to most (but not all) rail designs. The file to change is motor_mount/knob.scad with the following variables likely being relevant:


KNOB_DIAMETER = 15.1;
KNOB_INSET_DIAMETER = 13.2;
...
finger_cutout_diameter = 4;
finger_cutout_count = 8;

Controller Case

controller.png
controller_stl.png
controller_dxf.png

I'll start by saying you can download an already-exported model you at 3d_models/stl/controller.stl. The rest of this section is if you want or need to customize the case.


In the folder 3d_models/controller, there is a file named controller.scad, which can be loaded into OpenSCAD. The model is parametric and has many variables you can change and experiment with. The bottom of the file allows you to turn components on and off using the standard OpenSCAD prefixes of *, ! and //:


// comment out everything but controller for the 3d print model
controller(false);
placed_pcb();
placed_gimbal();
cover();
// comment out everything but this to create a dxf projection
//cover_projection();


The cover_projection() can be used to create a DXF export for CNC or a laser cut. Alternatively, you can 3D print the cover, likely with some modifications to allow the screen to be viewed:


An exported DXF is available at 3d_models/dxf/controller_cover.dxf if you would like to use that as your starting point.

Configuration

a4988_calibrate.jpg
settings.jpg

Motor Current Calibration


You will need to calibrate your A4988 driver board to set the maximum current for your chosen stepper motor. Instructions on how to calibrate are here with alternate instructions here.


Firmware Settings


If you power on the unit and press the "previous button", you are taken to a menu that lets you change the following settings:


  1. Max Velocity: The maximum motor turn speed. Too high of a value may cause the stepper motor to miss steps or lead to long spin down times if acceleration is not risen to match.
  2. Acceleration: The maximum motor acceleration/deceleration. Too high of a value may cause the motor to miss steps or lead to rail vibrations.
  3. Backlash: When the motor switches direction, it will take some slack before the main gear is engaged; this is known as backlash. If you want a perfect value, you can run the test mode with a caliper attached to the rail. It's usually not critical that this number be fully tuned.
  4. Settle Seconds: This is how long the controller should wait between stopping the rail and taking a photo. The intent is to allow any vibrations/oscillations from rail deceleration to subside.


Steps / mm


This final menu item relates to both your motors steps/rotation and your rails rotations/mm. The A4988 driver is configured in the schematic above to 16x microstep mode, meaning that 16 steps equal one step on the motor. The formula to use is thus:


motor_steps_per_rotation * 16 / mm_per_rotation


For my case, I'm personally using a 200 steps/rotation stepper motor and a 1 rotation/mm rail, thus my number will be 200 * 16 / 1 = 3200.

Process Walkthrough - Setup

connected_rail.jpg
20241227_MacroRail_0001.jpg

You first need to attach the stepper motor to the rail by sliding it on and gently tightening the bolts (don't overdo it). The motor can easily be detached if you don't need it for a given session.

Next line up the camera and target and make sure that nothing is moving.

It's good to have a light on your subject to reduce to exposure time and make the light consistent. Where you place the light is an artistic choice but side lighting is a good starting point. Flash is an option but you might need to slow down your process to allow the flash to charge between shots.

You'll want manual everything on your camera, focus, shutter speed, aperture, ISO and white balance. If these parameters change in any of the photos, it can create problems with the stacking software.

I suggest f/5.6, f/8 or f/11 for aperture. Wider apertures (such as f/4) may have (possibly not perceptible) sharpness improvements due to less diffraction but you will need to take more images to due to less depth of field. Wide apertures may also create larger OOF circles which could lead to artifacts in the stacking software results.

Process Walkthrough - Finding End Points

camera_focus_back.jpg
controller_end_pos.jpg
camera_focus_front.jpg
controller_start_pos.jpg

Find most distant point


Power on the focusing rail and use the joystick to find the farthest out point (note you can also find the closest point first, if you prefer). If your camera has "focus peaking" as a focus aid, I suggest trying it out.


Find closest point


Hit the 'next' button and find the closest point using the joystick.


Process Walkthrough - Shot Delay and Count

controller_shot_delay.jpg
controller_shot_count.jpg

Choose shot delay


Hit the 'next' button to choose the shot delay. My exposure settings indicate that a photo will take 1/8th of a second to take. You also want to think about how long the camera will take to write the photo to the SD card (most cameras will buffer shots in memory, but maybe not enough). If your camera offers a setting for "electronic shutter", I suggest turning it on as any amount of shutter shock is especially visible during macro work.

If you don't have the remote shutter working with your camera, you have the option of choosing 0.0 here. In that case, the rail will pause after each photo, giving you as much time as you need to manually take the photo. In this mode, the "next" button is used to continue.

Choose image count


The correct image count depends on many variables:

  1. How magnified the subject actually is
  2. How many megapixels your camera has and if you plan to pixel peep
  3. Your choice of aperture setting

You'll need to experiment. If you do not know where to begin, I suggest f/8 and 0.2mm and see how it goes (or try this chart).

Hit the 'next' button and choose your shot count


Take photos


Hit the next button to take all of the photos. You can pause/resume the process with the next button or cancel it with the back button. If you find a need to abort everything quickly or just want to start over, you can press the reset button (I suggest using next/back over reset if the motor is spinning).

When all photos are taken, you have the option of repeating the process in the reverse direction with the 'next' button or starting over with the 'back' button.

Load Onto Computer and Run Software

helicon.jpg
focus_stack.jpg

I suggest Helicon focus for reasonably priced, turn key software with a free trial period. The software is for mac or windows but I am running it in Linux with Wine and it runs fine.

If you want a free/open source solution, check out the focus stack project. The main downside of going this route is that the excellent post-stack retouching features of Helicon are not present, but many people are able to use the software to produce excellent images regardless:


Find More Subjects!

Moss_4X-Edit.jpg
needle_stack10_f8.jpg
StackedArduino_82images.jpg
StackedDime_60images.jpg

Here is where your creativity comes in. I have a few images attached to possibly give some idea. Any search on "extreme macro" will give more. Have fun!