An open-source, Python3-based GUI to control stepping motor-driven syringe pumps with G-codes.
- This project provides you with the tools,
SyringeGUI(latest version: 2.4.1) and itsconfig-generator(latest version: 1), to control DIY syringe pumps (max. 3 pumps) connected to an Arduino device. - Licensing:
SyringeGUIandconfig-generatorare free software, released under the MIT license. - You can modify the scripts for your own works.
- The coding for this project was assisted by AI. Any feedback including bugs and suggestions are welcome.
config-generatormight also be helpful for CNC users to determine Steps/mm values for the machine.- Standalone pre-compiled packages (
.app/.exe) are available from releases.
- DIY syringe pumps consisting of
stepping motors (bipolar/4-wire)and an actuator such as lead screws and tables/sliders. - Control devices: 1x
Arduino Uno/Nanoandstepping motor drivers(as many as needed) like DRV8825, A4988, etc. - Option:
CNC shield v3.0for Arduino Uno orCNC shield v4.0for Arduino Nano
Note: You can only use the highest microstepping for your stepper driver with the CNC shield v4.0 unless the board is modified. AC-to-DC converter(12 V, at least 3 A for 2 pumps).Any computerthat can run Python 3.10 or higher (Mac, Win, Linux, or Raspberry Pi).
You can find many great instructions on making DIY syringe pumps. To start this project, I was highly impressed and inspired by the "poseidon" system.
- https://github.com/pachterlab/poseidon
- https://www.instructables.com/DIY-Syringe-Pump/
- https://chem.uncg.edu/croatt/flow-chemistry/building-the-syringe-pump/
- https://reprap.org/wiki/Open-source_syringe_pump
- https://www.mass-spec.ru/projects/diy/syringe_pump/eng/
Note: In this project, the mechanical syringe pump parts were obtained from a Chinese company.
The details are well described in poseindon system. Here I just tell you techinical tips to adjust the Vref (reference voltage), which determines the maximum current flowing to the motor, for stepping motor drivers, such as DRV8825 and A4988. Proper adjustment is critical to maximize motor performance while avoiding the overheating of the motors and drivers.
For this process, you will need a multimeter (electrical tester) to check the voltage.
The following site could help you to calculate and set Vref.
https://www.circuitist.com/how-to-set-driver-current-a4988-drv8825-tmc2208-tmc2209/
Vref = Imax × Rs × C × RF
- Imax: Rated current of the motor
- Rs: Sense resistor value (DRV8825:
0.1 Ω, A4988:0.05-0.1 Ω)- C: Coefficient specific to drivers (DRV8825:
5, A4988:8)- RF: Reducing factor to keep the circuit safe (typically
0.8-0.9)
To find the rated current, check the datasheet of your stepping motor. It is typically 0.8 - 2.0 A for NEMA17 stepping motors, which are commonly used in DIY syringe pumps. If you do not know the specifications of your motor, start with 0.8 A as Imax for safety. For the DRV8825, a Vref value around 0.5 V is usually optimal for controlling standard NEMA17 motors.
Before running the SyringeGUI software, you need to flash your Arduino with a sketch that includes the script to control stepping motors via the GRBL library.
Steps (Verified on Arduino IDE 2.3.8 for macOS):
- Download and install the Arduino IDE.
- Download the GRBL v1.1h library (grbl-1.1h.20190825.zip).
- Unzip the ZIP file and find the internal
grblfolder, zip only this internal folder again. - Open Arduino IDE ->
Sketch->Include Library->Add .ZIP Library... - Select the zipped
grblfile you just created. - Select
Filetab ->Examples->grbl(usually found at the bottom) ->grblUpload.
If you cannot find it, restart the Arduino IDE and try step 6 again. - A new sketch window will open.
- Connect your Arduino Uno/Nano to your computer using a USB cable.
- Select
Toolstab ->Board:-> Select Arduino Uno or Nano. - Select
Toolstab ->Port:-> Select the USB serial port connected to the Arduino.
(e.g.,/dev/cu.usbserial-XXXXor/dev/cu.usbmodem-XXXXon Mac;COMxon Windows)
In case that you use Arduino Nano, you might need to select "ATmega328P (Old Bootloader)" forProcessor:. - Click the Upload button (indicated by the right arrow icon
→). - Once completed, your Arduino device is successfully flashed and ready to use!
This project consists of two main tools:
SyringeGUI: The main controller application for the syringe pumps.config-generator: An utility to create and manage theconfig.jsonfile for mechanical setups and syringe types.
Prerequisites
-
Python 3.10 or higher is recommended.
-
pip (Python package installer).
This GUI is built using Python's standard
tkinterlibrary andpyserial.Alternatively, standalone pre-compiled packages (
.appfor Mac /.exefor Windows) are available. Since they are compiled with PyInstaller, Python 3 and its libraries are not required to run them. Please download from releases.
Open your terminal (Command Prompt/PowerShell for Windows) and follow these steps:
bash
git clone https://github.com/hiro-shikata/SyringeGUI.git
cd SyringeGUI
pip3 install --upgrade pip
If you have not installed Python3, please download and install it from python.org
pip install pyserial
Important Note for Linux & Raspberry Pi OS:
Tkinter is often not included by default in Linux distributions.
Please run:
sudo apt update
sudo apt install python3-pip
pip3 install pyserial
If you encounter issues installing pyserial, it is recommended to install it within a virtual environment (venv):
python3 -m venv venv
source venv/bin/activate
pip install pyserial
🍎 macOS
Miniconda/Anaconda Users: If you encounter errors like _tkinter not found, ensure you are using the base environment or have installed tk via conda (conda install tk).
Security: You may need to grant "Input Monitoring" or "Serial Port" access depending on your macOS version.
💻 Windows
Port Discovery: Look for COM ports (e.g., COM3) in the Device Manager.
Python Path: Ensure "Add Python to PATH" was checked during installation.
🍓 Raspberry Pi OS / Linux
Permissions: You might need permission to access the serial port. Add your user to the dialout group:
Bash
sudo usermod -a -G dialout $USER
(Please Log out and log back in for changes to take effect.)
CPU Load: On older Raspberry Pi models, high-frequency GUI updates might cause slight lag.
If you use venv to install pyserial, you need to activate venv before running SyringeGUI.py.
Bash
source /home/USER/venv/bin/activate # Replace USER with your USER directory
python3 /home/PATH/SyringeGUI_raspi.py # Replace PATH with your path to locate the `SyringeGUI`
Alternatively, you can use Desktop Entry as a shootcut to run SyringeGUI without operating Terminal. Please replace PATH on the distributed SyringeGUI.desktop file with your correct path. Then, please place the file on your desktop or somewhere and just click it.
The code for Raspberry Pi OS is distributed as Syringe_GUI_raspi.py in rasp folder. That GUI appearance is optimized when Raspberry Pi 7-inch Touch Screen Display or its alternatives are used.
Run the config-generator app to define your pump's mechanical settings (Steps/mm, Max Rate, etc.). While you can modify these settings via the Arduino IDE, using this interactive app is much easier.
Bash
python3 --version # Check the installed Python 3 version
python3.XX config-generator_v1.py # Replace XX with your actual version (e.g., python3.10)
- At Tab 1: Pump Settings, please choose a method to specify the
Steps/mmvalue, which is the most crucial setting for this system.- A. Step Angle: Stepping motors rotate at a specific angle (e.g., 0.9°, 1.8°, or 18°) per step (pulse) received from the Arduino device. Please check the specifications of your stepping motor. For standard NEMA17 motors, this angle is typically
1.8°. - B. Microstepping: Specify the microstepping setting configured on your motor driver. This is determined by the jumper pin configuration on your CNC shield and the driver's specifications. For example, when using a DRV8825 driver on a CNC shield v3.0 with M0, M1, and M2 all set to HIGH (all three jumper pins set), it enables
1/32microstepping.
- A. Step Angle: Stepping motors rotate at a specific angle (e.g., 0.9°, 1.8°, or 18°) per step (pulse) received from the Arduino device. Please check the specifications of your stepping motor. For standard NEMA17 motors, this angle is typically
- C. Gear Ratio: This setting is optional. Since general DIY syringe pumps do not utilize gears, simply enter
1in this box. If your specific hardware setup includes a gear assembly between the motor and the lead screw, please specify that precise ratio. - D. Lead Screw Pitch: You can enter the pitch value directly, or calculate it by measuring the number of threads within a specific physical length.
- Specify the values for
Max rate (mm/min),Accel (mm/sec²), andMax Travel Distance (mm)according to the on-screen instructions. - Fill out the settings for all active pumps. Alternatively, you can check the box at the top to instantly copy the configuration of Pump X to the other pump columns.
- At Tab 2: Syringe Settings, you can register and manage your syringe profiles. You only need to provide a
Name,Volume (mL), andLength (mm)for each syringe.
Tip for Accuracy: For the highest precision, it is highly recommended to calibrate this value by measuring the weight of the dispensed water using a precision weighing scale (mass-to-volume calibration).
6. 5. Click Generate New Config File to save your settings. Save the generated file as XXX.json (replace XXX with your desired configuration name) into the directory ~/SyringeGUI_Data/CONFIG.
- You can also modify existing JSON files using this app. It is easier to load the distributed default
onfig.jsonfirst. - You can generate and use multiple JSON files as needed (e.g., if you run different pump systems with a single controller).
- If no JSON files are found in the directory, SyringeGUI will automatically fall back to its internal default settings.
-
Rate Limitation: For Arduino Uno/Nano based setups, ensure your Max Rate does not exceed the theoretical limit calculated in the
config-generator_v1. Exceeding a 20kHz pulse frequency may cause the stepper motor to stall or behave unpredictably. -
Invert Direction: Check this setting in the
config-generator_v1if your pump moves in the opposite direction than expected.
Bash
python3.XX SyringeGUI.py
- Navigate to the
Settingstab. - In the Serial Port Settings section, click the combobox to display the available port tree.
- Choose the same port used in the Arduino IDE (
/dev/cu.usbserial-XXXX//dev/cu.usbmodem-XXXXon Mac,COMxon Windows,/dev/ttyACM0on Raspberry Pi). - Click the
Connectbutton. - You can monitor the connection status message in the
Logwindow on theManualtab.
Once the connection is successfully established, the app will automatically connect to the pumps on the next startup.
- You can review the
Current Configurationin theSettingstab. By default, the internal default settings are applied. - Click
Load Different Config JSON. - Navigate to the directory
~/SyringeGUI_Data/CONFIGand choose your generated JSON file. - After selecting the file, only the syringe list will be loaded into the UI.
- To synchronize the mechanical settings with the Arduino device, click
Sync to Grbl EEPROM. - You will see a confirmation message in the Log window on the
Manualtab.
Once these settings are written to the Arduino's EEPROM, you do not need to repeat step 3.2 on subsequent launches of SyringeGUI.
By default, the path ~/SyringeGUI_Data/ is selected as the default save directory. You can change this destination folder at any time by clicking Select Directory.
Once you select a new directory, CSV files for experimental settings will be generated there immediately. To apply the new path to the main system log file, you will need to restart SyringeGUI.
photo
Manually control your syringe pumps using the following features:
-
Choose Pumps:
Checkboxes are located at the top of the three columns named Pump X, Y, and Z. Checking them activates the respective pump for operation. -
Select Syringe:
Select your syringe type from the populated combobox list. -
Flow: Input the desired flow rate speed to inject or draw. Entering a negative value will move the pump in the opposite direction. Changing the unit automatically recalculates the flow rate value.
-
Duration:
Defines the total operating run time for the pump. -
Max Vol.: Specifies the maximum volume capacity the syringe can handle. If your syringe is partially filled, set that specific limit here. If the calculated volume (Flow × Duration) exceeds the Max Vol, the app will block the pump execution for safety.
-
RUN/STOP X, Y, Z:
Runs each pump individually. Note: If at least one pump is already running, you cannot start another individual pump. This is a technical hardware limitation of the current GRBL setup. -
RUN/STOP ALL:
Runs all activated pumps simultaneously using their respective individual settings. -
Reset Position:
Displays the current real-time position and volume for each pump. These values initialize to 0 when the app starts. It is good practice to clickRESET POSITIONbefore starting a new experiment. -
Jog:
Provides manual jog controls for fine adjustments. Adjust the rate using the slider bar or input a precise numerical value. Maximum and minimum jog rates are automatically bounded. -
Log & Command window:
Displays real-time serial communication between the app and the Arduino. You can also manually input GRBL-supported hex commands (e.g., enter$$to view the active GRBL core settings).
Execute sequential, complex automated profiles using this tab. You can load a custom CSV file to specify your sequence recipes.
- File Selection:
Click to choose your sequence recipe CSV file. Once loaded, the steps are populated as an preview list and visually mapped on the right panels.
The configuration CSV file must follow this exact format:
Pump, Start time (s), End time (s), Flow (µm/min)
Example recipe:
X, 0, 60, 100
X, 60, 120, 200
Y, 0, 120, 100
Z, 90, 120, 50
Note: Only commas (,) must be used as delimiters to separate values in the CSV file.
Note: There is no restriction on the number of sequence rows.
Note: Only the specific pumps declared in the CSV recipe will engage in motion.
How it executes:
- From 0 to 60 sec: Pump X moves at 100 µL/min, and Pump Y moves at 100 µL/min.
- From 60 to 90 sec: Pump X accelerates to 200 µL/min, while Pump Y continues at 100 µL/min.
- From 90 to 120 sec: Pump X runs at 200 µL/min, Pump Y runs at 100 µL/min, and Pump Z joins at 50 µL/min.
- Execution:
"START SEQUENCE": Begins the sequence run.
"PAUSE": Temporarily pauses the running sequence.
"RESUME": Restarts the sequence precisely from the paused timestamp.
"ABORT": Triggers an emergency stop and resets the sequence recipe completely.
To achieve maximum pumping accuracy, performing a physical calibration is highly recommended. Use the following procedure:
- Click
Reset Positionin the UI. - Physically measure the exact distance between the moving table/stage and the end of the lead screw (or main frame body).
- Move the stage as far as possible (~ 100 mm) using either the Manual
RUNorJogcontrols.Physical Distance Travelled: A mm - Check the software position displayed on SyringeGUI and record it.
Displayed Position: X mm - Re-measure the physical distance between the table/stage and the frame body.
Remaining Distance: B mm - Calculate your new calibrated Steps/mm value using this formula:
Calibrated Steps/mm = Current Steps/mm × (X / |A - B|) - Launch the
Config-Generatorutility, open your JSON config file, and update the Steps/mm field with this new calibrated value. - Save the file, reload it into SyringeGUI, and click
Sync to Grbl EEPROMto commit the change to your hardware.
In this case, current Steps/mm value was 6500. Calibrated value = 6500 x (100 / |14.20 - 115.75|) = 6400.8 Steps/mm
This project was supported by the grants from the Japan Society for the Promotion of Science (Grant# JP24H01499) and the Kato Memorial Bioscience Foundation.


















