python+OpenCV笔记(二十八):显示与捕捉摄像头帧

一、在窗口中显示摄像头帧

        摄像头帧流也可以用VideoCapture对象来表示。但是,对于摄像头,我们通过传递摄像头设备索引(而不是视频文件名称)来构造VideoCapture对象。

        OpenCV允许使用namedWindow、imshow和destroyWindow函数来创建、重新绘制和注销指定的窗口。此外,任何窗口都可以通过waitKey函数捕获键盘输入,通过setMouseCallBack函数捕获鼠标输入。

代码编写

import cv2 as cv

clicked = False


def onMouse(event, x, y, flags, param):
    global clicked
    if event == cv.EVENT_LBUTTONUP:
        clicked = True


cameraCapture = cv.VideoCapture(0)
cv.namedWindow("Camera")
cv.setMouseCallback("Camera", onMouse)

success, frame = cameraCapture.read()
while success and cv.waitKey(1) == -1 and not clicked:
    cv.putText(frame, "Click Window or press any key to stop!",
               (0, 450), cv.FONT_HERSHEY_COMPLEX, 0.7, (255, 0, 0))
    cv.imshow("Camera", frame)
    success, frame = cameraCapture.read()

cv.destroyWindow("Camera")
cameraCapture.release()

传递给setMouseCallBack的鼠标回调应有5个参数,如代码示例所示,把回调的param参数设置为setMouseCallBack的第三个可选参数,默认情况下为0.

回调的事件参数是以下操作之一:

  • cv2_EVENT_MOUSEMOVE   滑动 
    cv2_EVENT_LBUTTONDOWN   左键点击 
    cv2_EVENT_RBUTTONDOWN   右键点击 
    cv2_EVENT_MBUTTONDOWN   中间点击 
    cv2_EVENT_LBUTTONUP   左键释放 
    cv2_EVENT_RBUTTONUP   右键释放 
    cv2_EVENT_MBUTTONUP   中间释放 
    cv2_EVENT_LBUTTONDBLCLK   左键双击 
    cv2_EVENT_RBUTTONDBLCLK   右键双击 
    cv2_EVENT_MBUTTONDBLCLK   中间释放
    鼠标回调的flag参数可能是以下事件的一些按位组合:
    cv2_EVENT_FLAG_LBUTTON   左键拖拽  
    cv2_EVENT_FLAG_RBUTTON   右键拖拽  
    cv2_EVENT_FLAG_MBUTTON   中间拖拽  
    cv2_EVENT_FLAG_CTRLKEY   按Ctrl不放事件  
    cv2_EVENT_FLAG_SHIFTKEY  按Shift不放事件  
    cv2_EVENT_FLAG_ALTKEY  按Alt不放事件

二、捕捉摄像头帧

下面我们从摄像头抓取10秒的视频,并将其写入AVI文件

代码编写

import cv2 as cv

camera_number = 0
cameraCapture = cv.VideoCapture(camera_number + cv.CAP_DSHOW)
fps = 30
size = (int(cameraCapture.get(cv.CAP_PROP_FRAME_WIDTH)),
        int(cameraCapture.get(cv.CAP_PROP_FRAME_HEIGHT)))
out = cv.VideoWriter("E:\\MyOutput001.avi", cv.VideoWriter_fourcc('D', 'I', 'V', 'X'),
                     fps, size)

success, frame = cameraCapture.read()
numFrameRemaining = 10 * fps - 1  # 10秒
while success and cv.waitKey(1) and numFrameRemaining > 0:
    out.write(frame)
    success, frame = cameraCapture.read()
    cv.imshow("camera", frame)
    numFrameRemaining -= 1
    if numFrameRemaining == 0:
        print("保存成功!!!")

cameraCapture.release()
out.release()
cv.destroyAllWindows()

OpenCV不提供任何查询摄像头数量或者摄像头属性的方法,如果用无效的索引构造VideoCapture类,VideoCapture类将不会产生任何帧,它的read方法返回(False,None),要试图避免从未正确打开的VideoCapture对象检索帧。

当我们需要同步一组摄像头或者多摄像头相机(如立体摄像机)时,read 方法是不合适的。我们可以改用 grab 和 retrieve 方法。对于一组(两台)摄像机,可以使用类似下面的代码:

success0 = cameraCapture.grab()
success1 = cameraCapture.grab()
if success0 and success1:
    frame0 = cameraCapture.retrieve()
    frame1 = cameraCapture.retrieve()

猜你喜欢

转载自blog.csdn.net/qq_45832961/article/details/122722869
今日推荐