小白的opencv学习笔记

OpenCV

序章

介绍

OpenCV是计算机视觉中经典的专用库,其支持多语言、跨平台,功能强大。 OpenCV-Python为OpenCV提供了Python接口,使得使用者在Python中能够调用C/C++,在保证易读性和运行效率的前提下,实现所需的功能。 OpenCV-Python Tutorials是官方提供的文档,其内容全面、简单易懂,使得初学者能够快速上手使用。

  • OpenCV-Python
    • OpenCV-Python是旨在解决计算机视觉问题的Python专用库。
    • 与C/C++之类的语言相比,Python速度较慢。也就是说,可以使用C/C++轻松扩展Python,这使我们能够用C/C++编写计算密集型代码并创建可用作Python模块的Python包装器。这给我们带来了两个好处:首先,代码与原始C/C++代码一样快(因为它是在后台运行的实际C++代码),其次,在Python中比C/C++编写代码更容易。OpenCV-Python是原始OpenCV C++实现的Python包装器。
    • OpenCV-Py利用了Numpy。所有OpenCV数组结构都与Numpy数组相互转换。这也使与使用Numpy的其他库(例如SciPy和Matplotlib)的集成变得更加容易。

安装

anaconda新建环境,pip install numpy,openCV-python,matploylib

然后在pycharm中为该解释器添加cv2路径,方便代码补全

图像入门

imread

  • 功能

    读取图像

  • 参数

    • 图像的完整路径或者相对路径
    • 读取图像的方式
      • cv.IMREAD_COLOR:加载彩色图像。任何图像的透明度都会被忽视。它是默认标志。
      • cv.IMREAD_GRAYSCALE:以灰度模式加载图像
      • cv.IMREAD_UNCHANGED:加载图像,包括alpha通道

注意:除了这三个标志,你可以分别简单地传递整数1、0或-1。

  • example
import numpy as np
import cv2
img = cv2.imread('路径',参数)
  • 注意

    即使图像路径错误,它也不会引发任何错误,但是 print img 会给出 None

imshow

  • 功能

    显示图像,窗口自动适合图像尺寸

  • 参数

    第一个参数是窗口名称,它是一个字符串。第二个参数是我们的对象。你可以根据需要创建任意多个窗口,但可以使用不同的窗口名称。

  • example

    cv.imshow('image',img)
    cv.waitKey(0)
    cv.destroyAllWindows()
    
  • waitkey

    一个键盘绑定函数。其参数是以毫秒为单位的时间。该函数等待任何键盘事件指定

    的毫秒。如果在这段时间内按下任何键,程序将继续运行。如果0被传递,它将无限期地等

    待一次敲击键。

  • destroyAllWindows

    只会破坏我们创建的所有窗口。如果要销毁任何特定的窗口,请使用函数cv.destroyWindow()在其中传递确切的窗口名称作为参数。

注意 在特殊情况下,你可以创建一个空窗口,然后再将图像加载到该窗口。在这种情况下,你可以指定窗口是否可调整大小。这是通过功能cv.namedWindow()完成的。默认情况下,该标志为cv.WINDOW_AUTOSIZE。但是,如果将标志指定为cv.WINDOW_NORMAL,则可以调整窗口大小。当图像尺寸过大以及向窗口添加跟踪栏时,这将很有帮助。

cv.namedWindow('image',cv.WINDOW_NORMAL)
cv.imshow('image',img)
cv.waitKey(0)
cv.destroyAllWindows()

imwrite

  • 功能

    保存图像

  • 参数

    第一个参数是文件名,第二个参数是要保存的图像。 cv.imwrite(‘messigray.png’,img)

    保存格式:PNG

  • example

    import numpy as np
    import cv2 as cv
    img = cv.imread('messi5.jpg',0)
    cv.imshow('image',img)
    k = cv.waitKey(0)
    if k == 27: # 等待ESC退出
     cv.destroyAllWindows()
    elif k == ord('s'): # 等待关键字,保存和退出
     cv.imwrite('messigray.png',img)
     cv.destroyAllWindows()
    
  • 警告

    如果使用的是64位计算机,则必须 k = cv.waitKey(0) 按如下所示修改行: k = cv.waitKey(0) & 0xFF

使用matplotlib

  • 介绍

    绘图库,有多种绘图方法

  • example

    import numpy as np
    import cv2 as cv
    from matplotlib import pyplot as plt
    img = cv.imread('messi5.jpg',0)
    plt.imshow(img, cmap = 'gray', interpolation = 'bicubic')
    plt.xticks([]), plt.yticks([]) # 隐藏 x 轴和 y 轴上的刻度值
    plt.show()
    
  • 警告

    OpenCV加载的彩色图像处于BGR模式。但是Matplotlib以RGB模式显示。因此,如果使用OpenCV读取彩色图像,则Matplotlib中将无法正确显示彩色图像。

  • 参考链接

    [Matplotlib绘图样式及其功能](pyplot — Matplotlib 2.0.2 documentation)

    Matplotlib使用教程(保姆级说明教程) - 知乎 (zhihu.com)

VideoCapture

  • 功能1

    从相机中读取视频

  • 步骤

    创建一个 VideoCapture 对象。它的参数可以是设备索引或视频文件的名称。设备索引就是指定哪个摄像头的数字。正常情况下,一个摄像头会被连接。所以我简单地传0(或-1)。你可以通过传递1来选择第二个相机,以此类推。

  • example

    import numpy as np
    import cv2 as cv
    cap = cv.VideoCapture(0)
    if not cap.isOpened():
     print("Cannot open camera")
     exit()
    while True:
     # 逐帧捕获
     ret, frame = cap.read()
     # 如果正确读取帧,ret为True
     if not ret:
     print("Can't receive frame (stream end?). Exiting ...")
     break
        # 我们在框架上的操作到这里
     gray = cv.cvtColor(frame, cv.COLOR_BGR2GRAY)
     # 显示结果帧e
     cv.imshow('frame', gray)
     if cv.waitKey(1) == ord('q'):
     break
    # 完成所有操作后,释放捕获器
    cap.release()
    cv.destroyAllWindows()
    
  • cap.read() 返回布尔值( True / False )。如果正确读取了帧,它将为 True 。因此,你可以通过检查此返回值来检查视频的结尾。

  • 通过cap.isOpened()方法检查cap是否已初始化。如果是 True ,那么确定。否则,使用cap.open()打开它

  • 还可以使用 cap.get(propId) 方法访问该视频的某些功能,其中propId是0到18之间的一个数字。每个数字表示视频的属性(如果适用于该视频),并且可以显示完整的详细信息在这里看到:cv::VideoCapture::get()。其中一些值可以使用 cap.set(propId,value) 进行修改。value是你想要的新值

  • 例如,我可以通过 cap.get(cv.CAP_PROP_FRAME_WIDTH) 和 cap.get(cv.CAP_PROP_FRAME_HEIGHT)检查框架的宽度和高度。默认情况下,它的分辨率为640x480。但我想将其修改为320x240。只需使用和即可。 ret = cap.set(cv.CAP_PROP_FRAME_WIDTH,320) and ret =cap.set(cv.CAP_PROP_FRAME_HEIGHT,240) .

  • 功能2

    播放视频。与从相机捕获相同,只是用视频文件名更改摄像机索引。另外,在显示框架时,请使用适当的时间 cv.waitKey() 。如果太小,则视频将非常快,而如果太大,则视频将变得很慢(这就是显示慢动作的方式)。正常情况下25毫秒就可以了。

  • example

    import numpy as np
    import cv2 as cv
    cap = cv.VideoCapture('vtest.avi')
    while cap.isOpened():
        ret, frame = cap.read()
     # 如果正确读取帧,ret为True
     	if not ret:
     	print("Can't receive frame (stream end?). Exiting ...")
     	break
     	gray = cv.cvtColor(frame, cv.COLOR_BGR2GRAY)
     	cv.imshow('frame', gray)
     	if cv.waitKey(1) == ord('q'):
     	break
    cap.release()
    cv.destroyAllWindows()
    

注意 确保安装了正确的 ffmpeg 或 gstreamer 版本。有时,使用视频捕获(Video Capture)是一件令人头疼的事情,主要原因是错误地安装了 ffmpeg / gstreamer。

VideoWriter

  • 功能

    保存视频。

    该类四个参数:

    • 指定输出文件名(例如: output.avi)。
    • 指定 FourCC 代码(详见下一段)。
    • 传递帧率的数量和帧大小
    • 颜色标志。如果为True ,编码器期望颜色帧,否则它与灰度帧一起工作。
  • 使用

    FourCC代码作为MJPG的cv.VideoWriter_fourcc(‘M’,‘J’,‘P’,‘G’) or cv.VideoWriter_fourcc(*‘MJPG’)

    类似的可以解码XVID等

  • example

    cap = cv.VideoCapture(0)
    # 定义编解码器并创建VideoWriter对象
    fourcc = cv.VideoWriter_fourcc(*'XVID')
    out = cv.VideoWriter('output.avi', fourcc, 20.0, (640, 480))
    while cap.isOpened():
     ret, frame = cap.read()
     if not ret:
     print("Can't receive frame (stream end?). Exiting ...")
     break
     frame = cv.flip(frame, 0)
     # 写翻转的框架
     out.write(frame)
     cv.imshow('frame', frame)
     if cv.waitKey(1) == ord('q'):
     break
    # 完成工作后释放所有内容
    cap.release()
    out.release()
    cv.destroyAllWindows()
    
  • 参考资料

    FourCC:FourCC - 维基百科 (wikipedia.org)用于指定视频编解码器的4字节代码

    可用代码列表可在fourcc.org中:http://www.fourcc.org/codecs.php 找到

    Windows:DIVX

    在OSX中:MJPG(.mp4),DIVX(.avi),X264(.mkv)

OpenCV中的绘图功能

常见参数

  • img:您要绘制形状的图像

  • color:形状的颜色。对于BGR,将其作为元组传递,例如:(255,0,0)对于蓝色。对于灰度,只需传递标量值即可。

  • 厚度:线或圆等的粗细。如果对闭合图形(如圆)传递 -1 ,它将填充形状。默认厚度*= 1*

  • lineType:线的类型,是否为8连接线,抗锯齿线等。默认情况下,为8连接线。cv.LINE_AA给出了抗锯齿的线条,看起来非常适合曲线。

line

  • 参数

    传递线的开始和结束坐标

  • example

    # 创建黑色的图像
    img = np.zeros((512,512,3), np.uint8)
    # 绘制一条厚度为5的蓝色对角线
    cv.line(img,(0,0),(511,511),(255,0,0),5)
    

rectangle

  • 参数

    矩形的左上角和右下角

  • cv.rectangle(img,(384,0),(510,128),(0,255,0),3)

circle

  • 参数

    中心坐标和半径

  • cv.circle(img,(447,63), 63, (0,0,255), -1)

ellipse

  • 参数

    • 中心位置(x,y)
    • 轴长度(长轴,短轴)
    • angle是椭圆逆时针方向旋转的角度
    • startAngle和endAngle表示从主轴沿顺时针方向测量的椭圆弧的开始和结束。即给出0和360给出完整的椭圆
  • 使用

    def ellipse(img: Any,
    center: Any,
    axes: Any,
    angle: Any,
    startAngle: Any,
    endAngle: Any,
    color: Any,
    thickness: Any = None,
    lineType: Any = None,
    shift: Any = None) -> None

  • cv.ellipse(img,(256,256),(100,50),0,0,180,255,-1)

polylines

  • 参数

    首先需要顶点的坐标。将这些点组成形状为 ROWSx1x2 的数组,其中 ROWS 是顶点

    数,并且其类型应为int32。

  • example

    pts = np.array([[10,5],[20,30],[70,20],[50,10]], np.int32)
    pts = pts.reshape((-1,1,2))
    cv.polylines(img,[pts],True,(0,255,255))
    

注意 如果第三个参数为False,您将获得一条连接所有点的折线,而不是闭合形状。

cv.polylines()可用于绘制多条线。只需创建要绘制的所有线条的列表,然后将其传递给函数即可。所有线条将单独绘制。与为每条线调用cv.line相比,绘制一组线是一种更好,更快的方法

向图像添加文本

  • 参数

    • 要写入的文字数据
    • 放置它的位置坐标(数据开始的左下角)
    • 字体类型(检查cv.putText文档以获取受支持的字体)
    • 字体比例(指定字体大小)
    • 常规的内容(如颜色、厚度、线条类型)为了获得更好的外观,建议使用lineType = cv.LINE_AA
  • example

    font = cv.FONT_HERSHEY_SIMPLEX
    cv.putText(img,'OpenCV',(10,500), font, 4,(255,255,255),2,cv.LINE_AA)
    
  • 参考资料

    椭圆函数中使用的角度不是我们的圆角。有关更多详细信息,请访问此讨论:http://answers.opencv.org/question/14541/angles-in-ellipse-function/

鼠标作为画笔

setMouseCallback

  • 参数

    窗口名字,鼠标回调函数名称

  • 简单演示

    功能:双击画圆

    思路:创建一个鼠标回调函数,该函数在发生鼠标事件时执行。鼠标事件可以是与鼠标相关的任何事物,例如左键按下,左键按下,左键双击等。它为我们提供了每个鼠标事件的坐标(x,y)。通过此活动和地点,我们可以做任何我们喜欢的事情。

    鼠标回调函数格式:def mouse_callback(event, x, y, flags, param)

    • 查看所有可用事件:
    import cv2 as cv
    events = [i for i in dir(cv) if 'EVENT' in i]
    print( events )
    
    • 创建鼠标回调函数具有特定的格式,该格式在所有地方都相同。它仅在功能上有所不同。按ESC键关闭窗口。

      import cv2 as cv
      # 鼠标回调函数
      def draw_circle(event,x,y,flags,param):
       if event == cv.EVENT_LBUTTONDBLCLK:
       cv.circle(img,(x,y),100,(255,0,0),-1)
      # 创建一个黑色的图像,一个窗口,并绑定到窗口的功能
      img = np.zeros((512,512,3), np.uint8)
      cv.namedWindow('image')
      cv.setMouseCallback('image',draw_circle)
      while(1):
       cv.imshow('image',img)
       if cv.waitKey(20) & 0xFF == 27:
       break
      cv.destroyAllWindows()
      

      结果:
      在这里插入图片描述

  • 更高级的演示

    功能:拖动鼠标来绘制矩形或圆形。我们的鼠标回调函数有两部分,一部分用于绘制矩形,另一部分用于绘制圆形。这个具体的例子对于创建和理解一些交互式应用程序非常有帮助,比如目标跟踪,图像分割地图等等。

    import numpy as np
    import cv2 as cv
    drawing = False # 如果按下鼠标,则为真
    mode = True # 如果为真,绘制矩形。按 m 键可以切换到曲线
    ix,iy = -1,-1
    # 鼠标回调函数
    def draw_circle(event,x,y,flags,param):
     global ix,iy,drawing,mode
     if event == cv.EVENT_LBUTTONDOWN:
     drawing = True
     ix,iy = x,y
     elif event == cv.EVENT_MOUSEMOVE:
     if drawing == True:
     if mode == True:
     cv.rectangle(img,(ix,iy),(x,y),(0,255,0),-1)
     else:
     cv.circle(img,(x,y),5,(0,0,255),-1)
     elif event == cv.EVENT_LBUTTONUP:
     drawing = False
     if mode == True:
     cv.rectangle(img,(ix,iy),(x,y),(0,255,0),-1)
     else:
     cv.circle(img,(x,y),5,(0,0,255),-1)
    
  • 练习:修改代码以绘制一个未填充的矩形

    • 代码:
img = np.zeros((512, 512, 3), np.uint8)

is_mouse = False  # 判断是否按下鼠标
mode = True  # 真则绘制矩形
ix, iy = -1, -1

# 鼠标回调函数
def draw_circle(event, x, y, flags, param):
    global ix, iy, is_mouse, mode
    if event == cv.EVENT_LBUTTONDOWN:
        # 按下左键
        is_mouse = True
        ix, iy = x, y
    elif event == cv.EVENT_MOUSEMOVE:
        if is_mouse:
            # 如果已经按定鼠标了
            if mode:
                pass
            else:
                cv.circle(img, (x, y), 5, (0, 0, 255), -1)
    elif event == cv.EVENT_LBUTTONUP:
        # 松开鼠标左键
        is_mouse = False
        if mode:
            cv.rectangle(img, (ix, iy), (x, y), (0, 255, 0), 4)
        else:
            cv.circle(img,(x,y), 5,(0,0,255), -1)

cv.namedWindow('image')
cv.setMouseCallback('image', draw_circle)
while 1:
    cv.imshow('image', img)
    smile = cv.waitKey(20) & 0xff
    if smile == 27:
        # esc
        break
    elif smile == 109:
        # 'm'切换模式
        mode = (mode + 1) % 2
cv.destroyAllWindows()
  • 结果
    在这里插入图片描述
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
根据提供的引用内容,OpenCV一个开源计算机视觉和机器学习软件库,用于开发图像和视频处理应用程序。通过使用OpenCV,您可以读取摄像头并显示实图像,打开视频文件或摄像头文件,并获取视频的相关信息,例如帧宽度、帧高度、帧率和总帧数。 对于学习OpenCV,你可以按照以下步骤进行: 1. 安装OpenCV库:在开始学习OpenCV之前,您需要从OpenCV官方网站下载和安装OpenCV库。根据您的操作系统和编程语言选择合适的版本。 2. 学习基本概念:熟悉OpenCV的基本概念和术语,例如图像和视频的加载、显示、保存以及常用的图像处理操作,如滤波、边缘检测和特征提取等。 3. 掌握OpenCV函数和类:深入了解OpenCV提供的函数和类,例如cv::Mat用于图像和矩阵操作,cv::VideoCapture用于读取和处理视频,以及cv::imshow和cv::waitKey等用于显示图像的函数。 4. 实践项目:通过完成一些实践项目来应用您所学到的知识。例如,利用OpenCV实现人脸检测、目标追踪、图像识别等。 5. 学习资料和资源:查找和阅读OpenCV的官方文档、教程和示例代码,参与开源社区讨论和交流,加入相关的论坛和邮件列表等。 总结起来,学习OpenCV包括安装OpenCV库、学习基本概念、掌握OpenCV函数和类、实践项目以及查找和阅读相关资料和资源。通过不断实践和学习,您将能够更好地理解和应用OpenCV库来开发图像和视频处理应用程序。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值