双目立体视觉三维重构总结

2023-10-27


前面多多少少记录一些相关知识,由于相关工作还在继续,加上网上的教程总不是十分完善。这里做一个总结,希望自己能够加深对这个过程的整体的理解与认识。

基本步骤

  1. 相机标定
  2. 图片采集
  3. 立体校正
  4. 匹配算法
  5. 三维重构
  6. 点云去噪
  7. 点云显示

相机标定

使用的Matlab标定工具箱,需要注意的点有:

  1. 每个相机单独标定,之后再标定双目相机的位姿
  2. 标定单目时需要选择畸变个数,一般如果不是鱼眼镜头,只需要标定两个径向畸变、两个切向畸变。
  3. 图像采集,和标定精度测试移步这里
  4. Matlab标定参数用于opencv移步这里

图像采集

我使用的非常基础的USB双目相机,两个相机之间居然还存在色差。。。videoCapture就可以了

立体校正

立体校正对于双目的最主要的目的是为稠密匹配算法提供便利。opencv中有具体的立体校正函数

stereoRectify(cameraMatrixL, distCoeffL, cameraMatrixR, distCoeffR,
		imageSize, R, T, Rl, Rr, Pl, Pr, Q, CALIB_ZERO_DISPARITY,
		0, imageSize, &validROIL, &validROIR);
	//再采用映射变换计算函数initUndistortRectifyMap得出校准映射参数,该函数功能是计算畸变矫正和立体校正的映射变换
	initUndistortRectifyMap(cameraMatrixL, distCoeffL, Rl, Pl(Rect(0, 0, 3, 3)),
		imageSize, CV_32FC1, mapLx, mapLy);
	initUndistortRectifyMap(cameraMatrixR, distCoeffR, Rr, Pr(Rect(0, 0, 3, 3)),
		imageSize, CV_32FC1, mapRx, mapRy);
	remap(grayImageL, rectifyImageL, mapLx, mapLy, INTER_LINEAR);
	remap(grayImageR, rectifyImageR, mapRx, mapRy, INTER_LINEAR);//立体校正完成的图片即保存在rectifyImageL/R中

匹配算法

使用SGM算法计算左目视差,其实为了增加准确程度,也会计算右目的视差用于补偿左目视差。但是为了实时性,在这里只计算了左目视差。我自己学习了SGM算法的源代码,也可以使用opencv自带的函数,具体如何使用网上教程很多很多,这里只给出一个示例:

cv::Ptr<cv::StereoSGBM> sgbm = StereoSGBM::create(0, 16, 3);	
sgbm->setPreFilterCap(63);
	int SADWindowSize = 5;
	int sgbmWinSize = SADWindowSize > 0 ? SADWindowSize : 3;
	sgbm->setBlockSize(sgbmWinSize);
	int cn = rectifyImageL.channels();
	sgbm->setP1(8 * cn*sgbmWinSize*sgbmWinSize);
	sgbm->setP2(32 * cn*sgbmWinSize*sgbmWinSize);
	sgbm->setMinDisparity(0);
	sgbm->setNumDisparities(numberOfDisparities);
	sgbm->setUniquenessRatio(10);
	sgbm->setSpeckleWindowSize(100);
	sgbm->setSpeckleRange(1);
	sgbm->setDisp12MaxDiff(1);
	sgbm->setMode(cv::StereoSGBM::MODE_SGBM);
	sgbm->compute(rectifyImageL,//250, 100, 250, 100;150, 100, 400, 300
		rectifyImageR, disp);

三维重构

我只想说,opencv挺好用

	disp.convertTo(disp8, CV_32F, 255 / (numberOfDisparities * 16.));	//1.0/16计算出的视差是CV_16S格式 CV_32F, 255 / ((numDisparities * 16 + 16)*16.) 255 / (numberOfDisparities*16.) 
	reprojectImageTo3D(disp8, xyz, Q, true);//Q是之前立体校正得到的参数计算3D点云保存在xyz中

点云去噪

在上述过程中获得了稠密点的坐标xyz,将其赋值给点云,使用点云滤波即可去噪。PCL点云库的使用移步这里

void two_Eyes::cal_cloud(int disflag)
{
	double plane[3];
	mutex1.lock();
	param_3D.xyz.copyTo(xyz);
	plane[0] = param_3D.plane[0];
	plane[1] = param_3D.plane[1];
	plane[2] = param_3D.plane[2];
	mutex1.unlock();	
	double fenmu = sqrt(powf(plane[0], 2) + powf(plane[1], 2) + 1);
	double Wx, Wy, Wz;
	vector<double>().swap(dis);			//清楚dis中的内容


	double t_c = (double)clock();
	cvtColor(rectifyImageL, rectifyImageL, CV_GRAY2RGB);
	int rowNumber = rectifyImageL.rows;
	int colNumber = rectifyImageL.cols;
	pcl::PointCloud<pcl::PointXYZRGB> cloud_a2,cloud_a3;
	cloud_a2.height = rowNumber;
	cloud_a2.width = colNumber;
	cloud_a2.points.resize(colNumber* rowNumber);
	for (unsigned int u = 0; u < rowNumber; ++u)
	{
		for (unsigned int v = 0; v < colNumber; ++v)
		{
			/*unsigned int num = rowNumber*colNumber-(u*colNumber + v)-1;*/
			unsigned int num = u * colNumber + v;
			cloud_a2.points[num].b = rectifyImageL.at<Vec3b>(u, v)[0];
			cloud_a2.points[num].g = rectifyImageL.at<Vec3b>(u, v)[1];
			cloud_a2.points[num].r = rectifyImageL.at<Vec3b>(u, v)[2];
			
			double Xw = 0, Yw = 0, Zw = 0;
			if (xyz.at<Vec3f>(u, v)[2] < 1000&& xyz.at<Vec3f>(u, v)[2]!=0)					//使用OpenCV计算的结果,感觉更加准确
			{
				Wx= xyz.at<Vec3f>(u, v)[0]; 
				Wy= xyz.at<Vec3f>(u, v)[1]; 
				Wz= xyz.at<Vec3f>(u, v)[2];
				cloud_a2.points[num].x = Wx/1000;
				cloud_a2.points[num].y = Wy/1000;
				cloud_a2.points[num].z = Wz/1000;
					
			}
			
			


		}
	}

///滤波示例
	 创建pcl::StatisticalOutlierRemoval滤波器对象
	//pcl::StatisticalOutlierRemoval<pcl::PointXYZRGB> sor;
	//sor.setInputCloud(cloud_a2.makeShared());
	//sor.setStddevMulThresh(1.0);
	将标准差倍数设为1,意味着超过一点的距离超出平均距离一个标准差以上,
	则该点被标记为离群点,将被移除。
	//sor.filter(cloud_a3);  //滤波结果存储于此 
	
	
	
	
	mutex1.lock();
	param_3D.cloud_a = cloud_a2;
	mutex1.unlock();
	cloud_test.close();
	
}

点云显示

可以直接使用PCL库
我是在QT界面上使用VTK显示的点云,这里涉及到更多的QT界面的基础知识,不再赘述
结果如图:
在这里插入图片描述
点云示例:
在这里插入图片描述
在这里插入图片描述

总结

细心可以避免很多小错误
不怕自己做不好,就怕自己停止尝试

由于相机编号0,1和左右不一定是对应的,所以一定要搞清楚再运行算法,别问我是咋知道的~

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

双目立体视觉三维重构总结 的相关文章

  • 矩形相交

    是否有任何已知的方法来计算两个矩形之间的相交矩形 我的意思是 如果矩形 A 由 x1 y2 x2 y2 定义 B 由 x3 y3 x4 y4 定义 那么如何计算相交矩形 C x5 y5 x6 y6 的坐标 Thanks 相交多边形的一般问题
  • Python openAL 3D 声音

    我刚刚开始使用 python 正在制作音频操作程序 我正在尝试在我的 python 应用程序中使用 openAL 实现 3D 声音 但我只能让它工作 这是我的 3D 声音代码 from openal loaders import load
  • 如何插值旋转?

    我有两个描述旋转的向量 起始旋转 A 和目标旋转 B 我如何最好地通过因子 F 对 A 进行插值以接近 B 当需要插值多个维度时 即产生不需要的旋转 在向量上使用简单的 lerp 不起作用 也许从旋转向量构建四元数并使用Slerp http
  • 网格三角剖分和简化 C++ 库 [关闭]

    Closed 这个问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 我正在寻找一个 C 库来三角测量和简化 3D 网格 我的 3D 网格可能很大 大约 300 万个顶点
  • xna 防止下坡或上太陡的山

    如何防止在高度图地形上过于陡峭的斜坡或上山 我有一个可以在地形上移动的 3D 相机 它现在可以在任何地方移动 甚至在大斜坡和太陡的山丘上 我该怎么办 如果你试图朝一个方向移动 你应该预测你最终会到达哪里 然后弄清楚是否slope http
  • 如何在 Android 上将 2D 图像转换为 3D? [关闭]

    很难说出这里问的是什么 这个问题是含糊的 模糊的 不完整的 过于宽泛的或修辞性的 无法以目前的形式得到合理的回答 如需帮助澄清此问题以便重新打开 访问帮助中心 help reopen questions 我需要将 2D 图像显示为 3D 图
  • 是否可以在 Netbeans 7.0 应用程序中使用 Jzy3D?

    好吧 我们正在尝试将 3D 散点图合并到 Netbeans 7 0 中的项目中 我们选择测试的库之一是 Jzy3D 看起来它会做我们需要它做的一切 但不幸的是 它什么也没做 我已经正确安装了 JOGL 并对其进行了测试 发现它可以正常工作
  • SceneKit 修改 3D 对象并导出文件

    在我的应用程序中 我使用 SceneKit Framework 在 SCNView 中显示 3D 对象 并导出修改后的文件 并进行一些小的更改 如颜色 温度等 但在将其导出到文档文件夹后 我得到了原始文件 在这里我可以显示 3D 对象并对其
  • 求 3d 中 2 个任意立方体的交集

    所以 我想找出一个函数 可以让您确定两个任意旋转和大小的立方体是否相交 如果立方体的旋转不是任意的 而是锁定到特定的轴 则相交很简单 您可以通过检查它们的边界来检查它们是否在所有三个维度上相交 以查看它们在所有三个维度上是否相交或在彼此之内
  • Python 中的标量场可视化

    我需要在 Python 中可视化几个重叠的标量场 我发现mayavi图书馆做这种情节 问题是我不明白如何为标量字段自定义颜色图 我的想法是为每个字段设置一种颜色的阴影 我尝试采用一个例子 http docs enthought com ma
  • 编写每个三角形/面具有纯色的 GLSL 片段着色器的方法

    我有顶点和三角形数据 其中包含每个数据的颜色triangle 面 不是每个顶点 即单个顶点由多个面共享 每个面可能具有不同的颜色 我应该如何在 GLSL 中解决这个问题以获得每个的纯色分配face正在渲染 通过平均顶点相邻多边形的颜色来计算
  • 给定 3D 空间中的一条线,如何找到从它到一点的角度?

    我在 3D 空间中有两组点 我想画一条穿过两组点的中心的线 然后找到从该线到每个点的角度 从那里开始 我将根据两个角度的接近程度来确定两组中的匹配点 我知道如何找到每组点的中心 只需将它们平均在一起 并且我知道如何将它们匹配 甚至考虑到它们
  • 点列表的 3D 轮廓(凹壳)

    我有一个 C 中的 Vector3 点列表 我需要计算这些点的凹轮廓 确实有很多参考资料 特别是对于 凸 分辨率 由于格雷厄姆算法 我已经成功实现了 然而 由于我现在需要有效地计算凹轮廓 所以我迷失了 维基百科确实列出了很多用于凸计算的资源
  • OpenGL Z 偏置(多边形偏移)限制

    我有两个共面的多边形 我尝试做 glEnable GL POLYGON OFFSET FILL glPolygonOffset 0 1 并期望其中一个明显 位于 另一个之上 这种情况直到大约 70 75 个单位之外 近剪裁平面为 1 远剪裁
  • 在 Three.js 中将贝塞尔曲线转换为平面道路

    我试图根据之前计算得到的一些贝塞尔曲线在 Three js 中绘制一条弯曲的道路 问题是我找不到转换曲线序列的方法 一条从上一条曲线的末尾开始 到一个曲面 我有一个 3D 场景 其中有一些汽车 一条用飞机创建的道路 并且绘制了即将到来的道路
  • 投影 3D 网格的 2D 轮廓算法

    给定 一个 3D 网格 由一组顶点和三角形定义 并用这些点构建网格 问题 找到任意平面上投影的任意旋转网格的二维轮廓 投影很容易 挑战在于找到平面中投影三角形边的 外壳 我需要一些有关研究该算法的输入 指针的帮助 为简单起见 我们可以假设
  • GL_CULL_FACE使所有对象消失

    我正在尝试在 openGL3 3 中创建一些简单的多边形 我有两种类型的对象 具有以下属性 对象 1 10 个顶点 按顺序在下面列出 存储在GL ARRAY BUFFER并使用GL TRIANGLE FAN v x y z w v 0 0
  • IE9-11 检测变换样式:preserve-3d

    我为一个项目制作了一个 3d 类型的菜单 自然 IE 会引起问题 因为 IE10 即使 3d 变换工作 也不支持变换样式 preserve 3d 我尝试了解决方法 通过对 3d 菜单容器的每个子元素应用变换 但至少可以说 动画看起来很糟糕
  • CSS3DObject 始终位于 WebGL Mesh 前面

    我正在混合CSS3D Renderer with WebGL Renderer to add HTML3D 空间中的元素WebGL场景 这CSS3DObject在前面WebGL网格即使WebGL Renderer具有较高的 z index
  • 不明确的 OpenGL 默认相机位置

    在我的Opengl程序中 在我应用透视投影矩阵之前 每当我绘制一些对象时 我都会在世界坐标系的原点处绘制它 但是几乎所有Opengl教程都指出相机 我的投影视图 位于原点朝向正 z 轴 这取决于您稍后如何处理投影矩阵中的 z 值 但是如果这

随机推荐

  • 将图像上雨水去除的四种主流方法

    http blog csdn net whyymlm article details 76999469 对图片或者视频进行去噪的研究一直以来都是计算机视觉和图像处理领域内的一个重要课题 在现实生活中 因为雨雪会对道路上的路况造成一定程度的遮
  • 程序员兼职接私活平台大全,兼职也能月薪上万

    前言 PS 如有需要Python学习资料的小伙伴可以加点击下方链接自行获取 CSDN大礼包 python兼职资源 全套学习资料 免费分享 安全链接 放心点击 根据我们的经验 程序员兼职主要分为三种 兼职职位众包 项目整包和自由职业者驻场 我
  • C++14变量模板

    如果对模板或者C 标准感兴趣的开发者们相信都不会对变量模板感到陌生 我们今天就讲一讲变量模板 从C 14 开始 变量也可以被某种类型参数化 称为变量模板 例如可以通过下面的代码定义pi 但是参数化了其类型 template
  • Kaggle竞赛题目之——Digit Recognizer

    Classify handwritten digits using the famous MNIST data This competition is the first in a series of tutorial competitio
  • 代码随想录刷题笔记3

    文章目录 回溯 细节 模板 题型 组合 分割 子集 排列 棋盘问题 N皇后问题 解数独问题 其他 总结 回溯 本质上 穷举 剪枝 回溯法就是解决这种k层for循环嵌套的问题 for循环横向遍历 递归纵向遍历 回溯不断调整结果集 注意画出 解
  • JavaScript闭包

    h2 span style font weight normal background color rgb 192 192 192 span style font size 18px 1 什么是闭包 span span h2 h4 span
  • RabbitMQ--基础--8.2--消息确认机制--发布确认机制

    RabbitMQ 基础 8 2 消息确认机制 发布确认机制 代码位置 https gitee com DanShenGuiZu learnDemo tree master rabbitMq learn rabbitMq 03 1 发布确认原
  • 空间相关分析(二) 全局莫兰指数的理解与计算

    在了解空间权重矩阵的相关知识后 再展开对空间相关分析的学习就会变得轻松许多 而在空间相关分析中 全局相关分析和局部相关分析是比较常用的两个方法 今天 就来分享一下全局相关分析的有关知识 目录 一 公式说明 二 深入理解 三 Moran I指
  • 投资理财笔记——以贴现的方式看待基金

    文章目录 DDM DCF 避免空中楼阁 DDM 关于DDM的相关知识 我在股票价值分析中写过 DDM模型认为股票价值决定于分红而不是未来的股价 而在基金购买中 我认为不可以盲目崇拜于分红 也就是基金的累计净值和净值之差 因为分红势必会出售部
  • Relational Learning with Gated and Attentive Neighbor Aggregator for Few-Shot Knowledge Graph Comple...

    小样本知识图补全 关系学习 利用三元组的邻域信息 提升模型的关系表示学习 来实现小样本的链接预测 主要应用的思想和模型包括 GAT TransH SLTM Model Agnostic Meta Learning MAML 论文地址 htt
  • Java8新特性

    可以利用 List 的 sort 方法进行排序 Comparator comparing 可以指定排序字段 thenComparing 可以继续指定其他的排序字段 默认使用正序排列 如果想倒序可以使用 Comparator reverseO
  • 人工智能与营销新纪元 2023 AI+

    人工智能是什么 有望飞跃式提升营销生产力的变革力量 人工智能是研究 开发用于模拟 延伸和扩展人的智能的理论 方法 技术及应用系统的一门新的 技术科学 是计算机科学的一个分支 它企图了解智能的实质 并生产出一种新的能以人类智能相 似的方式做出
  • macOS和谐安装Office 2021

    声明 和谐 PJ 安装Office 2021 仅用于学习研究使用 不能作为办公用途 本人概不负法律责任 简介 Microsoft Office 2021是Microsoft推出的办公软件 2021年10月5日 Office 2021 for
  • This call to matplotlib.use() has no effect because the backend has alreadybeen chosen

    遇到这个咋办 方法 将 matplotlib use Agg 改为 plt switch backend agg 大吉大利
  • AF_XDP socket 测试

    本篇是之前博客 1 的进阶篇 博客中给出了相关环境安装配置 功能 本篇通过bpf程序 将icmp数据包重定向到AF XDP socket 内核侧程序片断 xdpsock kern c SPDX License Identifier GPL
  • 如何在windows电脑端添加本地环回网卡loopback网络适配器

    电脑端添加本地环回网卡loopback网络适配器 在使用vmware workstation虚拟机或ENSP等网络模拟器等工具时 经常需要绑定多个电脑网卡来进行实验 但电脑中物理网卡有限 此时可通过添加本地环回网卡来解决相关问题 1 桌面单
  • Mysql中的七种常用查询连接详解

    目录 一 概述 二 连接查询的分类 三 七种常用连接查询详解 1 笛卡尔积 2 内连接 2 1隐式与显式连接 2 2等值连接 2 3非等值连接 2 4自连接 3外连接 3 1左外连接 3 2右外连接 3 3全外连接 一 概述 在实际开发中
  • cocos2d函数

    CCNodeLoader parseProperties CCBReader readNodeGraph kCCBPropTypeBlockCCControl CCInvocation parsePropTypeBlockCCControl
  • 【华为OD机试真题 python】任务最优调度 【2021 H2, 2022 Q1,Q2 考试题】

    题目描述 给定一个正整数组表示待系统执行的任务列表 数组的每一个元素代表一个任务 元素的值表示该任务的类型 请计算执行完所有任务所需的最短时间 任务执行规则如下 任务可以按任意顺序执行 且每个任务执行耗时间均为1个时间单位 两个同类型的任务
  • 双目立体视觉三维重构总结

    文章目录 基本步骤 相机标定 图像采集 立体校正 匹配算法 三维重构 点云去噪 点云显示 总结 前面多多少少记录一些相关知识 由于相关工作还在继续 加上网上的教程总不是十分完善 这里做一个总结 希望自己能够加深对这个过程的整体的理解与认识