2D LiDAR Raycasting & Occupancy Grid SLAM
Simulate real-time 360° laser rangefinding, Gaussian sensor noise, Bresenham ray-marching, and recursive Bayesian log-odds occupancy probability mapping. Export production ROS 2 Nav2 map packages.
📐 Mathematical Theory & Log-Odds Bayesian Mapping
1. The Binary Bayes Filter & Log-Odds
Each cell $m_i$ in an occupancy grid represents a static binary random variable: either occupied ($m_i = 1$) or free ($m_i = 0$). Calculating probability directly requires floating point multiplications that suffer from numerical underflow. We map probability $p(m_i)$ to log-odds representation $l(m_i)$:
Under Markov assumptions, recursive Bayesian updates turn into simple scalar additions without Bayes theorem divisions:
2. Bresenham Ray-Marching & Inverse Sensor Model
For every LiDAR laser pulse fired at bearing angle $\theta$ with measured distance $r$:
- Free Space Cells (Miss): Using Bresenham's integer line algorithm, all cells traversed between the sensor origin $(x_{bot}, y_{bot})$ and the beam endpoint $(x_{hit}, y_{hit})$ are updated with negative log-odds: $l_{free} = \ln(p_{free} / (1 - p_{free})) < 0$.
- Obstacle Surface (Hit): The terminal cell $(x_{hit}, y_{hit})$ receives a positive log-odds increment: $l_{occ} = \ln(p_{occ} / (1 - p_{occ})) > 0$.
- Clamping Limits: Log-odds are clamped between $[L_{min}, L_{max}] = [-5.0, +5.0]$ to prevent confidence saturation.
3. Exporting to ROS 2 Nav2 Map Server
ROS 2 standard nav2_map_server expects an image (PNG or PGM) and an accompanying metadata YAML file:
image: map.png
resolution: 0.05 # 5cm per pixel
origin: [-10.0, -10.0, 0.0]
negate: 0
occupied_thresh: 0.65
free_thresh: 0.196
White pixels represent free traversable space, black represents obstacles/walls, and gray represents unmapped territory.