取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点

Python OpenCV 365 天学习计划,与橡皮擦一起进入图像领域吧。本篇博客是这个系列的第 55 篇。
该系列文章导航参考:https://blog.csdn.net/hihell/category_10688961.html

学在前面

正式学习之前,先将上一篇 博客的内容回顾一下,通过一系列的轮廓操作,得到了目标图像的轮廓。

取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点
本篇博客的目标将逐步实现对其进行透视变换。

获取轮廓的四个顶点坐标

上篇博客已经获取到了轮廓坐标,但是每个坐标对应的位置是不确定的,需要通过计算将其明确出来。
轮廓坐标从三维修改为二维

cv.drawContours(src, [screen_cnt], -1, (0, 0, 255), 2)

print(screen_cnt)
print(screen_cnt.shape)
print(screen_cnt.reshape(4, 2))

代码运行效果如下,图片不同得到的数值不同。

[[[ 30  94]]
 [[ 17 273]]
 [[469 278]]
 [[462 106]]]
(4, 1, 2)
[[ 30  94]
 [ 17 273]
 [469 278]
 [462 106]]

坐标转换之后,对应到图片的位置如下图所示。

取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点
一般情况下,我们描述一个矩形区域,在 OpenCV 中,采用的是 左上,右上,右下,左下 顺时针顺序,所以接下来需要对这四个坐标进行转换。

声明一个函数进行相应的计算工作。

def change_points(input_points):
	pass

# 函数调用
change_points(screen_cnt.reshape(4, 2))

计算 4 个点横纵坐标之和

def change_points(input_points):
    s = input_points.sum(axis=1)
    print(s)

核心用到的是 numpy 中的 sum 函数,注意 axis 轴参数,0 表示竖向,1 表示横向,这里的横向就是该点的横纵坐标之和。

取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点
取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点
对于一个矩形区域,左上点与右下点分别是横纵坐标之和最小的点与最大的点,基于此,继续完善代码。

下述代码使用了 np.argmin()np.argmax() 函数,可以通过搜索引擎进行快速学习。

def change_points(input_points):
    s = input_points.sum(axis=1)
    p1 = input_points[np.argmin(s)]
    p3 = input_points[np.argmax(s)]
    print(p1,p3)

得到的数据如下:

[[ 30  94]
 [ 17 273]
 [469 278]
 [462 106]]
[30 94] [469 278]

左下点与右上点的计算方式为,使用 np.diff() 函数,计算横纵坐标之差最小找到右上角的点,横纵坐标之差最大找到左下角的点。对应下图可以辅助理解,左下点 300-100 = 200,右上点 100-400 = -300

取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点

def change_points(input_points):
    s = input_points.sum(axis=1)
    p1 = input_points[np.argmin(s)]
    p3 = input_points[np.argmax(s)]
    print(p1,p3)

    diff = np.diff(input_points,axis=1)
    p2 = input_points[np.argmin(diff)]
    p4 = input_points[np.argmax(diff)]
    print(p2,p4)

此时,4 个坐标都已经获取到,最后声明一个空矩阵,赋值之后进行返回。

def change_points(input_points):
    s = input_points.sum(axis=1)
    p1 = input_points[np.argmin(s)]
    p3 = input_points[np.argmax(s)]

    diff = np.diff(input_points, axis=1)
    p2 = input_points[np.argmin(diff)]
    p4 = input_points[np.argmax(diff)]

    # 声明一个所有元素都为 0 的矩阵
    rect = np.zeros((4, 2), dtype="float32")
    rect[0] = p1
    rect[1] = p2
    rect[2] = p3
    rect[3] = p4
    print(rect)
    return rect
change_points(screen_cnt.reshape(4, 2))

坐标数值与图片对应位置如下:
取经之旅第 55 天,Python OpenCV 透视变换前置知识轮廓坐标点

橡皮擦的小节

希望今天的 1 个小时(貌似不太够)你有所收获,我们下篇博客见~

相关阅读

  1. Python 爬虫 100 例教程,超棒的爬虫教程,立即订阅吧
  2. Python 游戏世界(更新中,目标文章数 50+,现在订阅,都是老粉)
  3. Python 爬虫小课,精彩 9 讲

今天是持续写作的第 115 / 200 天。
如果你想跟博主建立亲密关系,可以关注同名公众号 梦想橡皮擦,近距离接触一个逗趣的互联网高级网虫。
博主 ID:梦想橡皮擦,希望大家点赞评论收藏

评论 15
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

梦想橡皮擦

如有帮助,来瓶可乐

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值