OpenCV:如何在cv2.fisheye.undistortImage之后得到一个点的位置?
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了OpenCV:如何在cv2.fisheye.undistortImage之后得到一个点的位置?相关的知识,希望对你有一定的参考价值。
我想创造一个鱼眼效果,但我不熟悉cv2.fisheye.undistortImage()
和cv2.fisheye.undistortPoints()
。这是我的代码:
import cv2
import glob
import numpy as np
# grab a list of jpg from one folder
img_list = glob.glob('/home/folder/*.jpg')
# get the K and D for cv2.fisheye.undistortImage
K = np.array([[900.,0,512],
[0,900.,288],
[0.,0.,1]])
D = np.array([4.,100.,0.,0.])
# create a random point
point = np.array([[[300.,300.],[300,400],[400,400],[400,300]]])
# get a knew for cv2.fisheye.undistortImage
Knew = K.copy()
Knew[(0,1),(0,1)] = Knew[(0,1),(0,1)]
for img_path in img_list:
img = cv2.imread(img_path)
# draw all four points on the original image
cv2.circle(img,(300,300), 5, (0,0,255), -1)
cv2.circle(img,(400,300), 5, (0,0,255), -1)
cv2.circle(img,(300,400), 5, (0,0,255), -1)
cv2.circle(img,(400,400), 5, (0,0,255), -1)
# distort the images
img_out = cv2.fisheye.undistortImage(img,K,D=D,Knew=Knew)
# send the points to cv2.fisheye.undistortPoints
point_out = cv2.fisheye.undistortPoints(point,K =K1, D=D)
# looks like the out is around (-1,1) so i tried to recover back
#cv2.circle(img,(600,300), 5, (0,0,255), -1)
x = int((512.+(point_out[0][0][0]*1024)))
y = int((288.+(point_out[0][0][1]*576)))
cv2.circle(img_out,(x,y), 5, (0,255,0), 1)
x = int((512.+(point_out[0][1][0]*1024)))
y = int((288.+(point_out[0][1][1]*576)))
cv2.circle(img_out,(x,y), 5, (0,255,0), 1)
x = int((512.+(point_out[0][2][0]*1024)))
y = int((288.+(point_out[0][2][1]*576)))
cv2.circle(img_out,(x,y), 5, (0,255,0), 1)
x = int((512.+(point_out[0][3][0]*1024)))
y = int((288.+(point_out[0][3][1]*576)))
cv2.circle(img_out,(x,y), 5, (0,255,0), 1)
# save the img
cv2.imwrite(img_path+'.jpg',img_out,[100])
此代码是一个尝试在执行undistortImage()
后获取输出位置的实验。首先,我在原始图像上绘制一个红点,例如(300,300)。然后,我使用undistortImage()
进行鱼眼效果,因此红点可能位于不同的位置。但是,我不知道如何计算正确的位置。
我认为undistortPoints()
可能会得到正确的位置。不幸的是,绿色圆圈显示我的方法是错误的。有人可以告诉我们如何获得正确的价值吗?
答案
在调用fisheye.undistortImage时,使用Knew为失真图像指定摄像机矩阵。当你打电话给fisheye.undistortPoints时,你需要做同样的事情。如果您阅读文档,您将看到您可以给出一个P参数,即“新相机矩阵(3x3)或新投影矩阵(3x4)”。那正是你想要的。
for img_path in img_list:
img = cv2.imread(img_path)
# draw all four points on the original image
cv2.circle(img,(300,300), 5, (0,0,255), -1)
cv2.circle(img,(400,300), 5, (0,0,255), -1)
cv2.circle(img,(300,400), 5, (0,0,255), -1)
cv2.circle(img,(400,400), 5, (0,0,255), -1)
# distort the images
img_out = cv2.fisheye.undistortImage(img,K,D=D,Knew=Knew)
# send the points to cv2.fisheye.undistortPoints
point_out = cv2.fisheye.undistortPoints(point,K =K, D=D, P=Knew)[0]
for point in point_out:
cv2.circle(img_out, (int(point[0]), int(point[1])), 5, (0,255,0), 1)
# save the img
cv2.imwrite(img_path+'.jpg',img_out,[100])
以上是关于OpenCV:如何在cv2.fisheye.undistortImage之后得到一个点的位置?的主要内容,如果未能解决你的问题,请参考以下文章
Qt-OpenCV:如何在 Qt 中显示灰度图像(opencv)