繁体   English   中英

OpenCV - 用于立体视觉的倾斜摄像机和三角测量地标

[英]OpenCV - Tilted camera and triangulation landmark for stereo vision

我正在使用立体声系统,因此我试图通过三角测量获得某些点的世界坐标。

我的相机呈现一个角度,Z轴方向(深度方向)与我的表面不正常。 这就是为什么当我观察平面时,我得不到恒定的深度而是“线性”变化,对吗? 我希望从基线方向的深度...我如何重新投射?

在此输入图像描述

我的代码与我的投射数组和三角函数:

#C1 and C2 are the cameras matrix (left and rig)
#R_0 and T_0 are the transformation between cameras
#Coord1 and Coord2 are the correspondant coordinates of left and right respectively
P1 = np.dot(C1,np.hstack((np.identity(3),np.zeros((3,1))))) 

P2 =np.dot(C2,np.hstack(((R_0),T_0)))

for i in range(Coord1.shape[0])
    z = cv2.triangulatePoints(P1, P2, Coord1[i,],Coord2[i,])

--------编辑以后-----------

谢谢scribbleink,所以我试图应用你的提议。 但我认为我有一个错误,因为它不能很好地工作,你可以在下面看到。 并且点云似乎被弯曲并朝向图像的边缘弯曲。

在此输入图像描述

U, S, Vt = linalg.svd(F)
V = Vt.T

#Right epipol
U[:,2]/U[2,2]

# The expected X-direction with C1 camera matri and C1[0,0] the focal length
vecteurX = np.array([(U[:,2]/U[2,2])[0],(U[:,2]/U[2,2])[1],C1[0,0]])
vecteurX_unit = vecteurX/np.sqrt(vecteurX[0]**2 + vecteurX[1]**2 + vecteurX[2]**2)


# The expected Y axis :
height = 2048
vecteurY = np.array([0, height -1, 0])
vecteurY_unit = vecteurY/np.sqrt(vecteurY[0]**2 + vecteurY[1]**2 + vecteurY[2]**2)


# The expected Z direction :
vecteurZ = np.cross(vecteurX,vecteurY)
vecteurZ_unit = vecteurZ/np.sqrt(vecteurZ[0]**2 + vecteurZ[1]**2 + vecteurZ[2]**2)

#Normal of the Z optical (the current Z direction)
Zopitcal = np.array([0,0,1])

cos_theta = np.arccos(np.dot(vecteurZ_unit, Zopitcal)/np.sqrt(vecteurZ_unit[0]**2 + vecteurZ_unit[1]**2 + vecteurZ_unit[2]**2)*np.sqrt(Zopitcal[0]**2 + Zopitcal[1]**2 + Zopitcal[2]**2))

sin_theta = (np.cross(vecteurZ_unit, Zopitcal))[1]

#Definition of the Rodrigues vector and use of cv2.Rodrigues to get rotation matrix
v1 = Zopitcal  
v2 = vecteurZ_unit 

v_rodrigues = v1*cos_theta + (np.cross(v2,v1))*sin_theta + v2*(np.cross(v2,v1))*(1. - cos_theta)
R = cv2.Rodrigues(v_rodrigues)[0]

您期望的z方向对于重建方法是任意的。 通常,您有一个旋转矩阵,可以从您想要的方向旋转左摄像机。 您可以轻松构建该矩阵,然后您需要做的就是将重建点乘以R的转置。

为了增加火力反应,这里有一个候选解决方案,假设预期的X方向与连接两个摄像机投影中心的线重合。

  1. 计算焦距f_1和f_2(通过针孔模型校准)。
  2. 解决摄像机1帧中摄像机2的epipole的位置问题。 为此,您可以使用立体相机对的基本矩阵(F)或基本矩阵(E)。 具体来说,左侧和右侧的epipoles位于F的零空间中,因此您可以使用奇异值分解 有关可靠的理论参考,请参见Hartley和Zisserman,第二版,表9.1“基本矩阵属性摘要”(第246页)( 本章免费提供PDF )。
  3. 相机1的投影中心,即(0,0,0)和右极点的位置,即(e_x,e_y,f_1)一起限定了与连接相机中心的线对齐的光线。 这可以用作预期的X方向。 将此向量称为v_x。
  4. 假设预期的Y轴在图像平面中面向下,即从(0,0,f_1)到(0,高度-1,f_1),其中f是焦距。 将此向量称为v_y。
  5. 预期的Z方向现在是向量v_x和v_y的叉积。
  6. 使用预期的Z方向以及摄像机1的光轴(Z轴),然后您可以使用这个其他stackoverflow帖子中列出的方法,从两个3D矢量计算旋转矩阵。

实际注意事项:根据我的实际经验,在没有相当大的努力的情况下,期望平面物体与立体基线精确对准是不可能的。 需要一定量的平面拟合和额外的旋转。

一次性工作:这取决于您是否需要执行此操作,例如,对于一次性校准,在这种情况下,只需实时进行此估算过程,然后旋转立体相机对,直到深度图方差最小化。 然后锁定你的相机位置,并祈祷有人不会碰到它。

可重复性:如果您需要将估计的深度图对齐到真正任意的Z轴,这些Z轴对于捕获的每个新帧都会发生变化,那么您应该考虑在平面估算方法中投入时间并使其更加稳健。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM