机器视觉Computer vision

参考书籍

  • Computer Vision: Algorithms and Applications, 2nd Edition by Richard Szeliski 理论基础
  • Digital Image Processing, Third Edition, by Rafael C. Gonzalez and Richard E. Woods 着重于信号处理
  • Learning OpenCV, by Adrian Kaehler and Gary Bradski 经典动物书,与第一本配套看,着重于实现与API手册

图像的形成 Image formation

3D到2D的映射 ^cv-camera-property

相机内参

  • 内参
    • :skew
    • :aspect ratio
    • 在许多应用中简化为

相机外参

  • 相机的位置和旋转

3D空间投影至2D成像平面

  • 假设成像平面坐标为,3D空间内坐标为,相机内参为(例如简化形态
  • 代码示例
def proj_to_2d(k, pt_3d):
    ## project 3d to 2d using the camera's intrisic matrix
    ## [u,v,1] = (1/z)*(k*[x,y,z]^T)
    k = np.array(k).reshape((3,3))
    px = np.dot(k, pt_3d.reshape((3,1)))
    px = (int(px[0,0]/pt_3d[2]), int(px[1,0]/pt_3d[2]))
    return px

2D到3D的逆映射

透视n点的位姿估计问题Perspective-n-Point pose computation

  • 已知物体尺寸
  • 可调用OpenCV的[[2.application/robotics/robot_software/computer_vision/opencv/opencv_camera^opencv-solvepnp|solvePnP()]]函数求解
  • 应用举例:二维码的位姿检定

深度图的逆映射

  • 如RealSense产生的,和RGB图像大小一致,作为相应像素点的值,为3D空间投影至2D成像平面的逆运算。 (实际操作中还加了负号改变方向?)
import open3d as o3d
 
self.pcd = o3d.geometry.PointCloud()
 
def img_callback(self, data):
        if self.is_k_empty == False:
            self.height = data.height
            self.width = data.width
 
            np_cloud = np.zeros((self.height*self.width,3))
            # print(self.k)
            for iy in range(self.height):
                for ix in range(self.width):
                    idx = iy*self.width+ix
                    z = (data.data[idx*2+1]*256+data.data[idx*2])/1000.0
                    if z!=0:
                        ## x, y are on the camera plane, z is the depth
                        #np_cloud[idx][0] = z*(ix-self.k[2])/self.k[0] #x
                        #np_cloud[idx][1] = z*(iy-self.k[5])/self.k[4] #y
                        #np_cloud[idx][2] = z
                        ## same coordinate as `/camera/depth/image_rect_raw`
                        ## y (left & right), z (up & down) are on the camera plane, x is the depth
                        np_cloud[idx][1] = -z*(ix-self.k[2])/self.k[0]
                        np_cloud[idx][2] = -z*(iy-self.k[5])/self.k[4]
                        np_cloud[idx][0] = z
 
            self.pcd.points = o3d.utility.Vector3dVector(np_cloud)
            ## publish as a ROS message
            # header = Header()
            # header.stamp = rospy.Time.now()
            # header.frame_id = "camera_depth_frame"
            # fields = self.FIELDS_XYZ
 
            # pc2_data = pc2.create_cloud(header, fields, np.asarray(np_cloud))
            # self.pub.publish(pc2_data)
            self.is_data_updated = True

色彩空间

RGB

HSV/HSL

  • 三个参数分别为色调Hue,饱和度Saturation和亮度Value
  • 采用HSV色彩空间进行颜色特征检测时如何选择取值区间:
    • 可以先截取一张图片,使用工具HsvRangeTool帮助找出上下限
    • 通过调整H的区间选取特征颜色
    • 通过调整S选择白色的成分(保留适当的饱和度)
    • 通过调整V选择黑色的成分

LAB

  • 三个参数分别为亮度Luminosity,洋红色到绿色A,黄色到蓝色B

LUV

  • 三个参数分别为L为物体亮度,U和V为色度,由CIE XYZ空间变换而来

图像处理Image processing

滤波器

  • 图像平滑滤波:均值滤波,中值滤波,高斯滤波
  • Sobel

相邻算子的操作More neighborhood operators

形态学Morphology

  • 侵蚀erosion
  • 膨胀dilation
  • majority
  • opening:先做侵蚀,再做膨胀,在噪点较多的情况下,移除面积较小的噪点,同时保持目标的面积
  • closing:先做膨胀,再做侵蚀,某些情况下(如阈值较高,或原图像质量不好)去掉了较多实际应划归目标的像素,使得处理前应该是一整块的目标中间有断开的部分,先通过膨胀将断开的目标碎片连接起来,再通过侵蚀保持其外形大小

特征检测、匹配与对其Feature detection, matching and Feature-based alignment

  • 从图像中提取特征点,并通过特征点匹配两张图片/不同角度中的同一物体:特征与SLAM

图像分割Segmentation

常用的测量区域属性(measure properties of image regions)的方法

立体视觉的图像匹配

相似度的度量/模板匹配

Sum of Absolute Diffeerence (SAD)

  • 公式

Sum of Squared Differences (SSD)

  • 公式

Zero-mean SAD

  • 公式

Locally scaled SAD

  • 公式

Normalized Cross Correlation(NCC)

  • 公式