Phonon的VideoWidget在QGLWidget上显示错误颜色(Qt,Python)

18 投票
2 回答
1571 浏览
提问于 2025-04-17 03:52

我有一个小项目,里面有一个视频播放器,能显示字幕。之前我一直在忙项目的其他部分,现在需要实现字幕显示的功能,尽量做到最好。

为了这个目的,我没有找到什么有用的资料,除了这个链接

但是当我使用这个代码时,视频的画面出现了问题。

视频画面中红色和蓝色互换

颜色被修改了:红色变成了蓝色,蓝色变成了红色,等等。

有没有人能帮我解决这个代码的问题,或者给我提供另一种在视频上方显示字幕的解决方案?

补充说明:我在 PySide 1.0.0 和 1.0.6 版本上,以及在 Arch 和 Ubuntu Linux 系统上测试过。


编辑:解决方法

有一个不太优雅的解决办法,多亏了alexisdm。这个方法修改了paint()方法,以反转颜色。

import sys
from PySide.QtGui import QApplication, QMessageBox
# overlay
from PySide.QtGui import QGraphicsScene, QGraphicsView, QGraphicsProxyWidget, QPainter, QImage
from PySide.QtOpenGL import QGLWidget

from PySide.phonon import Phonon

try:
    from OpenGL import GL
except ImportError:
    app = QApplication(sys.argv)
    QMessageBox.critical(None, "OpenGL 2dpainting",
                            "PyOpenGL must be installed to run this example.",
                            QMessageBox.Ok | QMessageBox.Default,
                            QMessageBox.NoButton)
    sys.exit(1)


#class CustomProxy(QGraphicsProxyWidget):
#    def __init__(self, parent=None):
#        QGraphicsProxyWidget.__init__(self, parent)
#
#
#    def boundingRect(self):
#        return QGraphicsProxyWidget.boundingRect(self).adjusted(0, 0, 0, 0);


class CustomProxy(QGraphicsProxyWidget):
    def __init__(self, parent=None):
        QGraphicsProxyWidget.__init__(self, parent)


    def boundingRect(self):
        return QGraphicsProxyWidget.boundingRect(self).adjusted(0, 0, 0, 0);

# This is the magic:
    def paint(self, painter, option, widget=None):
        painter_inverted = QPainter()
        brect= QGraphicsProxyWidget.boundingRect(self)
        invertedColor = QImage(brect.width(),brect.height(),QImage.Format_RGB32)
        painter_inverted.begin(invertedColor)
        QGraphicsProxyWidget.paint(self,painter_inverted, option, widget)
        painter_inverted.end()
        painter.drawImage(0,0,invertedColor.rgbSwapped())


if __name__ == '__main__':
    app = QApplication(sys.argv)
    app.setApplicationName("tete")

    scene = QGraphicsScene()

    media = Phonon.MediaObject()
    video = Phonon.VideoWidget()
    Phonon.createPath(media, video)

    proxy = CustomProxy()
    proxy.setWidget(video)
    rect = proxy.boundingRect()
    #proxy.setPos(0, 0)
    #proxy.show()
    scene.addItem(proxy)

    media.setCurrentSource("/home/boo/Development/mindmap/test/resources/glvideo.avi")
    media.play()

    titem = scene.addText("Bla-bla-bla")
    titem.setPos(130, 130)
    #titem.setPos(rect.width()/2, rect.height()/2)

    view = QGraphicsView(scene)
    vp = QGLWidget()
    view.setViewport(vp)

    #view.setRenderHints(QPainter.Antialiasing | QPainter.SmoothPixmapTransform)
    view.setViewportUpdateMode(QGraphicsView.BoundingRectViewportUpdate)
    view.setWindowTitle("Eternal fire")

    view.show()
    sys.exit(app.exec_())

2 个回答

0

有些操作系统、框架和文件格式把颜色存储为RGB格式,有些则是BGR格式(后者在Windows系统中更常见)。所以,当你在这两种格式之间传递颜色时,红色和蓝色可能会互换。仔细查看你的颜色结构,确保你使用的颜色格式和你正在使用的技术是匹配的。

2

正如alexisdm在评论中提到的,这是Qt的一个已知问题。

这个问题可以在#GTBUG-8738上找到,里面还有人提供了一个解决办法。

撰写回答