最终效果图: 注意一点:在窗口初始化中建立yolov3模型并进行相应的初始化,直接将预测处理的函数加到槽函数中。不这样做,会使得检测速度十分的慢。 代码如下:
import sys from PyQt5 import QtCore, QtGui, QtWidgets from PyQt5.QtWidgets import * from pyqt5.yolov3.util import * import torch import time from pyqt5.yolov3.cam_demo import write, prep_image, arg_parse from pyqt5.yolov3.darknet import Darknet from pyqt5.yolov3.preprocess import prep_image class Ui_MainWindow(object): def setupUi(self, MainWindow): MainWindow.setObjectName("MainWindow") MainWindow.resize(1042, 921) self.centralwidget = QtWidgets.QWidget(MainWindow) self.centralwidget.setObjectName("centralwidget") # 显示摄像头画面 self.cam_frame = QtWidgets.QFrame(self.centralwidget) self.cam_frame.setGeometry(QtCore.QRect(10, 110, 521, 571)) self.cam_frame.setFrameShape(QtWidgets.QFrame.StyledPanel) self.cam_frame.setFrameShadow(QtWidgets.QFrame.Raised) self.cam_frame.setObjectName("cam_frame") self.label_img_show = QtWidgets.QLabel(self.cam_frame) self.label_img_show.setGeometry(QtCore.QRect(10, 10, 501, 551)) self.label_img_show.setObjectName("label_img_show") # self.label_img_show.setStyleSheet(("border:2px solid red")) # 显示检测画面 self.detect_frame = QtWidgets.QFrame(self.centralwidget) self.detect_frame.setGeometry(QtCore.QRect(540, 110, 491, 571)) self.detect_frame.setFrameShape(QtWidgets.QFrame.StyledPanel) self.detect_frame.setFrameShadow(QtWidgets.QFrame.Raised) self.detect_frame.setObjectName("detect_frame") self.label_detect_show = QtWidgets.QLabel(self.detect_frame) self.label_detect_show.setGeometry(QtCore.QRect(10, 10, 481, 551)) self.label_detect_show.setObjectName("label_detect_show") # self.label_detect_show.setStyleSheet(("border:2px solid green")) # 按钮框架 self.btn_frame = QtWidgets.QFrame(self.centralwidget) self.btn_frame.setGeometry(QtCore.QRect(10, 20, 1021, 80)) self.btn_frame.setFrameShape(QtWidgets.QFrame.StyledPanel) self.btn_frame.setFrameShadow(QtWidgets.QFrame.Raised) self.btn_frame.setObjectName("frame_3") # 按钮水平布局 self.widget = QtWidgets.QWidget(self.btn_frame) self.widget.setGeometry(QtCore.QRect(20, 10, 501, 60)) self.widget.setObjectName("widget") self.horizontalLayout = QtWidgets.QHBoxLayout(self.widget) self.horizontalLayout.setContentsMargins(0, 20, 20, 20) self.horizontalLayout.setSpacing(20) self.horizontalLayout.setObjectName("horizontalLayout") # 打开摄像头 self.btn_opencam = QtWidgets.QPushButton(self.widget) self.btn_opencam.setObjectName("btn_opencam") self.horizontalLayout.addWidget(self.btn_opencam) # 加载模型文件 self.btn_model_add_file = QtWidgets.QPushButton(self.widget) self.btn_model_add_file.setObjectName("btn_model_add_file") self.horizontalLayout.addWidget(self.btn_model_add_file) # 加载cfg文件 self.btn_cfg_add_file = QtWidgets.QPushButton(self.widget) self.btn_cfg_add_file.setObjectName("btn_cfg_add_file") self.horizontalLayout.addWidget(self.btn_cfg_add_file) # 开始检测 self.btn_detect = QtWidgets.QPushButton(self.widget) self.btn_detect.setObjectName("btn_detect") self.horizontalLayout.addWidget(self.btn_detect) # 退出 self.btn_exit = QtWidgets.QPushButton(self.widget) self.btn_exit.setObjectName("btn_exit") self.horizontalLayout.addWidget(self.btn_exit) MainWindow.setCentralWidget(self.centralwidget) self.menubar = QtWidgets.QMenuBar(MainWindow) self.menubar.setGeometry(QtCore.QRect(0, 0, 1042, 17)) self.menubar.setObjectName("menubar") MainWindow.setMenuBar(self.menubar) self.statusbar = QtWidgets.QStatusBar(MainWindow) self.statusbar.setObjectName("statusbar") MainWindow.setStatusBar(self.statusbar) self.retranslateUi(MainWindow) # 这里将按钮和定义的动作相连,通过click信号连接openfile槽? # 加载模型文件 self.btn_model_add_file.clicked.connect(self.open_model) # 加载cfg文件 self.btn_cfg_add_file.clicked.connect(self.open_cfg) # 打开摄像头 self.btn_opencam.clicked.connect(self.opencam) # 开始识别 self.btn_detect.clicked.connect(self.detect) # 这里是将btn_exit按钮和Form窗口相连,点击按钮发送关闭窗口命令 self.btn_exit.clicked.connect(MainWindow.close) QtCore.QMetaObject.connectSlotsByName(MainWindow) def retranslateUi(self, MainWindow): _translate = QtCore.QCoreApplication.translate MainWindow.setWindowTitle(_translate("MainWindow", "目标检测")) self.label_img_show.setText(_translate("MainWindow", "摄像头原始画面")) self.label_detect_show.setText(_translate("MainWindow", "实时检测效果")) self.btn_opencam.setText(_translate("MainWindow", "打开摄像头")) self.btn_model_add_file.setText(_translate("MainWindow", "加载模型文件")) self.btn_cfg_add_file.setText(_translate("MainWindow", "加载cfg文件")) self.btn_detect.setText(_translate("MainWindow", "开始检测")) self.btn_exit.setText(_translate("MainWindow", "退出")) def open_model(self): global openfile_name_mdoel openfile_name_mdoel, _ = QFileDialog.getOpenFileName(self.btn_model_add_file, '选择模型文件', '/home/ljw/桌面/demo/project_demo/pyqt5/yolov3/') print('加载模型文件地址为:' + str(openfile_name_mdoel)) def open_cfg(self): global openfile_name_cfg openfile_name_cfg, _ = QFileDialog.getOpenFileName(self.btn_cfg_add_file, '选择cfg文件', '/home/ljw/桌面/demo/project_demo/pyqt5/yolov3/') print('加载cfg文件地址为:' + str(openfile_name_cfg)) def opencam(self): self.camcapture = cv2.VideoCapture(0) self.timer = QtCore.QTimer() self.timer.start() self.timer.setInterval(3) # 0.1s刷新一次 self.timer.timeout.connect(self.camshow) def camshow(self): # global self.camimg _, self.camimg = self.camcapture.read() camimg = cv2.cvtColor(self.camimg, cv2.COLOR_BGR2RGB) showImage = QtGui.QImage(camimg.data, camimg.shape[1], camimg.shape[0], QtGui.QImage.Format_RGB888) self.label_img_show.setPixmap(QtGui.QPixmap.fromImage(showImage)) def detect(self): self.frames = 0 self.start = time.time() cfgfile = openfile_name_cfg weightsfile = openfile_name_mdoel self.num_classes = 80 args = arg_parse() self.confidence = float(args.confidence) self.nms_thesh = float(args.nms_thresh) self.CUDA = torch.cuda.is_available() self.model = Darknet(cfgfile) self.model.load_weights(weightsfile) self.model.net_info["height"] = args.reso self.inp_dim = int(self.model.net_info["height"]) assert self.inp_dim % 32 == 0 assert self.inp_dim > 32 self.timerdec = QtCore.QTimer() self.timerdec.start() self.timerdec.setInterval(3) # 0.1s刷新一次 self.timerdec.timeout.connect(self.object_detection) def object_detection(self): if self.CUDA: self.model.cuda() self.model.eval() img, orig_im, dim = prep_image(self.camimg, self.inp_dim) output = self.model(Variable(img), self.CUDA) output = write_results(output, self.confidence, self.num_classes, nms=True, nms_conf=self.nms_thesh) output[:, 1:5] = torch.clamp(output[:, 1:5], 0.0, float(self.inp_dim)) / self.inp_dim output[:, [1, 3]] *= self.camimg.shape[1] output[:, [2, 4]] *= self.camimg.shape[0] list(map(lambda x: write(x, orig_im), output)) self.frames += 1 print("FPS of the video is {:5.2f}".format(self.frames / (time.time() - self.start))) camimg = cv2.cvtColor(self.camimg, cv2.COLOR_BGR2RGB) showImage = QtGui.QImage(camimg.data, camimg.shape[1], camimg.shape[0], QtGui.QImage.Format_RGB888) self.label_detect_show.setPixmap(QtGui.QPixmap.fromImage(showImage)) QApplication.processEvents() if __name__ == '__main__': app = QApplication(sys.argv) mainWindow = QMainWindow() ui = Ui_MainWindow() # 向主窗口上添加控件 ui.setupUi(mainWindow) mainWindow.show() sys.exit(app.exec_())注意修改自己模型与cfg文件的路径,然后就是注意调用yolov3的包的头文件。 我这里使用的yolov3的代码为 yolov3的代码 后续将对这个界面进行改进,加入一个文本显示框用来显示帧率以及检测的内容。