OpenCV学习笔记-几何变换

一、扩展缩放

扩展缩放只是改变图像的大小。OpenCV提供函数cv.resize()实现这个功能。在缩放时推荐使用cv.INTER_AREA,在扩展时推荐使用cv.INTER_CUBIC(慢)和cv.INTER_LINEAR。

#扩展缩放
def resize_demo(img):
    #使用缩放因子
    res = cv.resize(img, None, fx=2, fy=2, interpolation=cv.INTER_CUBIC)
    cv.imshow('resize 2', res)

    height, width = img.shape[:2]
    #指定输出图像大小,输出图像的尺寸必须是整数
    res = cv.resize(img, (int(0.5 * width), int(0.5 * height)), interpolation=cv.INTER_AREA)
    cv.imshow('resize 0.5', res)


二、平移

平移就是将对象换一个位置。如果要沿(x, y)方向移动,移动的距离是(tx, ty),使用numpy构建一个2x3矩阵(数据类型是float32),
                M= [[1 0 tx]
                        [0 1 ty]] ,下面的例子被移动了(100,50)个像素
#平移
def translation_demo(img):
    trans = np.array([[1, 0, 100],
                      [0, 1, 50]], dtype=np.float32)
    dstImg = cv.warpAffine(img, M=trans, dsize=(img.shape[0], img.shape[1]), borderValue=(127, 127, 127))
    cv.imshow('dstimg', dstImg)


三、旋转

对一个图像旋转角度θ,需要使用到下面形式的旋转矩阵。
但是OpenCV允许在任意地方进行旋转,但是旋转矩阵应该修改为:
其中:α = scale * cosθ,β = scale * sinθ

#旋转
def rotate_demo(img):
    rows, cols = img.shape[:2]
    #getRotationMatrix2D(旋转中心,旋转角度, 旋转图像缩放大小)
    M = cv.getRotationMatrix2D((rows/2, cols/2), 45, 0.6)
    dst = cv.warpAffine(img, M, (cols, rows))
    cv.imshow('rotate', dst)

函数:getRotationMatrix2D(center, angle, scale),第一个参数是旋转中心,第二个为旋转角度,第三个为旋转后的图像的缩放因子。可以通过设置旋转中心,缩放因子,以及缩放因子来防止旋转后超出边界的问题。OpenCV中逆时针旋转,角度大小为正。

四、仿射变换

在仿射变换中, 原图中所有的平行线在结果图像中同样平行。为了创建这个矩阵我们需要在原图像中找到三个点,以及它们在输出图像中的位置,然后cv.getAffineTransform会创建一个2*3的矩阵,这个矩阵传给cv.warpAffine()得到旋转后的图像。

#仿射变换
def warpaffine_demo(img):
    rows, cols = img.shape[:2]
    #在原图像上的坐标
    pts1 = np.float32([[50,50],[200,50],[50,200]])
    #在输出图像上的坐标
    pts2 = np.float32([[10,100], [200, 50], [100, 250]])

    #会创建一个2x3的矩阵
    M = cv.getAffineTransform(pts1, pts2)
    dst = cv.warpAffine(img, M, (cols, rows))

    cv.imshow('dst', dst)

函数warpAffine(src, M, dsize, dst=None, flags=None, borderMode=None, borderValue=None),
src是输入图像,
M是2x3的变换矩阵,
dsize是输出图像指定尺寸,
flags:插值算法标识符,默认值为INTER_LINEAR

borderMode:边界像素模式,默认值为BORDER_CONSTANT
borderValue:边界取值,默认值为0

五、透视变换

对于透视变换,我们需要一个3*3变换矩阵。 在变换前后直线还是直线。要构建这个矩阵,需要在输入图像上找到4个点,以及它们在输出图像上对应的位置。这四个点中的任意三个不能共线。
#透视变换
def perspective_demo(img):
    rows, cols = img.shape[:2]
    #输入图像上的四个点,任意三个点不能共线
    pts1 = np.float32([[56, 65], [368, 52], [28, 387], [389, 390]])
    #输出图像上的四个点
    pts2 = np.float32([[0, 0], [300, 0], [0, 300], [300, 300]])

    M = cv.getPerspectiveTransform(pts1, pts2)
    print(M)
    dst = cv.warpPerspective(img, M, (300, 300))
    cv.imshow('perspective', dst)

猜你喜欢

转载自blog.csdn.net/qq_36387683/article/details/80538718
今日推荐