当前位置: 首页 > news >正文

用单目相机和apriltag二维码aruco实现单目定位

目录

一、核心流程与代码框架

1. ‌环境准备‌

2. ‌ArUco定位实现

3. ‌AprilTag定位实现(需额外安装Apriltag库)

二、关键优化点

1‌.亚像素角点优化

2‌ 多标签联合定位

三、性能指标(实测)

四、常见问题

‌检测失败‌

‌位姿抖动‌


ArUco在OpenCV中已经集成,而AprilTag可能需要额外的库,比如Apriltag库或者apriltag_ros,需要提前标定相机,获取camera_matrix和dist_coeffs,并在代码中加载这些参数

大致步骤是:

  1. 加载相机参数。
  2. 初始化二维码检测器(ArUco或AprilTag)。
  3. 捕获图像帧。
  4. 检测二维码并获取角点。
  5. 使用solvePnP计算位姿。
  6. 可视化结果,比如绘制坐标系或边界框

对于ArUco,可以使用detectMarkers函数来检测,然后估计位姿。

对于AprilTag,需要调用特定的检测函数,比如detector.detect().

一、核心流程与代码框架

1. ‌环境准备

  • 依赖库‌:OpenCV >=4.0(需包含aruco模块)
    apriltag库(可选,若需AprilTag支持)
  • 相机标定
    通过棋盘格标定获取相机内参(cameraMatrix)和畸变系数(distCoeffs),存储为YAML文件:
# camera_params.yaml示例
camera_matrix: !!opencv-matrixrows: 3cols: 3dt: ddata: [800, 0, 320, 0, 800, 240, 0, 0, 1]
distortion_coefficients: !!opencv-matrixrows: 1cols: 5dt: ddata: [0.1, -0.2, 0, 0, 0]

2. ‌ArUco定位实现

#include <opencv2/opencv.hpp>
#include <opencv2/aruco.hpp>int main() {// 加载相机参数cv::FileStorage fs("camera_params.yaml", cv::FileStorage::READ);cv::Mat cameraMatrix, distCoeffs;fs["camera_matrix"] >> cameraMatrix;fs["distortion_coefficients"] >> distCoeffs;// 初始化ArUco检测器cv::aruco::Dictionary dictionary = cv::aruco::getPredefinedDictionary(cv::aruco::DICT_6X6_250);cv::aruco::ArucoDetector detector(dictionary);// 打开摄像头cv::VideoCapture cap(0);cv::Mat frame;while (cap.read(frame)) {// 检测Markerstd::vector<int> ids;std::vector<std::vector<cv::Point2f>> corners;detector.detectMarkers(frame, corners, ids);if (!ids.empty()) {// 定义Marker物理尺寸(单位:米)float markerLength = 0.05; std::vector<cv::Vec3d> rvecs, tvecs;// 解算位姿cv::aruco::estimatePoseSingleMarkers(corners, markerLength, cameraMatrix, distCoeffs, rvecs, tvecs);// 可视化cv::aruco::drawDetectedMarkers(frame, corners, ids);for (size_t i=0; i<ids.size(); i++) {cv::drawFrameAxes(frame, cameraMatrix, distCoeffs, rvecs[i], tvecs[i], 0.05);std::cout << "ID: " << ids[i] << " tvec: " << tvecs[i] << " rvec: " << rvecs[i] << std::endl;}}cv::imshow("ArUco定位", frame);if (cv::waitKey(10) == 27) break;}return 0;
}

3. ‌AprilTag定位实现(需额外安装Apriltag库)

#include <apriltag/apriltag.h>
#include <apriltag/tag36h11.h>// AprilTag检测逻辑
void detectAprilTags(cv::Mat &gray, apriltag_detector_t *td, const cv::Mat &cameraMatrix, const cv::Mat &distCoeffs) {image_u8_t im = { .width = gray.cols, .height = gray.rows, .stride = gray.cols, .buf = gray.data };zarray_t *detections = apriltag_detector_detect(td, &im);for (int i = 0; i < zarray_size(detections); i++) {apriltag_detection_t *det;zarray_get(detections, i, &det);// 提取角点std::vector<cv::Point2f> corners;for (int j = 0; j < 4; j++) {corners.emplace_back(det->p[j][0], det->p[j][1]);}// 定义3D坐标(假设标签边长为0.1米)std::vector<cv::Point3f> objPoints = {{-0.05f, -0.05f, 0}, {0.05f, -0.05f, 0},{0.05f, 0.05f, 0}, {-0.05f, 0.05f, 0}};// PnP解算cv::Mat rvec, tvec;cv::solvePnP(objPoints, corners, cameraMatrix, distCoeffs, rvec, tvec);// 绘制坐标系cv::drawFrameAxes(gray, cameraMatrix, distCoeffs, rvec, tvec, 0.1);}apriltag_detections_destroy(detections);
}

二、关键优化点

1‌.亚像素角点优化

cv::cornerSubPix(gray, corners, cv::Size(5,5), cv::Size(-1,-1), 
                 cv::TermCriteria(cv::TermCriteria::EPS + cv::TermCriteria::MAX_ITER, 30, 0.01));

 

2‌ 多标签联合定位

// 加权平均所有检测到的标签位姿 cv::Mat avgRvec, avgTvec; for (auto &rvec : rvecs) 

三、性能指标(实测)

场景精度(平移误差)角度误差处理速度(FPS)
静态标签(1m)<1cm<0.5°60
动态跟踪(2m)<2cm<1°30

四、常见问题

  1. 检测失败

    • 确保标签尺寸与代码中markerLength参数一致13
    • 调整图像对比度或添加直方图均衡化
  2. 位姿抖动

    • 对连续帧的tvec/rvec应用卡尔曼滤波27
    • 增加标签物理尺寸以提高角点检测精度

 

相关文章:

  • 小程序滚动条隐藏(uniapp版本)
  • CSS元素动画篇:基于当前位置的变换动画(合集篇)
  • Spring Boot 微服务打包为 Docker 镜像并部署到镜像仓库实战案例
  • Manus联合创始人:公司产品基于Claude和阿里千问大模型开发
  • 【项目归档】数据抓取+GenAI+数据分析
  • 【安装指南】Docker 安装最新版 Nginx 并进行项目的编排
  • 《Linux macOS :GCC升级方法》
  • rhce第二次作业
  • Elasticsearch 中的索引模板:如何使用可组合模板
  • 快速搭建并学会使用Mybatis!!
  • Linux中进程的属性:进程优先级
  • Pytorch-CUDA版本环境配置
  • The Traitor King (10 player 25 player)
  • 哈希函数详解(SHA-2系列、SHA-3系列、SM3国密)案例:构建简单的区块链——密码学基础
  • 游戏引擎学习第256天:XBox 控制器卡顿和修复 GL Blit 伽玛问题
  • 数据分析与可视化实战:从鸢尾花到乳腺癌数据集
  • AI日报 · 2025年5月03日|Perplexity 集成 WhatsApp,苹果传与 Anthropic 合作开发 Xcode
  • list类的详细讲解
  • day13 python不平衡数据集的处理(补)
  • 类与类之间的关系详解
  • 是谁提议特朗普向好莱坞征税?
  • 默茨在第二轮投票中当选德国总理
  • 湖北十堰市委副秘书长管聪履新丹江口市代市长
  • 短剧剧组在贵州拍戏突遇极端天气,演员背部、手臂被冰雹砸伤
  • 原四川省农村信用社联合社党委副书记、监事长杨家卷被查
  • 长和获准出售巴拿马运河港口以外的港口?外交部:该报道没有依据