# simulator_slam **Repository Path**: theyn/simulator_slam ## Basic Information - **Project Name**: simulator_slam - **Description**: 激光定位模拟器 - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: main - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-06-10 - **Last Updated**: 2026-06-27 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 2D SLAM 地图查看与激光点云配准工具 基于 PyQt5 的桌面应用程序,用于可视化 2D 栅格地图、加载激光点云数据,并通过暴力搜索算法实现点云与地图的配准。 ## 功能特性 - **地图加载与可视化**:支持加载 PNG 格式的栅格地图及其 ROS map_server 兼容的 YAML 元信息文件 - **地图自动摆正**:根据 YAML 中 origin 的偏转角自动旋转地图,使其与真实世界方向对齐 - **激光点云加载与显示**:加载 TXT 格式的 2D 激光点云数据,在场景中以散点形式可视化 - **点云-地图配准**:基于距离场的暴力搜索算法,将激光点云与栅格地图进行配准,输出最优位姿 (x, y, theta) - **坐标显示**:实时显示鼠标位置的像素坐标、原始世界坐标和修正后世界坐标 - **网格与原点标记**:可配置的网格叠加显示,在地图原点处显示红色标记 - **变换参数保存/加载**:支持保存和加载地图的旋转角度及原点偏移量 ## 项目结构 ``` simulator_slam/ ├── app/ │ ├── map_viewer.py # 主窗口应用(PyQt5 GUI + 业务逻辑) │ └── scan_matcher.py # 激光配准算法核心模块 ├── appDoc/ │ └── config/ │ ├── config.txt # 启动配置 │ └── filepaths.txt # 文件路径配置 ├── docs/ │ ├── 坐标系说明.md # 坐标系统文档 │ ├── 提示词.md # 开发需求文档 │ └── 配准方案.md # 激光配准方案文档 ├── maps/ │ ├── 0601-1.png # 示例栅格地图 │ ├── 0601-1.yaml # 地图元信息 │ └── 0601-1.txt # 保存的变换参数 ├── points/ │ └── radarFrame1.txt # 示例激光点云数据 └── widget/ ├── map_viewer.ui # Qt Designer UI 文件 ├── Ui_map_viewer.py # 自动生成的 UI 代码 └── QSS/ └── style.qss # Qt 样式表 ``` ## 环境要求 - Python 3.6+ - PyQt5 - NumPy - Pillow (PIL) ### 安装依赖 ```bash pip install PyQt5 numpy Pillow ``` ## 使用说明 ### 运行 ```bash cd simulator_slam python app/map_viewer.py ``` 启动后程序会自动加载配置文件和地图。 ### 基本操作 | 操作 | 说明 | |------|------| | 加载地图 | 点击工具栏"加载地图"按钮,选择 PNG 文件 | | 自动摆正 | 根据 YAML 元信息自动旋转地图 | | 手动旋转 | 在底部控制栏输入旋转角度(度) | | 加载点云 | 点击"加载点云"按钮,选择 TXT 文件 | | 执行配准 | 输入先验位姿 (X, Y, Theta),点击"匹配" | | 滚轮缩放 | 鼠标滚轮缩放视图 | | 右键拖动 | 右键拖拽平移视图 | ### 遮罩层操作 遮罩层用于遮蔽 SLAM 原始地图中的假障碍物(如玻璃、动态物体残留),防止其干扰点云配准。 - **进入/退出编辑**:点击侧边栏"遮罩层→进入编辑",退出时自动保存遮罩并重建距离场 - **绘制工具**:画笔(连续拖拽绘制)、矩形(点击拖拽拉框,右击删除)、橡皮擦 - **画笔粗细**:侧边栏可调节画笔/橡皮擦半径(像素) - **显示遮罩障碍物**:勾选时显示红色蒙层 + 被遮罩障碍物;取消勾选时隐藏蒙层,被遮罩区域变白(障碍物不可见) - **保存与加载**:退出编辑自动保存为 `*_mask.png`,重启地图时自动加载;遮罩层随地图旋转自动适配 ### 手动定位 手动在地图上指定 AGV 的初始位置和朝向,用于实车定位初始化。 - 点击顶部悬浮图标栏的"手动定位"按钮(十字光标) - **第一步**:在地图目标位置单击左键,显示蓝色圆点 - **第二步**:移动鼠标时出现蓝色虚线指示朝向,再次单击左键确认 - 确认后自动填入激光定位卡片(X/Y/角度),并触发 `0x40,0x38` 同步定位命令发送给实车 - 右键单击可取消手动定位 ## 配置文件 ### 启动配置 (`appDoc/config/config.txt`) ```text showGrid:true # 显示网格 showOrigin:true # 显示原点 scale:1.0 # 默认缩放 ``` ### 地图元信息 (`maps/*.yaml`) 兼容 ROS map_server 格式: ```yaml image: 0601-1.png resolution: 0.05 # 每像素 0.05 米(5cm/px) origin: [-38.8346, -56.3186, 0.0] # [origin_x(m), origin_y(m), yaw(rad)] negate: 0 occupied_thresh: 0.65 free_thresh: 0.196 ``` ### 激光点云格式 (`points/*.txt`) 每行一个点,包含 x y 坐标(单位:米),支持 `#` 注释: ```text # 模拟激光雷达一帧点云数据 (单位: 米) -2.00 3.00 -1.50 3.00 ... ``` ## 配准算法 采用基于距离场的暴力搜索策略: 1. **占据栅格构建**:将灰度图阈值化,生成二值占据栅格 2. **距离场构建**:使用双向动态规划(4遍扫描),计算每个像素到最近占据点的欧氏距离 3. **评分函数**:激光点投影到地图坐标后查距离场,使用高斯核评分 4. **搜索策略**:先粗搜(大步长 0.3m/3°)→ 精搜(小步长 0.05m/0.5°) 详见 `docs/配准方案.md`。 ## 文档 - `docs/坐标系说明.md` — 详细坐标系统说明 - `docs/配准方案.md` — 配准算法详细方案