ARTICLE DETAIL

资讯详情

深耕编程入门与网站建设的一线实战洞察。

ROS2标定板aruco apriltag

ROS2标定板aruco apriltag ROS2标定板aruco apriltaghttps://blog.csdn.net/wangmj_hdu/article/details/111233878AprilTag标记跟踪 · OpenMV中文入门教程https://blog.csdn.net/sinat_16643223/article/details/137357584https://docs.opencv.org/3.4/d5/d1f/calib3d_solvePnP.html安装docker pull ubuntu:22.04docker run -it --user root --gpus all \ -v /etc/localtime:/etc/localtime:ro \ -v /tmp/.X11-unix:/tmp/.X11-unix \ -e DISPLAYunix$DISPLAY \ -e GDK_SCALE \ -e GDK_DPI_SCALE \ --network host \ --volume /home/zoujiu/data:/home/data \ --volume /home/zoujiu/Downloads:/home/Downloads \ --volume /home/zoujiu/Desktop/projects:/home/Desktop \ --shm-size 30G --name ros2humble ubuntu:22.04 /bin/bashhttps://docs.ros.org/en/humble/Installation/Alternatives/Ubuntu-Development-Setup.htmlhttps://docs.ros.org/en/humble/Installation/Alternatives/Ubuntu-Development-Setup.html1 报错No rospy 使用rclpyNo cv_bridge https://index.ros.org/p/cv_bridge/git clone https://github.com/ros-perception/vision_opencv.git -b humble cd .. colcon build --symlink-install *colcon build --symlink-install --packages-select image_pipeline**# *https://index.ros.org/p/cv_bridge/# ros2 run image_view image_view --ros-args --remap image:/camera/rgb/image_raw --log-level debug*# *https://github.com/ros-perception/image_pipeline.git*# *https://index.ros.org/p/image_view/# colcon build --symlink-installcolcon build --symlink-install --packages-select image_pipeline配置**apt-get** install python3-cv-bridge python3-rospy **pip** install sensor_msgs --extra-index-url https://rospypi.github.io/simple/ *# https://www.cnblogs.com/yunhgu/p/15785460.html*2 标定要求的鱼眼相机标定对采集图片的要求核心目标只有一个让标定算法能稳定、准确地估计内参和畸变最终重投影误差 ≤ 0.5 像素。下面我给你按「必满足」和「加分项」分清楚方便你照着执行。✅ 必须满足的硬性要求少一个都可能标崩棋盘格本身必须合格格子数量内角点黑白交界点行列数要写对比如(8, 6)你代码里的CHECKERBOARD必须和实际完全一致。棋盘格要平整不能有弯曲、折痕、鼓包尤其是鱼眼镜头边缘轻微变形都会导致角点检测不准。格子尺寸必须真实准确比如每个格子 25mm标定代码里的SQUARE_SIZE要和实际完全一致否则外参全错内参也会受影响。角点必须能稳定检测到每张图片里棋盘格角点必须全部被检测到不能缺角点也不能只检测到部分。角点清晰锐利没有模糊、反光、阴影对比度要高。棋盘格不能被手、设备、人等遮挡边缘的角点也必须完整可见。覆盖足够多的镜头区域最关键鱼眼标定必须让棋盘格出现在画面中心画面四角和边缘不同高度、不同倾斜角度覆盖原则至少 15~20 张图片覆盖整个鱼眼视野尤其是边缘区域边缘区域必须有足够多的棋盘格否则边缘畸变无法被正确估计不要只拍中心位置的几张这样标出来的畸变参数基本是错的角度和姿态要多样化棋盘格要多拍不同倾斜角度上仰、下俯、左倾、右倾多拍不同距离近景格子占画面 1/3 以上、中景、远景格子在画面中占比适中多拍不同旋转角度棋盘格不要总是水平竖直适当旋转 30°/45° 拍几组避免这些致命场景强烈反光棋盘格反光、玻璃反射、强光直射运动模糊手持抖动导致的拖影严重过曝 / 欠曝棋盘格黑白边界不清晰棋盘格离镜头过近 / 过远角点太小或超出画面画面裁剪 / 畸变拍摄过程中不要对图片做任何裁剪、拉伸、畸变矫正标定用原始鱼眼原图 能让标定效果翻倍的加分项图片数量与质量建议采集 30~50 张比 10 张更稳尤其是鱼眼边缘畸变需要更多数据约束所有图片分辨率必须一致不能混不同分辨率的照片同一场景、同一棋盘格多拍几张不同角度避免单张异常数据影响整体结果棋盘格摆放技巧让棋盘格出现在画面的四个角落各几次边缘畸变估计会更准至少有 3~5 张图片里棋盘格同时覆盖画面中心和边缘倾斜拍摄时让棋盘格的一部分靠近镜头另一部分远离这样 Z 轴信息更丰富环境条件光线均匀柔和避免局部强光和大面积阴影相机固定避免拍摄过程中相机晃动如果是手持尽量稳定棋盘格背景尽量简单避免复杂纹理干扰角点检测 简单自检清单按这个检查你的数据集棋盘格内角点数量和代码里的CHECKERBOARD完全一致所有图片角点都能被findChessboardCorners完整检测棋盘格出现在画面中心、边缘、四角有不同倾斜、旋转、距离的图片没有反光、模糊、遮挡、过曝 / 欠曝图片数量 ≥ 15 张推荐 30~50 张所有图片都是鱼眼原始图没有裁剪 / 畸变矫正如果你愿意我可以帮你写一个批量角点检测脚本一键检查你的所有标定图片是否合格哪些图片角点检测失败帮你快速筛掉不合格的照片只保留能让标定一次成功的数据集。ROS2发布视频帧*#!/usr/bin/env python* *#coding:utf-8* import **os** *# os.environ[PYTHONPATH]/opt/ros/humble/lib/python3.10/site-packages;/opt/ros/humble/local/lib/python3.10/dist-packages* import **rclpy** import **sys** **sys**.path.**append**(.) import **cv2** import **time** from **rclpy**.**node** import **Node** import **numpy** as **np** from **sensor_msgs**.**msg** import **Image** from cv_bridge import CvBridge, CvBridgeError def **pubVideo**(): **rclpy**.**init**() nod **rclpy**.**create_node**(frame) pub nod.**create_publisher**(**Image**, /camera/rgb/image_raw, qos_profile1) *# rate nod.create_rate(5)* HZ 5 path /home/Desktop/ros2/002.mp4 cap **cv2**.**VideoCapture**(path) scaling_factor 0.5 bridge CvBridge() if not cap.**isOpened**(): **sys**.stdout.**write**(vedio is not available !) return -1 count 0 ret True while ret: ret, frame cap.**read**() if ret: count count 1 else: **rclpy**.loginfo(Capturing image failed.) if count 2: count 0 frame **cv2**.**resize**(frame,None,fxscaling_factor,fyscaling_factor,interpolation**cv2**.INTER_AREA) msg bridge.cv2_to_imgmsg(frame, encodingbgr8) pub.**publish**(msg) **print**(** publishing webcam_frame ***) *# rate.sleep()* **time**.**sleep**(1 / HZ) kk 0 **rclpy**.**shutdown**() if __name__ __main__: *# https://index.ros.org/p/cv_bridge/* *# ros2 run image_view image_view --ros-args --remap image:/camera/rgb/image_raw --log-level debug* try: **pubVideo**() except **rclpy**.ROSInterruptException: pass3 aruco自定义字典的作用含义自定义 ArUco 字典 作用、含义、使用方法超级通俗版我用最简单、最实用的方式给你讲清楚你马上就能用在你的多相机标定代码里。一、自定义 ArUco 字典 是什么含义ArUco 字典 一套二维码的编码规则它决定了二维码长什么样6×6 / 7×7一共有多少个不同的二维码100个 / 1000个哪些ID是合法的二维码之间差异多大防止误识别自定义字典 你自己造一套专属二维码别人用通用字典扫不出来只有你能扫。二、自定义字典 作用为什么要用1. 防止别人的二维码干扰你的检测工厂/车内环境如果有别人的二维码通用字典会误识别。自定义字典 只认你自己打印的码。2. 二维码数量你自己定OpenCV 自带字典最多 1000 个你可以做10000 个。3. 二维码尺寸你自己定6×6、7×7、8×8 随便选。4. 适合多相机、多传感器标定系统你现在做的车载多相机外参标定必须用自定义字典避免干扰。三、自定义字典 怎么用3步万能流程第1步创建字典生成XMLimport **cv2** *6x6 网格一共 1000 个二维码* dict **cv2**.**aruco**.**extendDictionary**(nMarkers1000, markerSize6) dict.maxCorrectionBits 6 *保存成 XML 文件和你 1000_6.xml 一样* fs **cv2**.**FileStorage**(my_dict.xml, **cv2**.FILE_STORAGE_WRITE) dict.**writeDictionary**(fs) fs.**release**()第2步生成二维码图片打印出来贴车上img **cv2**.**aruco**.**generateImageMarker**(dict, id0, sidePixels400) **cv2**.**imwrite**(marker0.png, img)第3步在你的相机标定代码里 加载自定义字典fs **cv2**.**FileStorage**(my_dict.xml, **cv2**.FILE_STORAGE_READ) bytesList fs.**getNode**(bytesList).**mat**() ms **int**(fs.**getNode**(markerSize).**real**()) mc **int**(fs.**getNode**(maxCorrectionBits).**real**()) fs.**release**() *加载你的 XML* *重建字典* aruco_dict **cv2**.**aruco**.Dictionary_create(1,1) aruco_dict.bytesList bytesList aruco_dict.markerSize ms aruco_dict.maxCorrectionBits mc *检测* detector **cv2**.**aruco**.**ArucoDetector**(aruco_dict, **cv2**.**aruco**.**DetectorParameters**()) corners, ids, _ detector.**detectMarkers**(gray)四、一句话总结最重要自定义 ArUco 字典 你自己的专属二维码家族作用防干扰、更稳定、适合车载多相机标定使用生成XML → 打印二维码 → 代码加载XML五、我可以直接帮你把 你的多相机标定代码 改成支持自定义字典从1000_6.xml加载的最终完整版4、自定义aruco字典下面我给你一套完整、可直接运行的流程生成自定义 ArUco 字典 → 保存为 XML → 在你的多相机标定代码里加载这个 XML。全程 Python OpenCV4和你现在的代码无缝对接。一、核心概念先搞懂一个 ArUco 字典由三个参数决定markerSize内部位矩阵大小如6表示 6×6 位不含边框nMarkers字典里有多少个标记ID 0 ~ nMarkers-1maxCorrectionBits最多可纠正的错误位数一般 markerSize你之前的1000_6.xml就是markerSize 6nMarkers 1000maxCorrectionBits 6二、生成自定义字典并保存为 XML直接运行import **cv2** import **numpy** as **np** *-------- 1. 自定义字典参数 --------* nMarkers 1000 *# 标记数量ID 0~999* markerSize 6 *# 6×6 位* maxCorrectionBits 6 *-------- 2. 创建自定义字典 --------* *方法extendDictionaryOpenCV 官方推荐* custom_dict **cv2**.**aruco**.**extendDictionary**( nMarkersnMarkers, markerSizemarkerSize ) custom_dict.maxCorrectionBits maxCorrectionBits *-------- 3. 保存为 XML和你 1000_6.xml 格式完全一致 --------* xml_path custom_1000_6.xml fs **cv2**.**FileStorage**(xml_path, **cv2**.FILE_STORAGE_WRITE) custom_dict.**writeDictionary**(fs) fs.**release**() **print**(f✅ 自定义字典已保存{xml_path}) **print**(f nMarkers{nMarkers}, markerSize{markerSize}) 运行后得到 custom_1000_6.xml**和你原来的 1000_6.xml 结构完全一样**。三、在你的多相机标定代码里加载自定义 XML把你代码里“ArUco 字典”那一段替换成下面这段* 加载自定义 ArUco 字典从 XML * dictFile /home/zoujiu/Desktop/.../custom_1000_6.xml *# 你的路径* cv_file **cv2**.**FileStorage**(dictFile, **cv2**.FILE_STORAGE_READ) bytesList cv_file.**getNode**(bytesList).**mat**() markerSize **int**(cv_file.**getNode**(markerSize).**real**()) maxCorrectionBits **int**(cv_file.**getNode**(maxCorrectionBits).**real**()) cv_file.**release**() *重建字典* aruco_dict **cv2**.**aruco**.Dictionary_create(markerSize, nMarkers) aruco_dict.bytesList bytesList aruco_dict.markerSize markerSize aruco_dict.maxCorrectionBits maxCorrectionBits detector **cv2**.**aruco**.**ArucoDetector**(aruco_dict, **cv2**.**aruco**.**DetectorParameters**()) 这样就**完全替代预定义字典**用你自己的 1000_6.xml 了。四、只生成指定 ID 的子集常用如果你不想 1000 个只要比如 0~9*从大字典里截取 ID 0~9* sub_dict **cv2**.**aruco**.custom_dictionary(10, 6) for i in **range**(10): sub_dict.bytesList[i] custom_dict.bytesList[i]五、生成标记图片用来打印size_px 300 *# 图片像素* for **id** in **range**(5): *# 生成前 5 个* img **cv2**.**aruco**.**generateImageMarker**(custom_dict, **id**, size_px) **cv2**.**imwrite**(fmarker_{**id**}.png, img)六、总结你要的一句话自定义字典用cv2.aruco.extendDictionary()生成保存 XMLdict.writeDictionary(fs)加载 XMLFileStorage读bytesList/markerSize替换你代码直接把字典部分换成“从 XML 加载”要不要我把完整的“生成XML多相机标定”合并成一个最终版脚本
返回列表