草庐IT

3D视觉笔记(1) - 双目视觉三维测量原理

亦枫Leonlew 2023-08-30 原文

中心投影模型(针孔相机模型)

        在之前的笔记中,有讨论过针孔相机的模型和世界坐标系统的点如何投影到图像坐标系中。参考如下两篇笔记:

几何角度理解相机成像过程_亦枫Leonlew的博客-CSDN博客本笔记从几何角度来理解相机的成像过程,我们生活在三维世界中,相机所捕捉到的画面是2D的,3D空间中的点是如何投影到2D平面的过程是本笔记关注的。这个过程其实和3D游戏中的透视投影过程是一样的。本笔记只要知道矩阵乘法的知识就可以理解。https://blog.csdn.net/vivo01/article/details/128252788?spm=1001.2014.3001.5502相机标定笔记(1) -- 相机模型_亦枫Leonlew的博客-CSDN博客我们知道,相机的图像是三维世界到2D平面的一个投影。仅从这个2D图像来看,我们无法得知图像中的物体在真实物理世界中有多大,距离相机的距离有多远。那么我们有没有办法从这个2D的图片结合相机的参数获得这些信息呢?答案是有的,方法有很多种,比如双目视觉技术,可以用来恢复三维信息。如何恢复精确的3D物体?图像失真(比如镜头畸变)了如何恢复?先用数学表达式描述对相机成像过程建模,然后通过数学表达式计算恢复这些信息。https://blog.csdn.net/vivo01/article/details/128471170?spm=1001.2014.3001.5502        在本笔记中,我们首先来搞清楚一件事情,为什么单目相机无法测得深度(这句话不太严谨,限定为单目相机位置不变的情况下,所拍摄的一张图,从这张图无法得到深度信息)?

        来看针孔相机模型示意图:

         

         在3D世界中的一个点P,经过投影后在相机的成像平面上形成一个像点p,这个过程(3D到2D的投影)是确定的。但是反过来,我们知道成像平面上的一个像点p,想要知道3D世界中的点P的信息,则P的位置是无法确定的。根据一副图像中的一个2D像点p,加上相机的中心点O,我们只能确定出一条射线,如下图:

         我们要找的P点,在Op延长线上的任意位置都有可能,这些点如P1,P2,P3经过投影都对应到相机成像平面的p点。

        为了能够确定出点P的位置,我们可以使用两个相机,拍摄两幅图。这样就能发出两条射线,如下图所示:

         这样两个相机的两条射线的交点就能确定目标点的3D位置。这是双目立体视觉系统进行3D测量的基本原理。

理想的双目系统模型

         理想的双目系统中,两个相机的焦距f完全相同,左右两个相机处于同一个平面内,光轴平行。

        首先来看两个概念:B - 基线长度,指的是左右两个相机关心之间的距离, D - 视差,表示P点投影到左右相机成像平面上两点的x坐标之间的差值

        如下图,假设P点的坐标位置是(X,Y,Z):

        在之前笔记中,我们知道了相机的图像坐标系以光轴和成像平面的交点为原点。因此在上图中,左相机的值为正,右相机的 为负,。

        图中标注了两个红色箭头,每个红色箭头所覆盖的两个一大一小的三角形是相似的。对于左相机的两个相似三角形,我们可以得到:

        (式1)

        同理,对于右相机来说,可以得到:

        (式2,由于为负,因此小三角形对应的边长度为-

         对于Y来说,同样根据相似三角形可以得到(这里不再画出YZ平面的视图,感兴趣的朋友自行推导):

        (式3)

        根据式1和式2,我们可以解出X:

        (式4)

        将X代入到式1中,可以解出Z:

        

        一般来说Z会先用这个式子求解,然后用Z和f去表示X和Y,因此X为:

        

        对于Y来说,将Z代入利用类似的方法也可以求解出来:

        

        综上,我们就可以通过左右两个相机的像点来推出P点的三维坐标了。

        对于P'和P‘’这两个位置来说,使用同样推导过程可以得出同样的结论,感兴趣的朋友自行推导,不再赘述。

如何确定左右两幅图的点对应关系

        前面小节说明了双目相机是如何根据两个点来演算出3D世界中的点P的。但有个前提是,我们知道这两个点是3D世界中的点P投影到左右相机成像平面上的点。也就是说这两个点对应3D世界中的同一个物点。

        对于计算机来说,它只是得到了两幅图,但两幅图中的两个点是否对应到3D世界中的同一个点来说,它是不知道的,因此我们需要一些匹配算法来做这个事情。

特征匹配

      在计算机视觉领域,计算机识别点对应关系的方法通常是特征匹配(Feature Matching)。  下图展示了使用ORB特征描述符(一种找点对应关系的方法)进行匹配后的结果。

        一种最简单的用于找到点对应关系的方法是找到临近像素信息都类似的像素,假设两个像素点一定范围内的邻居像素相似度很高,那么就认为这两个点是两幅图中对应的点。比如对于下图左相机的一个点,找出这个点和其邻居像素的信息作为比对信息,在右图中进行搜索匹配。

        但这种暴力搜索的方法有两个比较蛋疼的问题。如上图所示,第一个问题是搜索的空间太大,假设我们要找左图用蓝色线框所标记的点,在右图搜索时要去搜索的范围没有任何指导性的算法去缩小这个范围。第二个问题是我们从比对结果可以看到,对于左图中的一个像素,右图中存在多个匹配结果。显然这种方法要找到真正的匹配是非常低效并且困难的。

        有没有办法缩小搜索空间呢?其实是有的,可以使用对极几何(epipolar geometry)的知识来做到这一点。

        对极几何描述了左右两个相机所拍摄的两幅图之间固有的对应关系,是立体视觉研究中重要的数学方法。

对极几何在立体匹配中的应用

        以上图为例来讲解重要的概念:

        基线(baseline):左右相机中心点O1,O2的连线

         极平面(epipolar plane):上图中使用射线O1P1加上基线O1O2可以确定出一个平面O1O2P1。这个平面区域可以随着射线O1P1方向延伸,比如延伸到P点后,这个平面就是O1O2P,我们称这个平面为极平面。

        极点(epipole): e1,e2这两个点称为极点。e1是O2在左像平面的投影,e2是O1在右像平面的投影。

        极线(epipolar line):极平面和两个成像平面相交的线称为极线。如上图的e1P1,e2P2。

        知道了上面的基本概念后,我们来看一个立体视觉中经常会听到的概念,极线约束。

极线约束

        极线约束所要说的事情简单来说就是,一个成像平面A中的一个点在另一个成像平面B中的位置一定在极平面与成像平面B相交的极线上。还是以前面的图为例,假设我们知道右像平面中的P2点的坐标,我们想找到P2在左像平面中和其对应的点的坐标,我们就沿着e1P1这条线进行搜索就好了。

        我们最终要确定的位置点是P1,对应3D世界中的点P。点P和P3,P4,P5,P6都在射线O2P2延长线上,因此它们在右像平面上的投影都对应P2这个点。我们把P,P3,P4,P5,P6这几个点投影到左像平面上,由于这些点都共面(极平面),这几个点一定会投影到极线e1P1上。反过来,假设我们知道P1,想要在右像上搜索P2,原理也是类似的。

        上面的图基本是实际的双目相机中的例子,但这个和我们所说的理想双目系统的模型还是有差异。上图的例子中,极线是倾斜的,在两个维度上(x,y)上都有涉及。而理想的双目系统模型中,我们可以知道,左图中的某个点P,在右图中一定和P点处于同一行的位置,这样在做搜索时,就能去掉一个维度的信息,更加简单高效。那么有没有办法将真实的非理想的双目系统经过变换变成理想的双目系统呢?答案当然也是有的,就是接下来要介绍的极线校正的概念。

极线校正

         极线校正最终目的是让极线对共线且平行于像平面的某个坐标轴,通常是水平轴,经过极线校正后,建立了新的左右立体成像平面对。校正完成后,同一匹配点对,在两个成像平面中处于同一行内,也就是说它们在两个成像平面上只有水平位置的差异,这个差异称为视差(disparity)。

        下图是一个实际的例子,可以更加直观的看到校正前后的差别。

         上图(a)是为进行校正时,极线(黑色)的分布情况。(b)则是进行校正之后的样子。

        想要进一步了解极线校正细节,可以参考这篇文章:

立体视觉入门指南(6):对级约束与Fusiello法极线校正 - 知乎亲爱的同学们,我们的世界是3D世界,我们的双眼能够观测三维信息,帮助我们感知距离,导航避障,从而翱翔于天地之间。而当今世界是智能化的世界,我们的科学家们探索各种机器智能技术,让机器能够拥有人类的三维感…https://zhuanlan.zhihu.com/p/466758105

有关3D视觉笔记(1) - 双目视觉三维测量原理的更多相关文章

  1. 世界前沿3D开发引擎HOOPS全面讲解——集3D数据读取、3D图形渲染、3D数据发布于一体的全新3D应用开发工具 - 2

    无论您是想搭建桌面端、WEB端或者移动端APP应用,HOOPSPlatform组件都可以为您提供弹性的3D集成架构,同时,由工业领域3D技术专家组成的HOOPS技术团队也能为您提供技术支持服务。如果您的客户期望有一种在多个平台(桌面/WEB/APP,而且某些客户端是“瘦”客户端)快速、方便地将数据接入到3D应用系统的解决方案,并且当访问数据时,在各个平台上的性能和用户体验保持一致,HOOPSPlatform将帮助您完成。利用HOOPSPlatform,您可以开发在任何环境下的3D基础应用架构。HOOPSPlatform可以帮您打造3D创新型产品,HOOPSSDK包含的技术有:快速且准确的CAD

  2. FOHEART H1数据手套驱动Optitrack光学动捕双手运动(Unity3D) - 2

    本教程将在Unity3D中混合Optitrack与数据手套的数据流,在人体运动的基础上,添加双手手指部分的运动。双手手背的角度仍由Optitrack提供,数据手套提供双手手指的角度。 01  客户端软件分别安装MotiveBody与MotionVenus并校准人体与数据手套。MotiveBodyMotionVenus数据手套使用、校准流程参照:https://gitee.com/foheart_1/foheart-h1-data-summary.git02  数据转发打开MotiveBody软件的Streaming,开始向Unity3D广播数据;MotionVenus中设置->选项选择Unit

  3. Unity 3D 制作开关门动画,旋转门制作,推拉门制作,门把手动画制作 - 2

    Unity自动旋转动画1.开门需要门把手先动,门再动2.关门需要门先动,门把手再动3.中途播放过程中不可以再次进行操作觉得太复杂?查看我的文章开关门简易进阶版效果:如果这个门可以直接打开的话,就不需要放置"门把手"如果门把手还有钥匙需要旋转,那就可以把钥匙放在门把手的"门把手",理论上是可以无限套娃的可调整参数有:角度,反向,轴向,速度运行时点击Test进行测试自己写的代码比较垃圾,命名与结构比较拉,高手轻点喷,新手有类似的需求可以拿去做参考上代码usingSystem.Collections;usingSystem.Collections.Generic;usingUnityEngine;u

  4. [Vuforia]二.3D物体识别 - 2

    之前说过10之后的版本没有3dScan了,所以还是9.8的版本或者之前更早的版本。 3d物体扫描需要先下载扫描的APK进行扫面。首先要在手机上装一个扫描程序,扫描现实中的三维物体,然后上传高通官网,在下载成UnityPackage类型让Unity能够使用这个扫描程序可以从高通官网上进行下载,是一个安卓程序。点到Tools往下滑,找到VuforiaObjectScanner下载后解压数据线连接手机,将apk文件拷入手机安装然后刚才解压文件中的Media文件夹打开,两个PDF图打印第一张A4-ObjectScanningTarget.pdf,主要是用来辅助扫描的。好了,接下来就是扫描三维物体。将瓶

  5. LC滤波器设计学习笔记(一)滤波电路入门 - 2

    目录前言滤波电路科普主要分类实际情况单位的概念常用评价参数函数型滤波器简单分析滤波电路构成低通滤波器RC低通滤波器RL低通滤波器高通滤波器RC高通滤波器RL高通滤波器部分摘自《LC滤波器设计与制作》,侵权删。前言最近需要学习放大电路和滤波电路,但是由于只在之前做音乐频谱分析仪的时候简单了解过一点点运放,所以也是相当从零开始学习了。滤波电路科普主要分类滤波器:主要是从不同频率的成分中提取出特定频率的信号。有源滤波器:由RC元件与运算放大器组成的滤波器。可滤除某一次或多次谐波,最普通易于采用的无源滤波器结构是将电感与电容串联,可对主要次谐波(3、5、7)构成低阻抗旁路。无源滤波器:无源滤波器,又称

  6. ruby - 在没有基准或时间的情况下用 Ruby 测量用户时间或系统时间 - 2

    因为我现在正在做一些时间测量,我想知道是否可以在不使用Benchmark类或命令行实用程序time的情况下测量用户时间或系统时间。使用Time类只显示挂钟时间,而不显示系统和用户时间,但是我正在寻找具有相同灵active的解决方案,例如time=TimeUtility.now#somecodeuser,system,real=TimeUtility.now-time原因是我有点不喜欢Benchmark,因为它不能只返回数字(编辑:我错了-它可以。请参阅下面的答案。)。当然,我可以解析输出,但感觉不对。*NIX系统的time实用程序也应该可以解决我的问题,但我想知道是否已经在Ruby中实

  7. python - Ruby 或 Python 的 3d 游戏引擎? - 2

    关闭。这个问题不符合StackOverflowguidelines.它目前不接受答案。要求我们推荐或查找工具、库或最喜欢的场外资源的问题对于StackOverflow来说是偏离主题的,因为它们往往会吸引自以为是的答案和垃圾邮件。相反,describetheproblem以及迄今为止为解决该问题所做的工作。关闭9年前。Improvethisquestion是否有适用于这些的3d游戏引擎?

  8. Unity Shader 学习笔记(5)Shader变体、Shader属性定义技巧、自定义材质面板 - 2

    写在之前Shader变体、Shader属性定义技巧、自定义材质面板,这三个知识点任何一个单拿出来都是一套知识体系,不能一概而论,本文章目的在于将学习和实际工作中遇见的问题进行总结,类似于网络笔记之用,方便后续回顾查看,如有以偏概全、不祥不尽之处,还望海涵。1、Shader变体先看一段代码......Properties{ [KeywordEnum(on,off)]USL_USE_COL("IsUseColorMixTex?",int)=0 [Toggle(IS_RED_ON)]_IsRed("IsRed?",int)=0}......//中间省略,后续会有完整代码 #pragmamulti_c

  9. 【自动驾驶环境感知项目】——基于Paddle3D的点云障碍物检测 - 2

    文章目录1.自动驾驶实战:基于Paddle3D的点云障碍物检测1.1环境信息1.2准备点云数据1.3安装Paddle3D1.4模型训练1.5模型评估1.6模型导出1.7模型部署效果附录show_lidar_pred_on_image.py1.自动驾驶实战:基于Paddle3D的点云障碍物检测项目地址——自动驾驶实战:基于Paddle3D的点云障碍物检测课程地址——自动驾驶感知系统揭秘1.1环境信息硬件信息CPU:2核AI加速卡:v100总显存:16GB总内存:16GB总硬盘:100GB环境配置Python:3.7.4框架信息框架版本:PaddlePaddle2.4.0(项目默认框架版本为2.3

  10. Tcl脚本入门笔记详解(一) - 2

    TCL脚本语言简介•TCL(ToolCommandLanguage)是一种解释执行的脚本语言(ScriptingLanguage),它提供了通用的编程能力:支持变量、过程和控制结构;同时TCL还拥有一个功能强大的固有的核心命令集。TCL经常被用于快速原型开发,脚本编程,GUI和测试等方面。•实际上包含了两个部分:一个语言和一个库。首先,Tcl是一种简单的脚本语言,主要使用于发布命令给一些互交程序如文本编辑器、调试器和shell。由于TCL的解释器是用C\C++语言的过程库实现的,因此在某种意义上我们又可以把TCL看作C库,这个库中有丰富的用于扩展TCL命令的C\C++过程和函数,所以,Tcl是

随机推荐