开发环境:Ubuntu 18.04 LTS + ROS Melodic + ViSP 3.3.1
文章内容主要参考ViSP官方教学文档:https://visp-doc.inria.fr/doxygen/visp-daily/tutorial_mainpage.html

  本文主要介绍了如何使用ViSP实现目标检测和定位,实现过程分为两步,第一步在参考图像中检测并提取目标物体表面的关键点,并保存其对应的三维坐标,第二步在当前图像中寻找匹配对的关键点,并根据目标物体的CAD模型信息和关键点坐标估计目标物体的位置姿态。本文主要参考了detection/object中的 tutorial-detection-object-mbt.cpp例程。首先要获取这个例程文件并编译它

svn export https://github.com/lagadic/visp.git/trunk/tutorial/detection/object
cd object/
mkdir build
cd build
cmake .. -DCMAKE_BUILD_TYPE=Release -DVISP_DIR=$VISP_WS/visp-build
make

  执行例程,查看效果

./tutorial-detection-object-mbt

  根据示意图中的顺序,依次点击参考图像中对应的位置,选择出目标物体

  点击左键提取表面关键点

  点击左键实现目标检测和位姿估计

  下面介绍一下代码实现过程

#include <visp3/core/vpConfig.h>
#include <visp3/core/vpIoTools.h>
#include <visp3/gui/vpDisplayGDI.h>
#include <visp3/gui/vpDisplayOpenCV.h>
#include <visp3/gui/vpDisplayX.h>
#include <visp3/io/vpVideoReader.h>
#include <visp3/mbt/vpMbGenericTracker.h>
#include <visp3/vision/vpKeyPoint.h>
int main(int argc, char **argv)
{#if (VISP_HAVE_OPENCV_VERSION >= 0x020400)try {std::string videoname = "teabox.mp4";for (int i = 0; i < argc; i++) {if (std::string(argv[i]) == "--name")videoname = std::string(argv[i + 1]);else if (std::string(argv[i]) == "--help" || std::string(argv[i]) == "-h") {std::cout << "\nUsage: " << argv[0] << " [--name <video name>] [--help] [-h]\n" << std::endl;return 0;}}std::string parentname = vpIoTools::getParent(videoname);std::string objectname = vpIoTools::getNameWE(videoname);if (!parentname.empty())objectname = parentname + "/" + objectname;std::cout << "Video name: " << videoname << std::endl;std::cout << "Tracker requested config files: " << objectname << ".[init,"<< "xml,"<< "cao or wrl]" << std::endl;std::cout << "Tracker optional config files: " << objectname << ".[ppm]" << std::endl;vpImage<unsigned char> I;vpCameraParameters cam;vpHomogeneousMatrix cMo;vpVideoReader g;g.setFileName(videoname);g.open(I);
#if defined(VISP_HAVE_X11)vpDisplayX display;
#elif defined(VISP_HAVE_GDI)vpDisplayGDI display;
#elif defined(VISP_HAVE_OPENCV)vpDisplayOpenCV display;
#elsestd::cout << "No image viewer is available..." << std::endl;return 0;
#endifdisplay.init(I, 100, 100, "Model-based edge tracker");vpMbGenericTracker tracker(vpMbGenericTracker::EDGE_TRACKER);//创建一个跟踪器bool usexml = false;if (vpIoTools::checkFilename(objectname + ".xml")) {tracker.loadConfigFile(objectname + ".xml");//通过xml文件加载配置参数tracker.getCameraParameters(cam);//获取相机参数usexml = true;}if (!usexml) {vpMe me;//手动配置跟踪器参数me.setMaskSize(5);me.setMaskNumber(180);me.setRange(8);me.setThreshold(10000);me.setMu1(0.5);me.setMu2(0.5);me.setSampleStep(4);me.setNbTotalSample(250);tracker.setMovingEdge(me);cam.initPersProjWithoutDistortion(839, 839, 325, 243);tracker.setCameraParameters(cam);tracker.setAngleAppear(vpMath::rad(70));tracker.setAngleDisappear(vpMath::rad(80));tracker.setNearClippingDistance(0.1);tracker.setFarClippingDistance(100.0);tracker.setClipping(tracker.getClipping() | vpMbtPolygon::FOV_CLIPPING);}tracker.setOgreVisibilityTest(false);//加载目标CAD模型if (vpIoTools::checkFilename(objectname + ".cao"))tracker.loadModel(objectname + ".cao");else if (vpIoTools::checkFilename(objectname + ".wrl"))tracker.loadModel(objectname + ".wrl");tracker.setDisplayFeatures(true);tracker.initClick(I, objectname + ".init", true);tracker.track(I);
#if (defined(VISP_HAVE_OPENCV_NONFREE) || defined(VISP_HAVE_OPENCV_XFEATURES2D)) || \(VISP_HAVE_OPENCV_VERSION >= 0x030411 && CV_MAJOR_VERSION < 4) || (VISP_HAVE_OPENCV_VERSION >= 0x040400)std::string detectorName = "SIFT";//设置SIFT关键点检测器std::string extractorName = "SIFT";//设置SIFT特征提取器std::string matcherName = "BruteForce";//设置BruteForce匹配算法std::string configurationFile = "detection-config-SIFT.xml";//设置检测器参数文件
#elsestd::string detectorName = "FAST";std::string extractorName = "ORB";std::string matcherName = "BruteForce-Hamming";std::string configurationFile = "detection-config.xml";
#endifvpKeyPoint keypoint_learning;if (usexml) {keypoint_learning.loadConfigFile(configurationFile);//加载检测器参数文件} else {//手动配置检测器参数keypoint_learning.setDetector(detectorName);keypoint_learning.setExtractor(extractorName);keypoint_learning.setMatcher(matcherName);}std::vector<cv::KeyPoint> trainKeyPoints;double elapsedTime;keypoint_learning.detect(I, trainKeyPoints, elapsedTime);//检测关键点std::vector<vpPolygon> polygons;std::vector<std::vector<vpPoint> > roisPt;std::pair<std::vector<vpPolygon>, std::vector<std::vector<vpPoint> > > pair = tracker.getPolygonFaces(false);//获取物体表面polygons = pair.first;//保存物体各个表面的多边形信息roisPt = pair.second;//保存物体各个表面的角点信息std::vector<cv::Point3f> points3f;tracker.getPose(cMo);vpKeyPoint::compute3DForPointsInPolygons(cMo, cam, trainKeyPoints, polygons, roisPt, points3f);//计算表面点的三维坐标keypoint_learning.buildReference(I, trainKeyPoints, points3f);//构建参考关键点keypoint_learning.saveLearningData("teabox_learning_data.bin", true);//保存关键点的描述和坐标信息vpDisplay::display(I);for (std::vector<cv::KeyPoint>::const_iterator it = trainKeyPoints.begin(); it != trainKeyPoints.end(); ++it) {vpDisplay::displayCross(I, (int)it->pt.y, (int)it->pt.x, 4, vpColor::red);}vpDisplay::displayText(I, 10, 10, "Learning step: keypoints are detected on visible teabox faces", vpColor::red);vpDisplay::displayText(I, 30, 10, "Click to continue with detection...", vpColor::red);vpDisplay::flush(I);vpDisplay::getClick(I, true);vpKeyPoint keypoint_detection;if (usexml) {keypoint_detection.loadConfigFile(configurationFile);} else {keypoint_detection.setDetector(detectorName);keypoint_detection.setExtractor(extractorName);keypoint_detection.setMatcher(matcherName);keypoint_detection.setFilterMatchingType(vpKeyPoint::ratioDistanceThreshold);keypoint_detection.setMatchingRatioThreshold(0.8);keypoint_detection.setUseRansacVVS(true);keypoint_detection.setUseRansacConsensusPercentage(true);keypoint_detection.setRansacConsensusPercentage(20.0);keypoint_detection.setRansacIteration(200);keypoint_detection.setRansacThreshold(0.005);}keypoint_detection.loadLearningData("teabox_learning_data.bin", true);//加载参考关键点的描述和坐标信息double error;bool click_done = false;while (!g.end()) {g.acquire(I);vpDisplay::display(I);vpDisplay::displayText(I, 10, 10, "Detection and localization in process...", vpColor::red);//从当前的视频图像中匹配关键点并估计位姿if (keypoint_detection.matchPoint(I, cam, cMo, error, elapsedTime)) {tracker.setPose(I, cMo);tracker.display(I, cMo, cam, vpColor::red, 2);vpDisplay::displayFrame(I, cMo, cam, 0.025, vpColor::none, 3);}vpDisplay::displayText(I, 30, 10, "A click to exit.", vpColor::red);vpDisplay::flush(I);if (vpDisplay::getClick(I, false)) {click_done = true;break;}}if (!click_done)vpDisplay::getClick(I);} catch (const vpException &e) {std::cout << "Catch an exception: " << e << std::endl;}
#else(void)argc;(void)argv;std::cout << "Install OpenCV and rebuild ViSP to use this example." << std::endl;
#endifreturn 0;
}

如果大家对于深度学习与计算机视觉领域感兴趣,希望获得更多的知识分享与最新的论文解读,欢迎关注我的个人公众号“深视”。

ViSP学习笔记(二十二):目标检测和定位相关推荐

  1. OpenCV学习笔记(十二):边缘检测:Canny(),Sobel(),Laplace(),Scharr滤波器

    OpenCV学习笔记(十二):边缘检测:Canny(),Sobel(),Laplace(),Scharr滤波器 1)滤波:边缘检测的算法主要是基于图像强度的一阶和二阶导数,但导数通常对噪声很敏感,因此 ...

  2. Windows保护模式学习笔记(十二)—— 控制寄存器

    Windows保护模式学习笔记(十二)-- 控制寄存器 控制寄存器 Cr0寄存器 Cr2寄存器 Cr4寄存器 控制寄存器 描述: 控制寄存器有五个,分别是:Cr0 Cr1 Cr2 Cr3 Cr4 Cr ...

  3. Windows Workflow HOL学习笔记(十二):创建状态基工作流

    W indows Workflow HOL学习笔记(十二):创建状态基工作流 本文内容来自Microsoft Hands-on Labs for Windows Workflow Foundation ...

  4. tensorflow学习笔记(三十二):conv2d_transpose (解卷积)

    tensorflow学习笔记(三十二):conv2d_transpose ("解卷积") deconv解卷积,实际是叫做conv_transpose, conv_transpose ...

  5. 汇编入门学习笔记 (十二)—— int指令、port

    疯狂的暑假学习之  汇编入门学习笔记 (十二)--  int指令.port 參考: <汇编语言> 王爽 第13.14章 一.int指令 1. int指令引发的中断 int n指令,相当于引 ...

  6. QT学习笔记(十二):透明窗体设置

    QT学习笔记(十二):透明窗体设置 创建 My_Widget 类 基类为QWidget , My_Widget.cpp 源文件中添加代码 #include "widget.h" # ...

  7. MATLAB学习笔记(十二)

    MATLAB学习笔记(十二) 一.数据插值 1.1 数据插值的计算机制 1.2 数据插值的matlab函数 二.曲线拟合 2.1 曲线拟合原理 2.2 曲线拟合的实现方法 三.数据插值与曲线拟合比较 ...

  8. 模电学习笔记(十二)——跨阻放大器

    模电学习笔记(十二) 跨阻放大器 跨组运算放大器是将电流信号转换成为电压信号,电流到电压增益基于反馈电阻. 设计目标: 输入 输出 带宽 电源 0A 100uA 0V 7V 20kHz 15V -15 ...

  9. Spring Cloud学习笔记【十二】Hystrix的使用和了解

    Spring Cloud学习笔记[十二]Hystrix的使用和了解 Hystrix [hɪst'rɪks],中文含义是豪猪,因其背上长满棘刺,从而拥有了自我保护的能力.本文所说的Hystrix是Net ...

  10. Cty的Linux学习笔记(十二)

    Linux学习笔记--第十二篇 命令(command): RPM工具: rpm -ivh ......:安装RPM包 -i:表示安装 -v:表示可视化 -h:表示显示安装进度 在安装RPM包是常用的附 ...

最新文章

  1. ASP.NET MVC 3中ViewBag, ViewData和 TempData
  2. php执行跟踪_PHP使用debug_backtrace方法跟踪调试代码调用详解
  3. apache karaf_未来是Apache Karaf上的微服务架构
  4. spring集成多个rabbitMQ
  5. 基因组中的趣事(二)- 最长的基因2.7 million,最短的基因只有8 nt却能编码
  6. Python编程基础08:循环结构
  7. SpringBoot-WebMvcAutoConfiguration/WebMvcConfigurer/WebMvcRegistrationsAdapter
  8. 想更换手机卡,但它绑定了支付宝,微信,银行卡等,该怎么办啊?
  9. 一道关于CSS选择器优先级的题
  10. 网络协议TCP/IP、IPX/SPX、NETBEUI简介
  11. Java Socket聊天室
  12. 【2021-07最新可用】解决谷歌地球、Google地球、Google Earth Pro无法正常启动:启动一直转圈圈、无法链接到登录服务器 、显示黑屏地图无法加载 、软件无法启动双击图标没反应等
  13. 视频传输协议总结、码率
  14. 编程语言Python为什么这么火?
  15. 数据分析师——个人求职之路经历分享(2020届)
  16. 七大室内定位技术PK(转自3Snews)
  17. Error syncing pod, skipping: failed to “StartContainer“ for “POD“ with ErrImagePull: “image pull fai
  18. [转]自信过头是狂妄,谦虚过度是虚伪
  19. FFmpeg下载及命令行使用
  20. swoft实现自动重启服务

热门文章

  1. Pytorch---- CIFAR10实战(训练集+测试集+验证集)完整版,逐行注释-----学习笔记
  2. tensorflow cifar10 分类预测实战
  3. 舍与得 -- 诠释舍得
  4. 工业相机payloadSize的介绍
  5. 2020年安全生产监管人员考试题库及安全生产监管人员新版试题
  6. python 基准测试(cProfile \ kcachegrind \ line_profiler \ memory_profiler)
  7. 好看响应式Emlog博客主题模板
  8. 化繁为简,爆款语聊产品背后的业务逻辑
  9. uniapp scroll-view防抖
  10. 解决git取消ss代理后仍然访问代理端口的问题