CV — 透视(投影)变换

2,126 阅读2分钟

CV — 透视(投影)变换

一、前言

(一) 透视变换概念

  1. 前言:

  2. 仿射变换原理:

    • 参考:

    • 透视变换定义(百度百科): 透视变换(Perspective Transformation)是指利用 透视中心、像点、目标点 三点共线的条件,按透视旋转定律使承影面(透视面)绕迹线(透视轴)旋转某一角度,破坏原有的投影光线束,仍能保持承影面上投影几何图形不变的变换。

      简而言之,就是将一个 平面(图片)通过一个 投影矩阵 投影到一个新的视平面(Viewing Plane),也称作投影映射。

      在这里插入图片描述

    • 透视变换公式推导: 在这里插入图片描述

      • (xo,yo)是原始图像坐标点,写成增广向量形式 [xo,yo, 1],(X, Y, Z)为透视变换之后的目标点(三维空间中),因为图像在二维空间中,故对目标点除以 Z,得到转化到 二维图像上 的点为(x', y', z'),其中:其中:x'= X/Z,y'= Y/Z, z'=1

        变换矩阵中, a11,a12,a21,a22 表示 线性变换, 主要用于图像的 缩放旋转 操作 a31,a32 表示平移, a13,a23 表示透视变换。 第四部分参数 a33等于1。

      • 仿射变换矩阵 一共有6个参数,所以我们只需要 3个坐标对(6个方程)就能求解,而 透视变换矩阵 一共有8个参数,所以需要 4个坐标对(8个方程)才能求解。

    • 总结:

      • 已知 变换对应的几个点 就可以求取变换公式。反之,特定的变换公式也能产生新的变换后的图片。
      • 仿射变换 也是 透视变换 的一种特殊形式
      • 根据原图和投影前后对应的 4 个坐标对,可以求出 透视变换矩阵,然后根据透视变换矩阵 可以对原图进行透视变换。

二、代码实现

(一) opencv 函数说明

1. warpPerspective

  1. def warpPerspective(src, M, dsize, dst=None, flags=None, borderMode=None, borderValue=None):

    • 解释: 透视变换函数,可保持直线不变形,但是平行线可能不再平行
    • 参数: 其相关参数和cv2.warpAffine函数的类似, 区别在于:M 为 3×3 的变换矩阵,矩阵前两行用于仿射变换,第三行用于透视变换。

2. 示例

  • 示例代码:

    import cv2
    import numpy as np
    ​
    def perspective(image):
        # 原图中的点的坐标 四个
        pts1 = np.float32([[56, 65], [250, 52], [28, 200], [280, 290]])
        # 变换到新图片中,四个点对应的新的坐标 一一对应
        pts2 = np.float32([[0, 0], [300, 0], [0, 250], [300, 250]])
    ​
        # 生成变换矩阵
        M = cv2.getPerspectiveTransform(pts1, pts2)
        # 进行透视变换
        dst = cv2.warpPerspective(image, M, (image.shape[1], image.shape[2]))
    ​
        return dst
    

参考资料