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. QMediaPlayer Video Opens Second Window. Only One Desired. GStreamer Pipeline URI
Forum Updated to NodeBB v4.3 + New Features

QMediaPlayer Video Opens Second Window. Only One Desired. GStreamer Pipeline URI

Scheduled Pinned Locked Moved Solved Qt for Python
4 Posts 2 Posters 2.1k 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.
  • M Offline
    M Offline
    mbar
    wrote on last edited by
    #1

    I am trying to embed a video in a window with buttons. Here is my reduced Video Feed Widget example. When I run it in Linux 18.04 container, it opens two windows. I would like the "python3" window to show up in the "videoplayer.py" window.

    1a52a3a4-2219-44e0-bca0-af1c50a75831-image.png

    import logging
    
    from PySide2.QtCore import QSize, QUrl
    from PySide2.QtMultimedia import QMediaPlayer, QMediaPlaylist
    from PySide2.QtMultimediaWidgets import QVideoWidget
    from PySide2.QtWidgets import QWidget, QVBoxLayout
    
    logger = logging.getLogger(__name__)
    
    class VideoFeedWidget(QWidget):
        def __init__(self, parent=None):
            super().__init__(parent=parent)
            self.player = QMediaPlayer()
            self.resize(QSize(400, 300))
    
            uri = "gst-pipeline: videotestsrc ! ximagesink"
            self.player.setMedia(QUrl(uri))
    
            self.video_widget = QVideoWidget()
            self.player.setVideoOutput(self.video_widget)
    
            self.layout = QVBoxLayout()
            self.layout.addWidget(self.video_widget)
            self.setLayout(self.layout)
    
            self.player.play()
    
    if __name__ == "__main__":
        from PySide2.QtWidgets import QApplication
        import sys
        app = QApplication(sys.argv)
        player = VideoFeedWidget()
        player.raise_()
        player.show()
        app.exec_()
    
    1 Reply Last reply
    0
    • M mbar

      I am not sure how to implement the AbstractSurface example in Python

      class VideoFeedWidget(QWidget):
          class Surface(QAbstractVideoSurface):
              def __init__(self, parent=None):
                  super().__init__(parent=parent)
      
          def __init__(self, parent=None):
              super().__init__(parent=parent)
              self.player = QMediaPlayer()
              self.resize(QSize(400, 300))
      
              uri = "gst-pipeline: videotestsrc ! qtvideosink"
      
              self.video_widget = self.Surface()
              self.player.setVideoOutput(self.video_widget)
              self.player.setMedia(QUrl(uri))
              self.player.play()
      
              # self.layout = QVBoxLayout()
              # self.layout.addWidget(self.video_widget)
              # self.setLayout(self.layout)
      

      and got

      root@213c9f3fd16c:/# python3 videoplayer.py 
      QStandardPaths: XDG_RUNTIME_DIR not set, defaulting to '/tmp/runtime-root'
      Error: " videotestsrc ! qtvideosink" : "no element \"qtvideosink\""
      AL lib: (EE) ALCplaybackAlsa_open: Could not open playback device 'default': No such file or directory
      GStreamer; Unable to pause - "gst-pipeline: videotestsrc ! qtvideosink"
      GStreamer; Unable to play - "gst-pipeline: videotestsrc ! qtvideosink"
      libGL error: No matching fbConfigs or visuals found
      libGL error: failed to load driver: swrast
      Warning: "Failed to connect: Connection refused"
      Error: "No URI handler implemented for \"gst-pipeline\"."
      

      This works well enough. Throws a lot of "QWidget::paintEngine: Should no longer be called" errors though

      class VideoFeedWidget(QWidget):
          def __init__(self, parent=None):
              super().__init__(parent=parent)
              self.player = QMediaPlayer()
              self.resize(QSize(400, 300))
      
              uri = "gst-pipeline: videotestsrc ! xvimagesink name=\"qtvideosink\""
      
              self.video_widget = QVideoWidget()
              self.player.setVideoOutput(self.video_widget)
              self.player.setMedia(QUrl(uri))
              self.player.play()
      
              self.layout = QVBoxLayout()
              self.layout.addWidget(self.video_widget)
              self.setLayout(self.layout)
      

      ed90f4f4-1caf-4884-9605-898748024184-image.png

      M Offline
      M Offline
      mbar
      wrote on last edited by
      #4

      The problem appears to be related to where you call player.setMedia. If I call it after setVideoOutput, everything works hunky dory

      1 Reply Last reply
      0
      • SGaistS Offline
        SGaistS Offline
        SGaist
        Lifetime Qt Champion
        wrote on last edited by
        #2

        Hi and welcome to devnet,

        You should use the example pipeline provided in the QMediaPlayer::setMedia documentation. It shows how to properly setup the sink to use Qt as output.

        One thing you are missing is the name of the sink.

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

        1 Reply Last reply
        1
        • M Offline
          M Offline
          mbar
          wrote on last edited by mbar
          #3

          I am not sure how to implement the AbstractSurface example in Python

          class VideoFeedWidget(QWidget):
              class Surface(QAbstractVideoSurface):
                  def __init__(self, parent=None):
                      super().__init__(parent=parent)
          
              def __init__(self, parent=None):
                  super().__init__(parent=parent)
                  self.player = QMediaPlayer()
                  self.resize(QSize(400, 300))
          
                  uri = "gst-pipeline: videotestsrc ! qtvideosink"
          
                  self.video_widget = self.Surface()
                  self.player.setVideoOutput(self.video_widget)
                  self.player.setMedia(QUrl(uri))
                  self.player.play()
          
                  # self.layout = QVBoxLayout()
                  # self.layout.addWidget(self.video_widget)
                  # self.setLayout(self.layout)
          

          and got

          root@213c9f3fd16c:/# python3 videoplayer.py 
          QStandardPaths: XDG_RUNTIME_DIR not set, defaulting to '/tmp/runtime-root'
          Error: " videotestsrc ! qtvideosink" : "no element \"qtvideosink\""
          AL lib: (EE) ALCplaybackAlsa_open: Could not open playback device 'default': No such file or directory
          GStreamer; Unable to pause - "gst-pipeline: videotestsrc ! qtvideosink"
          GStreamer; Unable to play - "gst-pipeline: videotestsrc ! qtvideosink"
          libGL error: No matching fbConfigs or visuals found
          libGL error: failed to load driver: swrast
          Warning: "Failed to connect: Connection refused"
          Error: "No URI handler implemented for \"gst-pipeline\"."
          

          This works well enough. Throws a lot of "QWidget::paintEngine: Should no longer be called" errors though

          class VideoFeedWidget(QWidget):
              def __init__(self, parent=None):
                  super().__init__(parent=parent)
                  self.player = QMediaPlayer()
                  self.resize(QSize(400, 300))
          
                  uri = "gst-pipeline: videotestsrc ! xvimagesink name=\"qtvideosink\""
          
                  self.video_widget = QVideoWidget()
                  self.player.setVideoOutput(self.video_widget)
                  self.player.setMedia(QUrl(uri))
                  self.player.play()
          
                  self.layout = QVBoxLayout()
                  self.layout.addWidget(self.video_widget)
                  self.setLayout(self.layout)
          

          ed90f4f4-1caf-4884-9605-898748024184-image.png

          M 1 Reply Last reply
          0
          • M mbar

            I am not sure how to implement the AbstractSurface example in Python

            class VideoFeedWidget(QWidget):
                class Surface(QAbstractVideoSurface):
                    def __init__(self, parent=None):
                        super().__init__(parent=parent)
            
                def __init__(self, parent=None):
                    super().__init__(parent=parent)
                    self.player = QMediaPlayer()
                    self.resize(QSize(400, 300))
            
                    uri = "gst-pipeline: videotestsrc ! qtvideosink"
            
                    self.video_widget = self.Surface()
                    self.player.setVideoOutput(self.video_widget)
                    self.player.setMedia(QUrl(uri))
                    self.player.play()
            
                    # self.layout = QVBoxLayout()
                    # self.layout.addWidget(self.video_widget)
                    # self.setLayout(self.layout)
            

            and got

            root@213c9f3fd16c:/# python3 videoplayer.py 
            QStandardPaths: XDG_RUNTIME_DIR not set, defaulting to '/tmp/runtime-root'
            Error: " videotestsrc ! qtvideosink" : "no element \"qtvideosink\""
            AL lib: (EE) ALCplaybackAlsa_open: Could not open playback device 'default': No such file or directory
            GStreamer; Unable to pause - "gst-pipeline: videotestsrc ! qtvideosink"
            GStreamer; Unable to play - "gst-pipeline: videotestsrc ! qtvideosink"
            libGL error: No matching fbConfigs or visuals found
            libGL error: failed to load driver: swrast
            Warning: "Failed to connect: Connection refused"
            Error: "No URI handler implemented for \"gst-pipeline\"."
            

            This works well enough. Throws a lot of "QWidget::paintEngine: Should no longer be called" errors though

            class VideoFeedWidget(QWidget):
                def __init__(self, parent=None):
                    super().__init__(parent=parent)
                    self.player = QMediaPlayer()
                    self.resize(QSize(400, 300))
            
                    uri = "gst-pipeline: videotestsrc ! xvimagesink name=\"qtvideosink\""
            
                    self.video_widget = QVideoWidget()
                    self.player.setVideoOutput(self.video_widget)
                    self.player.setMedia(QUrl(uri))
                    self.player.play()
            
                    self.layout = QVBoxLayout()
                    self.layout.addWidget(self.video_widget)
                    self.setLayout(self.layout)
            

            ed90f4f4-1caf-4884-9605-898748024184-image.png

            M Offline
            M Offline
            mbar
            wrote on last edited by
            #4

            The problem appears to be related to where you call player.setMedia. If I call it after setVideoOutput, everything works hunky dory

            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