博客列表 >OpenCV中的图像处理 —— 改变颜色空间+图像几何变换

OpenCV中的图像处理 —— 改变颜色空间+图像几何变换

P粉962186587
P粉962186587原创
2022年03月20日 14:04:17552浏览

这一部分主要介绍OpenCV图像处理中的改变颜色空间和图像的几何变换,颜色空间的改变应用非常广泛,在处理图像的实际问题中,经常需要要图像变换为单通道灰度图像等形式操作,在文中会有一个追踪颜色的小实例便于理解,图像的几何变换是老生常谈的东西了,但是在图像处理中有一些新的概念,例如仿射变换和透视变换,废话不多说直接开干!

目录

  1. 改变颜色空间
    关于颜色空间的改变我们要掌握两个重要的功能函数:cv.cvtColor 和 cv.inRange

1.1 改变颜色空间
OpenCV中有超150中颜色空间转换方法,但是我们只掌握应用最广泛的两种即可:

BGR <-> 灰度 和 BGR <-> HSV

颜色转换的函数cv.cvtColor()非常简单,往其中传入两个参数即可吗,第一个参数是我们的图像对象,第二个参数代表我们要转换称为的类型标志

对于BGR→灰度转换,我们使用标志cv.COLOR_BGR2GRAY。类似地,对于BGR→HSV,我们使用标志cv.COLOR_BGR2HSV

要获取其他标志只需要在python终端把库中的标志名全部输出即可查看

  1. >>>import cv2 as cv
  2. >>> flags =[i for i indir(cv)if i.startswith('COLOR_')]>>>print( flags )

1.2 颜色对象追踪
我们通过一个实例来展示颜色对象追踪,其本质上就是在显示的视频中只显示我们要求的颜色,以达到追踪颜色的效果

在HSV中比在BGR中更容易显示颜色

代码实现

  1. import cv2 as cv
  2. import numpy as np
  3. cap = cv.VideoCapture(0)while(1):# 读取帧
  4. _, frame = cap.read()# 转换颜色空间 BGR HSV
  5. hsv = cv.cvtColor(frame, cv.COLOR_BGR2HSV)# 定义HSV中蓝色的范围
  6. lower_blue = np.array([110,50,50])
  7. upper_blue = np.array([130,255,255])# 设置HSV的阈值使得只取蓝色
  8. mask = cv.inRange(hsv, lower_blue, upper_blue)# 将掩膜和图像逐像素相加
  9. res = cv.bitwise_and(frame,frame, mask= mask)
  10. cv.imshow('frame',frame)
  11. cv.imshow('mask',mask)
  12. cv.imshow('res',res)
  13. k = cv.waitKey(5)&0xFFif k ==27:break
  14. cv.destroyAllWindows()

首先我们创建了一个VideoCapture对象用来捕获视频,再通过while来逐帧读取视频,在读取视频的过程中因为我们要单独筛出蓝色,所以还需要一些列操作

HSV比BGR更容易显示颜色,为了显示效果能够更好所有我们选择使用HSV的图像,这个过程用cv.cvtColor()将BGR转换为HSV,在代码中有一个很重要的函数cv.inRange()函数,这个函数就用来筛选处于给定像素区间的图像,其中有三个参数,第一个便是当前“帧”,第二第三个参数就是给定的像素区间了

这里还有一个很重要的函数cv.bitwise_and(),这个函数主要有两个用途:

提取掩膜选定的区域:cv.bitwise_and(img1,img2,mask = mask)
首先我们要知道我们是掩膜mask,我们在处理一些图像时,需要选定我们要处理的部分,我们怎么确定这一块儿部分呢?那就是用一块儿掩膜mask来遮住这一块儿区域

求两种图片的交集:cv.bitwise_and(img1,img2)
这个用法就很简单了,传入的两个参数就是两个图像对象,返回的结果就是这两个图像的交集

  1. 图像几何变换
    对于OpenCV的图像几何变换,其提供了两个转换函数:cv.warpAffine()和cv.warpPerspective()

cv.warpAffine采用2x3转换矩阵,而cv.warpPerspective采用3x3转换矩阵作为输入

2.1 缩放
图像的缩放我们可以通过cv.resize()没错就是重置图像的大小,这里有两个插值方式值得注意,一个是cv.INTER_AREA用于缩小,另一个是cv.INTER_CUBIC用于缩放

  1. import numpy as np
  2. import cv2 as cv
  3. img = cv.imread('messi5.jpg')
  4. res = cv.resize(img,None,fx=2, fy=2, interpolation = cv.INTER_CUBIC)#或者
  5. height, width = img.shape[:2]
  6. res = cv.resize(img,(2*width,2*height), interpolation = cv.INTER_CUBIC)

2.2 平移
图像的平移我们通过创建转换矩阵M来完成,并且需要使用函数cv.wrapAffine()

我们把转换矩阵放入np.float32类型的Numpy数组中,并将其传递给cv.wrapAffine()函数

  1. import numpy as np
  2. import cv2 as cv
  3. img = cv.imread('messi5.jpg',0)
  4. rows,cols = img.shape
  5. M = np.float32([[1,0,100],[0,1,50]])
  6. dst = cv.warpAffine(img,M,(cols,rows))
  7. cv.imshow('img',dst)
  8. cv.waitKey(0)
  9. cv.destroyAllWindows()

cv.wrapAffine()函数的参数:第一个为显示的图像,第二个是转换矩阵,第三个是图像的尺寸

2.3 旋转
图像的旋转同样需要一个转换矩阵,这个转换矩阵我们通过cv.getRotationMatrix2D()这个函数来得到,其中需要传递三个参数,第一个参数是旋转位置的坐标,它通过一个二元组来传递,第二个参数是旋转角度吗,第三个参数是用来做调整的参数,如果传入1,则按照正常的逆时针旋转,如果传入0则不会显示图片,如果传入-1会显示顺时针旋转的结果

  1. import numpy as np
  2. import cv2 as cv
  3. # cols-1 rows-1 是坐标限制
  4. img = cv.imread(r'E:\image\wqw.png',0)
  5. rows, cols = img.shape
  6. M = cv.getRotationMatrix2D(((cols -1)/2.0,(rows -1)/2.0),90,1)
  7. dst = cv.warpAffine(img, M,(cols, rows))
  8. cv.imshow('img', dst)
  9. cv.waitKey(0)
  10. cv.destroyAllWindows()

2.4 仿射变换
还记得我们在上面说的另一个函数cv.getAffineTransform吗?现在我们要开始使用它了

在仿射变换中,原始图像中的所有平行线在输出图像中仍将平行,为了找到变换矩阵,我们需要输入图像中的三个点的位置,然后使用cv.getAffineTransform()函数创建一个2*3的矩阵,再将其传入cv.wrapAffine()完成仿射变换

  1. img = cv.imread('drawing.png')
  2. rows,cols,ch = img.shape
  3. pts1 = np.float32([[50,50],[200,50],[50,200]])
  4. pts2 = np.float32([[10,100],[200,50],[100,250]])
  5. M = cv.getAffineTransform(pts1,pts2)
  6. dst = cv.warpAffine(img,M,(cols,rows))
  7. plt.subplot(121),plt.imshow(img),plt.title('Input')
  8. plt.subplot(122),plt.imshow(dst),plt.title('Output')

(注:文章内容参考OpenCV4.1中文官方文档)
如果文章对您有所帮助,记得一键三连支持一下哦

声明:本文内容转载自脚本之家,由网友自发贡献,版权归原作者所有,如您发现涉嫌抄袭侵权,请联系admin@php.cn 核实处理。
全部评论
文明上网理性发言,请遵守新闻评论服务协议