-
LiDAR: custom serial driver for LDRobot LD06, LD19 or STL27L
- CRC package integrity check
- calibrated PWM control using curve fitting
- 2D live visualization and export (numpy or CSV)
-
Panorama: 6K 360° spherical map
- stitched from fisheye photos using Hugin Panorama photo stitcher
- constant camera exposure by reading EXIF data of automatic
- constant white balance by iterative optimization of color gains
-
3D Scene: assembly of 3D scenes from 2D planes based on angle and offsets
- sampling vertex colors from panorama
- Open3D visualization and export (PCD, PLY or e57)
- aligning multiple scenes using global registration and ICP fine-tuning
- Poisson Surface Meshing (very slow on Pi4, recommended to run on PC)
-
LDRobot LD06, LD19 or STL27L LiDAR
-
Raspberry Pi HQ Camera with ArduCam M12 Lens (M25156H18, p.7)
-
Raspberry Pi 4
-
NEMA17 42-23 stepper with A4988 driver
-
Power Supply:
- v1: 2x 18650 Batteries (7.2V) with step-down converter
- v2: 10.000 mAh USB Powerbank with step-up converter
-
3D printed:
- custom housing with tripod mount (v1 here)
- M12 to C-Mount lens adapter (thingiverse.com)
- NEMA17 planetary reduction gearbox (printables.com)
Version 2 - (37Wh Powerbank with Step-Up converter + Relay for power efficiency)
- UART Tx (yellow)
- PWM (white)
- GND (black)
- VCC 5V (red)
- LD06 UART0 Rx: GP15
- LD06 PWM0: GP18
- Power Button: GP03
- Scan Button: GP17
- A4988 direction: GP26, step: GP19
- A4988 microstepping mode: GP5, GP6, GP13
- Wakeup is hardwired to Pin 3
- install Shutdown script
sudo nano /boot/firmware/config.txt
# CPU fan at lower temp
dtoverlay=gpio-fan,gpiopin=4,temp=45000
# Power LED Heartbeat:
dtparam=pwr_led_trigger=timer
create new service for autostart
sudo nano /etc/systemd/system/pidar.service
content:
[Unit]
Description=GPIO interrupt for PiDAR Scan Button
After=network.target
[Service]
Type=simple
ExecStart=/usr/bin/python3 /home/pi/Documents/PiDAR/gpio_interrupt.py
Restart=always
RestartSec=2
[Install]
WantedBy=multi-user.target
reload daemon, enable and start service:
sudo systemctl daemon-reload
sudo systemctl enable pidar.service
sudo systemctl start pidar.service
check service if necessary:
sudo systemctl status pidar.service
baudrate 230400, data bits 8, no parity, 1 stopbit
sampling frequency 4500 Hz, scan frequency 5-13 Hz, distance 2cm - 12 meter, ambient light 30 kLux
total package size: 48 Byte, big endian.
- starting character:Length 1 Byte, fixed value 0x54, means the beginning of data packet;
- Data Length: Length 1 Byte, the first three digits reserved, the last five digits represent the number of measured points in a packet, currently fixed value 12;
- speed:Length 2 Byte, in degrees per second;
- Start angle: Length: 2 Byte; unit: 0.01 degree;
- Data: Length 36 Byte; containing 12 data points with 3 Byte each: 2 Byte distance (unit: 1 mm), 1 Byte luminance. For white objects within 6m, the typical luminance is around 200.
- End Angle: Length: 2 Byte; unit: 0.01 degree;
- Timestamp: Length 2 Bytes in ms, recount if reaching to MAX 30000;
- CRC check: Length 1 Byte
The Angle value of each data point is obtained by linear interpolation of the starting angle and the ending angle.
The calculation method of the angle is as following:
step = (end_angle – start_angle)/(len – 1)
angle = start_angle + step*i
len is the length of the packet, and the i value range is [0, len].
temporary solution:
sudo chmod a+rw /dev/ttyS0
sudo visudo
pi ALL=(ALL:ALL) NOPASSWD: /usr/bin/chmod a+rw /dev/ttyS0
then execute the temporary solution from python:
import subprocess
command = "sudo chmod a+rw /dev/ttyS0"
process = subprocess.Popen(command.split(), stdout=subprocess.PIPE)
output, error = process.communicate()
(TODO: check and remove old!)
- forget about
visudoand the subprocess call above. - Open a terminal and run the following command:
sudo nano /etc/udev/rules.d/50-ttyS0.rules - Write the following line in the file and save it:
KERNEL=="ttyS0",GROUP="dialout",MODE="0660" - Run the following command to check if your user is a member of the dialout group:
groups - If you see
dialoutin the output, you are already a member of the group. If not, run the following command to add your user to the group:sudo usermod -a -G dialout pi - Run the following command to reload the udev rules:
sudo udevadm control --reload-rules - Unplug and replug the serial device, or reboot the system, to apply the changes.
enable GPIO_18 (PWM0) and GPIO_19 (PWM1)
echo "dtoverlay=pwm-2chan" >> /boot/config.txt
check if "pwm_bcm2835" now exists:
lsmod | grep pwm
Install RPi Hardware PWM library:
pip install rpi-hardware-pwm
install Hugin with enblend plugin
sudo apt-get install hugin-tools enblend
LD06:
- sampling frequency: 4500 Hz
- baudrate 230400
- Sales page
- mechanical Datasheet
- Protocol Description
STL27L:
disable hardware acceleration for VS Code (source)
Preferences: Configure Runtime Arguments
Set "disable-hardware-acceleration": true
there is no wheel for arm64. build requires libxerces:
sudo apt install libxerces-c-dev
pip install pye57
inspirations
- LIDAR_LD06_python_loder and Lidar_LD06_for_Arduino by Inoue Minoru ("henjin0")
- ShaunPrice's StereoPi-supporting fork of BrianBock's 360-camera script
- StereoPi Article on Medium
another Lidar implementation in Python
ICP implementations:
- Aeva Doppler-ICP
- Photogrammetry & Robotics Bonn KISS-ICP and Lidar-Visualizer
3D Demo Data for global registration, ICP, meshing etc.:


