Python_多线程打开多相机

#!/usr/bin/python3
# -*- coding: utf-8 -*-

from dvp import *                                           #将对应的dvp.pyd或dvp.so及dll文件放入python安装目录下或工程目录
import numpy as np
import cv2
import threading

#线程类
class myThread (threading.Thread):
    def __init__(self, threadID, name, counter):
        threading.Thread.__init__(self)
        self.threadID = threadID
        self.name = name
        self.counter = counter
    def run(self):
        global cam_list
        global oldtime
        global exit_list

        frame=["",""]
        img=["",""]

        print ("开始线程:" + self.name)
        while (cv2.waitKey(1) != 27):                           #按ESC键则退出循环
            try:
                frame[self.threadID] = cam_list[self.threadID].GetFrame(3000)                   #从相机采集图像数据,超时时间为3000毫秒
                img[self.threadID] = frame2mat(frame[self.threadID])
            except dvpException as e:
                print("相机"+cam_list[self.threadID].UserId+"等待触发信号超时:", e.Status)
                if(e.Status == Status.DVP_STATUS_TIME_OUT):
                    continue                                    #如果只是超时错误,则继续采集
                break                                           #其他错误则中止采集

            cv2.imshow("Camera"+str(self.threadID), img[self.threadID])                         #显示图像数据
            cv2.namedWindow("Camera"+str(self.threadID),0)                        #可以拖动窗口大小
            cv2.resizeWindow("Camera"+str(self.threadID), 640, 480)               #设置窗口大小

        cam_list[self.threadID].Stop()                                           #停止视频流
        cam_list[self.threadID].Close()                                          #关闭相机
        exit_list[self.threadID]=True
        print ("退出线程:" + self.name)

#将帧信息转换为numpy的矩阵对象,后续可以通过opencv的cvtColor转换为特定的图像格式
def frame2mat(frameBuffer):
    frame, buffer = frameBuffer
    bits = np.uint8 if(frame.bits == Bits.BITS_8) else np.uint16
    shape = None
    convertType = None
    if(frame.format >= ImageFormat.FORMAT_MONO and frame.format <= ImageFormat.FORMAT_BAYER_RG):
        shape = 1
    elif(frame.format == ImageFormat.FORMAT_BGR24 or frame.format == ImageFormat.FORMAT_RGB24):
        shape = 3
    elif(frame.format == ImageFormat.FORMAT_BGR32 or frame.format == ImageFormat.FORMAT_RGB32):
        shape = 4
    else:
        return None

    mat = np.frombuffer(buffer, bits)
    mat = mat.reshape(frame.iHeight, frame.iWidth, shape)   #转换维度
    return mat

#主函数
def main():
    global cam_list
    global exit_list

    camera_info = Refresh();                                 #刷新并获取相机列表

    if(len(camera_info) == 0):                               #没有任何设备则退出
        print(u"没有找到设备")
        return None

    cam_list = []
    exit_list=[False,False]

    for k, v in enumerate(camera_info):                      #打印相机索引和名称
        print(k, "->", v.FriendlyName)
    
    for index in range(len(camera_info)):
        try:
            camera = Camera(index)                          #以索引号的方式打开相机
            cam_list.append(camera)
        except dvpException as e:
            print(u"打开相机失败:", e.Status)                #如果是DVP的标准异常
    
        try:
            cam_list[index].TriggerState = True                         #触发模式
            cam_list[index].Start()                                      #启动视频流

        except dvpException as e:
            print(u"操作相机出错:", e.Status)

    # 创建新线程
    thread1 = myThread(0, "采集线程1", 1)
    thread2 = myThread(1, "采集线程2", 2)

    # 开启新线程
    thread1.start()
    thread2.start()

    while(exit_list[0]==False or exit_list[1]==False):
        try:
            if(exit_list[0]==False):
                cam_list[0].TriggerFire=True
            if(exit_list[1]==False):
                cam_list[1].TriggerFire=True
        except BaseException:
            None

    cv2.destroyAllWindows()

#执行主函数
main()

用触发模式是因为连续模式太快了,全分辨率缩放成窗口分辨率的过程导致屏幕疯狂闪烁眼睛都要瞎了

Python_多线程打开多相机_第1张图片

你可能感兴趣的:(工业摄像机,Python,备忘剪贴板,python,opencv,开发语言)