Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. Qt for Python
  4. Qcamera supportedViewfinderPixelFormats doesn't return the full list
Forum Updated to NodeBB v4.3 + New Features

Qcamera supportedViewfinderPixelFormats doesn't return the full list

Scheduled Pinned Locked Moved Unsolved Qt for Python
5 Posts 3 Posters 834 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • R Offline
    R Offline
    rhx9
    wrote on last edited by
    #1

    Hi,
    I'm trying to capture a still image from my camera, my camera isn AUKEY brand, viewing the camera in a program like guvcview and playing with the settings it seems like the camera can be set to 1920x1080 only if the format is set to H264, RGB3 or MJPEG.

    unfortunately the list of formats returned by supportedViewfinderPixelFormats only shows Format_YUYV which for my camera only support 640x480 and 1280x720.

    supported formats returned by v4l2-ctrl:

    ╰─➤  v4l2-ctl --list-formats -d /dev/video0 
    ioctl: VIDIOC_ENUM_FMT
            Type: Video Capture
    
            [0]: 'MJPG' (Motion-JPEG, compressed)
            [1]: 'H264' (H.264, compressed)
            [2]: 'YUYV' (YUYV 4:2:2)
    

    my sample program:

    import sys
    import os
    import signal
    import traceback
    from PyQt5 import QtWidgets as qtw
    from PyQt5 import QtCore as qtc
    from PyQt5 import QtGui as qtg
    
    from PyQt5.QtMultimedia import QCameraInfo, QCamera, QCameraImageCapture,QImageEncoderSettings
    
    from PyQt5.QtMultimediaWidgets import QCameraViewfinder
    
    
    class mainwindow(qtw.QMainWindow):
    
    
        def __init__(self, *args, **kwargs):
            super().__init__(*args, **kwargs)
            self.centralwidget = qtw.QWidget()
            self.setCentralWidget(self.centralwidget)
            self.gridLayout = qtw.QGridLayout(self.centralwidget)
            self.avatarLayout = qtw.QHBoxLayout()
            self.gridLayout.addLayout(self.avatarLayout, 0, 0, 1, 1)
            self.avatar = qtw.QLabel()
            self.avatar.setText("")
            self.avatar.setStyleSheet("background-color:#c7dcff")
            self.start_cam = qtw.QPushButton("start camera")
            self.capture_cam = qtw.QPushButton("capture camera")
            self.viewFinderContainer = qtw.QWidget()
            self.viewFinderContainer_layout =qtw.QGridLayout(self.viewFinderContainer)
            
            self.viewFinder = QCameraViewfinder()
            self.viewFinderContainer.setStyleSheet("background-color:#98b8ed")
            self.viewFinderContainer_layout.addWidget(self.viewFinder)
            self.viewFinderContainer.setMinimumHeight(400)
            self.viewFinderContainer.setMinimumWidth(400)
            self.avatar.setMinimumHeight(600)
            self.avatar.setMinimumWidth(400)
    
            self.avatarLayout.addWidget(self.viewFinderContainer)
            self.avatarLayout.addWidget(self.avatar)
            self.gridLayout.addWidget(self.start_cam,1,0,1,1)
            self.gridLayout.addWidget(self.capture_cam,2,0,1,1)
            
            self.statusbar = qtw.QStatusBar(self)
            self.setStatusBar(self.statusbar)
            
            self.start_cam.clicked.connect(self.get_webcam)
            self.capture_cam.clicked.connect(self.capture_img)
            self.online_webcams = QCameraInfo.availableCameras()
            self.show()
    
    
                
        @qtc.pyqtSlot()
        def get_webcam(self):
            if not self.online_webcams:
                self.statusbar.showMessage("you didn't connect a camera")
            else:
                print("getting webcam")
            self.my_webcam = QCamera(self.online_webcams[0])
            self.my_webcam.statusChanged.connect(self.status_changed)
            self.my_webcam.setViewfinder(self.viewFinder)
            self.my_webcam.setCaptureMode(QCamera.CaptureStillImage)
            self.my_webcam.error.connect(lambda: print(self.my_webcam.errorString()))
    
            print("starting webcam")
            self.my_webcam.start()
    
            self.capture = QCameraImageCapture(self.my_webcam)
            self.cap_end_settings = QImageEncoderSettings()
            # self.cap_end_settings.setResolution(qtc.QSize(1080,1920))
            self.capture.setEncodingSettings(self.cap_end_settings)
            self.capture.setCaptureDestination(self.capture.CaptureToBuffer)
            self.capture.error.connect(lambda i, e, s: print(s))
            self.capture.imageCaptured.connect(self.captured)
    
            self.current_camera_name = self.online_webcams[0].description()
            
        
        def captured(self,d,i):
            print('captured')
            print("scale the pixmap")
            pixmap = qtg.QPixmap.fromImage(i.convertToFormat(qtg.QImage.Format_ARGB32)).scaledToHeight(600,qtc.Qt.SmoothTransformation)
            self.avatar.setPixmap(pixmap)
        
        @qtc.pyqtSlot(QCamera.Status)
        def status_changed(self,status):
            print("status changed, new status: ",status)
    
            # Camera is loaded and we can query and set settings
            if status == QCamera.LoadedStatus:
                print("printing supported camera PixelFormats")
                print(self.my_webcam.supportedViewfinderPixelFormats())
                print("setting pixel format")
                self.my_webcam.viewfinderSettings().setPixelFormat(30)
                print(self.my_webcam.viewfinderSettings().pixelFormat())
                
                print("printing supported camera resolutions")
                print(self.my_webcam.supportedViewfinderResolutions())
                
                # print("setting resolution")
                # self.my_webcam.viewfinderSettings().setResolution(1080,1920)
                # print("printing supported camera resolutions")
                # print(self.my_webcam.viewfinderSettings().resolution())
                # print("printing current camera resolutions")
                # print(self.my_webcam.viewfinderSettings().resolution())
    
    
    
        @qtc.pyqtSlot()
        def capture_img(self):
            if (self.capture.isReadyForCapture()):
                self.capture.capture()
    
    def setup_interrupt_handling():
        """Setup handling of KeyboardInterrupt (Ctrl-C) for PyQt."""
        signal.signal(signal.SIGINT, _interrupt_handler)
        # Regularly run some (any) python code, so the signal handler gets a
        # chance to be executed:
        safe_timer(50, lambda: None)
    
    
    # Define this as a global function to make sure it is not garbage
    # collected when going out of scope:
    def _interrupt_handler(signum, frame):
        """Handle KeyboardInterrupt: quit application."""
        w.cleanup()
        qtw.QApplication.quit()
    
    
    def safe_timer(timeout, func, *args, **kwargs):
        """
        Create a timer that is safe against garbage collection and overlapping
        calls. See: http://ralsina.me/weblog/posts/BB974.html
        """
        def timer_event():
            try:
                func(*args, **kwargs)
            finally:
                qtc.QTimer.singleShot(timeout, timer_event)
        qtc.QTimer.singleShot(timeout, timer_event)
    
    
    def excepthook(exc_type, exc_value, exc_tb):
        tb = "".join(traceback.format_exception(exc_type, exc_value, exc_tb))
        print("error catched!:")
        print("error message:\n", tb)
        qtw.QApplication.quit()
    
    
    if __name__ == '__main__':
        os.environ["QT_AUTO_SCREEN_SCALE_FACTOR"] = "1"
        
        sys.excepthook = excepthook
        try:
            qtw.QApplication.setAttribute(qtc.Qt.AA_EnableHighDpiScaling)
        except AttributeError:  # Attribute only exists for Qt>=5.6.
            pass
        app = qtw.QApplication(sys.argv)
        setup_interrupt_handling()
    
        w = mainwindow()
        ret = app.exec_()
        sys.exit(ret)
    
    
    1 Reply Last reply
    1
    • SGaistS Offline
      SGaistS Offline
      SGaist
      Lifetime Qt Champion
      wrote on last edited by
      #2

      Hi,

      Which version of PyQt5 ?
      How did you install it ?
      Which distribution are you using ?
      Do you get the same result with PySide2/6 ?

      Interested in AI ? www.idiap.ch
      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

      R 1 Reply Last reply
      0
      • SGaistS SGaist

        Hi,

        Which version of PyQt5 ?
        How did you install it ?
        Which distribution are you using ?
        Do you get the same result with PySide2/6 ?

        R Offline
        R Offline
        rhx9
        wrote on last edited by
        #3

        @SGaist said in Qcamera supportedViewfinderPixelFormats doesn't return the full list:

        Hi,

        Which version of PyQt5 ?

        PyQt5==5.15.4
        PyQt5-sip==12.9.0

        How did you install it ?

        pip install PyQt5

        Which distribution are you using ?

        Manjaro linux

        Do you get the same result with PySide2/6 ?

        On, Pyside2 the problem is the same, I couldn't port it to PySide6 however, still have no experience in the version 6 bindings

        1 Reply Last reply
        0
        • F Offline
          F Offline
          farindk
          wrote on last edited by
          #4

          Some problem here. Qt 5.15.3 on Ubuntu 22.04.
          I'm using the C++ interface.

          supportedViewfinder* only returns YUYV formats even though the camera also supports MJPG and RGB formats.
          They are consistently missing everywhere. E.g. setting a resolution in QCameraViewFinderSettings and leaving pixel formats and frame rate unspecified only returns the YUYV frame rates.

          As far as I know, Qt uses gstreamer on Linux, so the problem may be in either of the two.
          V4L2 correctly detects all formats.

          1 Reply Last reply
          0
          • F Offline
            F Offline
            farindk
            wrote on last edited by
            #5

            Same code on Windows 10 returns YUYV and Jpeg pixel formats. I still don't get the RGB formats that V4L2 lists, but at least Jpeg is there.
            Hence, it seems to be specifically a Qt on Linux issue.

            1 Reply Last reply
            0

            • Login

            • Login or register to search.
            • First post
              Last post
            0
            • Categories
            • Recent
            • Tags
            • Popular
            • Users
            • Groups
            • Search
            • Get Qt Extensions
            • Unsolved