반응형

 

 

OpenCV에서 캡처한 영상을 pyQt5로 작성된 GUI에서 보여주는 방법을 다룹니다.

깃허브에 있는 코드를 수정하여 사용했습니다.



 

처음 실행하면 버튼 2개만 보입니다.

 




start 버튼을 클릭하면 웹캠 영상이 보입니다.

 




Canny 버튼을 클릭하면 오른쪽에 캐니 영상을 보여줍니다.

 



# 출처 - https://github.com/ddd4117/GUI/blob/master/src/camera_test.py
# 수정 - webnautes

import cv2
import sys
from PyQt5 import QtCore
from PyQt5 import QtWidgets
from PyQt5 import QtGui


class ShowVideo(QtCore.QObject):

   flag = 0

   camera = cv2.VideoCapture(0)

   ret, image = camera.read()
   height, width = image.shape[:2]

   VideoSignal1 = QtCore.pyqtSignal(QtGui.QImage)
   VideoSignal2 = QtCore.pyqtSignal(QtGui.QImage)

   def __init__(self, parent=None):
       super(ShowVideo, self).__init__(parent)

   @QtCore.pyqtSlot()
   def startVideo(self):
       global image

       run_video = True
       while run_video:
           ret, image = self.camera.read()
           color_swapped_image = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)

           qt_image1 = QtGui.QImage(color_swapped_image.data,
                                   self.width,
                                   self.height,
                                   color_swapped_image.strides[0],
                                   QtGui.QImage.Format_RGB888)
           self.VideoSignal1.emit(qt_image1)


           if self.flag:
               img_gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
               img_canny = cv2.Canny(img_gray, 50, 100)

               qt_image2 = QtGui.QImage(img_canny.data,
                                        self.width,
                                        self.height,
                                        img_canny.strides[0],
                                        QtGui.QImage.Format_Grayscale8)

               self.VideoSignal2.emit(qt_image2)


           loop = QtCore.QEventLoop()
           QtCore.QTimer.singleShot(25, loop.quit) #25 ms
           loop.exec_()

   @QtCore.pyqtSlot()
   def canny(self):
       self.flag = 1 - self.flag


class ImageViewer(QtWidgets.QWidget):
   def __init__(self, parent=None):
       super(ImageViewer, self).__init__(parent)
       self.image = QtGui.QImage()
       self.setAttribute(QtCore.Qt.WA_OpaquePaintEvent)

   def paintEvent(self, event):
       painter = QtGui.QPainter(self)
       painter.drawImage(0, 0, self.image)
       self.image = QtGui.QImage()

   def initUI(self):
       self.setWindowTitle('Test')

   @QtCore.pyqtSlot(QtGui.QImage)
   def setImage(self, image):
       if image.isNull():
           print("Viewer Dropped frame!")

       self.image = image
       if image.size() != self.size():
           self.setFixedSize(image.size())
       self.update()


if __name__ == '__main__':
   app = QtWidgets.QApplication(sys.argv)


   thread = QtCore.QThread()
   thread.start()
   vid = ShowVideo()
   vid.moveToThread(thread)

   image_viewer1 = ImageViewer()
   image_viewer2 = ImageViewer()

   vid.VideoSignal1.connect(image_viewer1.setImage)
   vid.VideoSignal2.connect(image_viewer2.setImage)

   push_button1 = QtWidgets.QPushButton('Start')
   push_button2 = QtWidgets.QPushButton('Canny')
   push_button1.clicked.connect(vid.startVideo)
   push_button2.clicked.connect(vid.canny)

   vertical_layout = QtWidgets.QVBoxLayout()
   horizontal_layout = QtWidgets.QHBoxLayout()
   horizontal_layout.addWidget(image_viewer1)
   horizontal_layout.addWidget(image_viewer2)
   vertical_layout.addLayout(horizontal_layout)
   vertical_layout.addWidget(push_button1)
   vertical_layout.addWidget(push_button2)

   layout_widget = QtWidgets.QWidget()
   layout_widget.setLayout(vertical_layout)

   main_window = QtWidgets.QMainWindow()
   main_window.setCentralWidget(layout_widget)
   main_window.show()
   sys.exit(app.exec_())




최초 작성  2019. 1. 24

 

 

관련 포스트

 

[OpenCV/OpenCV with Qt] - OpenCV에서 캡처한 webcam 영상을 QT에서 보여주기

 

OpenCV에서 캡처한 webcam 영상을 QT에서 보여주기

OpenCV에서 캡처한 webcam 영상을 QT에서 보여주는 예제 코드입니다.  2021. 8. 24 - 최초작성 실행 화면입니다. 처음 실행시 Open 버튼 클릭 후 Close 버튼 클릭 후 소스 코드입니다. // 원본 - https://gith..

webnautes.tistory.com

 

반응형

해본 것을 문서화하여 기록합니다.
부족함이 있지만 도움이 되었으면 합니다.


포스트 작성시에는 문제 없었지만 이후 문제가 생길 수 있습니다.
질문을 남겨주면 가능한 빨리 답변드립니다.


제가 쓴 책도 한번 검토해보세요 ^^

  • 네이버 블러그 공유하기
  • 네이버 밴드에 공유하기
  • 페이스북 공유하기
  • 카카오스토리 공유하기

댓글을 달아 주세요

">
  1. thumbnail
    ryu
    2019.01.25 12:53

    저는 vc로 해봤는데요.
    QImage에 Mat 데이터 집어넣고 QLabel(view1) 에 setPixmap() 호출하면 되더군요.
    제가 Qt를 지워버려서 다음에 혹시 필요할까봐 여기에 남겨요,
    --------
    void MainWindow::OnTimer()
    {
    Mat img;
    Mat1b img_gray;

    cap.read(img);

    cvtColor( img, img, COLOR_BGR2RGB );
    cvtColor( img, img_gray, COLOR_BGR2GRAY );

    QImage qimg1(img.data, img.cols, img.rows, img.step, QImage::Format_RGB888 );
    QImage qimg2(img_gray.data, img_gray.cols, img_gray.rows, img_gray.step, QImage::Format_Grayscale8 );

    ui->view1->setPixmap( QPixmap::fromImage(qimg1) );
    ui->view2->setPixmap( QPixmap::fromImage(qimg2) );
    }

  2. thumbnail
    안녕하세요
    2019.03.05 21:04

    감사합니다 덕분에 졸음감지코드에 gui를 입힐 수 있게 되었습니다.
    지금은 코드를 실행시켰을때 검은 화면이 아닌 바로 웹캠 화면이 나오도록 수정해보고 있습니다만... 쉬울것 같았는데 맘대로 되질 않네요
    혹시 어떻게 해야 하는지 알려주실 수 있나요?

    • thumbnail
      Favicon of https://webnautes.tistory.com BlogIcon webnautes
      2019.03.05 21:25 신고

      다음처럼 vid.startVideo()를 추가하면됩니다.

      main_window.show()
      vid.startVideo()
      sys.exit(app.exec_())

    • thumbnail
      안녕하세요
      2019.03.05 21:48

      처음에 startVideo를 실행시키면
      검은이미지에 관련된 코드는 없어도 될것 같은데, Image_viewer, ImageViewer() 관련 라인만 지우면 되는건 아닌가요??

    • thumbnail
      Favicon of https://webnautes.tistory.com BlogIcon webnautes
      2019.03.05 21:52 신고

      버튼 만드는 코드와 버튼 누를때 동작하도록 하는 코드 외에는 다 필요한 부분입니다.

  3. thumbnail
    eksox
    2019.03.08 16:57

    코드 응용해보고 있습니다
    저기서 위젯을 추가하고 싶은데 클래스나 함수를 만들어서 추가 하려면 showvideo클래스 안에 만들고 vid.ㅇㅇㅇㅇ 로 호출시키면 되나요?

    • thumbnail
      Favicon of https://webnautes.tistory.com BlogIcon webnautes
      2019.03.08 18:45 신고

      if __name__ == '__main__': 다음에 기존코드있는 위치에 필요한 위젯을 추가해야 합니다.

  4. thumbnail
    Marek Wojciechowski
    2019.05.25 01:25

    Hello.
    My name is Marek and for a long time I try to compile via cmake last version OpenCV 4.1 contrib for 32bit Python 3.7. There are so many errors in Visual Studio 15 I can not handle it. I want to use sirf, surf features for my programming with Kinect 360 (or if You can tell me there are new solutions in opencv for segmentation 3d ?) Can You help me ?
    wojciechowski.marek@outlook.com

  5. thumbnail
    2020.01.28 09:51

    비밀댓글입니다

  6. thumbnail
    helpme
    2020.05.21 15:24

    안녕하세요.
    python openCV with pyqt5로 공부하고 중에 블로그 보고 많이 알아가고 있습니다만
    혹시 실례가 안된다면 저기서 카메라 영상을 저장을 하려면 어떻게 해야되는지 알려주실 수 있을까요??ㅠㅠ
    cv2.VideoWriter() 함수 저장하는 걸로는 저장이 안되는데 qimage는 따로 해야하나요??

    • thumbnail
      Favicon of https://webnautes.tistory.com BlogIcon webnautes
      2020.05.21 15:37 신고

      opencv 방식으로 가능할텐데 이상하군요. 안된다면 qt에서 영상 저장하는 코드를 찾아보세요