Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/qt/6.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Qt 以不同的线程启动声子播放器?_Qt_Pyqt_Phonon - Fatal编程技术网

Qt 以不同的线程启动声子播放器?

Qt 以不同的线程启动声子播放器?,qt,pyqt,phonon,Qt,Pyqt,Phonon,我有一个Phonon.MediaObject,它通过Phonon.AudioOutput连接到网络源。因此,当运行play()时,主GUI将冻结,直到播放器开始播放(最坏情况下为5秒) 这可以通过移动播放器来解决,或者至少通过它的web抓取任务来解决。我在网上读过关于moveToThread()函数的文章,但它似乎不起作用 我试着用它做一条线,但运气不好:(用PyQt写) 有什么想法吗?子类QThread,使用您希望在线程中发生的内容重新实现run(),然后创建线程的实例并对其调用start()

我有一个
Phonon.MediaObject
,它通过
Phonon.AudioOutput
连接到网络源。因此,当运行
play()
时,主GUI将冻结,直到播放器开始播放(最坏情况下为5秒)

这可以通过移动播放器来解决,或者至少通过它的web抓取任务来解决。我在网上读过关于
moveToThread()
函数的文章,但它似乎不起作用

我试着用它做一条线,但运气不好:(用PyQt写)


有什么想法吗?

子类
QThread
,使用您希望在线程中发生的内容重新实现
run()
,然后创建线程的实例并对其调用
start()

只是在连接到线程中或线程中的内容时要小心,因为您不想进行直接或自动连接,在大多数情况下,您希望进行排队连接

此链接显示了使用
QThread
的两种方法,一种如我刚才所述,它使用
moveToThread()
链接到另一个生产者-消费者示例


希望对您有所帮助。

您是否尝试过
QtConcurrent::run
?它在单独的线程中运行函数


或者在这里检查它

这将需要在您这边进行更多的编码

我对python不太了解,但从您的代码来看,我认为您犯的一个错误是假设您的
phonthread
类存在于它自己的线程中,但它实际上存在于创建它的线程中

我甚至不会尝试在线程之间移动像
MediaObject
这样的对象。一种方法是创建自己的
QObject
子体,然后在它的构造函数中创建播放音乐所需的所有对象。您还需要向类中添加插槽,以访问需要从主线程调用的每个声子函数。请记住在不使用父对象的情况下创建此对象。 然后需要将其移动到新创建的QThread,并连接线程之间的所有信号/插槽

我不使用python,但下面是它的伪C++概要:

class MyPlayer: public QObject{
    Q_OBJECT

public:

    AudioOutput* ao;
    MediaObject* mo;

    MyPlayer() : QObject(0) {    // note no parent QObject instance
        ao = new AudioOutput();
        ... // Create and connect all objects
    }

public slots:

    void setCurrentSource ( const MediaSource & source ){
        mo->setCurrentSource(source);
    }
    // And other methods that are not slots already.
};
然后在应用程序中执行以下操作:

MyPlayer* mp = new MyPlayer();
QThread* th = new QThread();

connect(th, SIGNAL(finished()), mp, SLOT(deleteLater()));

connect( mainThreadObj, SIGNAL(setPlayerSource ( const MediaSource & ) ), mp, SLOT(setPlayerSource ( const MediaSource & ) ) );
... // and other signals; note that methods that are signals already can be conected witout wrappers:
connect( mainThreadObj, SIGNAL(playerPlay() ), mp->mo, SLOT(play()) );

mp->moveToThread(th);

要停止线程,只需将主线程的信号连接到th的
quit()
插槽,并在需要时发出信号。

如果整个播放器位于不同的线程中,输出仍将到达声卡?当我这样做时,我会得到以下错误:
警告:bool\u thiscall Phonon::FactoryPrivate::CreateBend(void)无法加载phonon后端插件
显然,phonon文件夹的链接方式与以前不同。。。您使用的是什么操作系统?您可以将后端文件夹复制到您的exe文件夹中,
C:/Qt/4.8.4/plugins/phonon\u backend
,这样在您的exe旁边就有一个名为
phonon\u backend
的文件夹,其中包含相应的DLL。我认为情况并非如此。我已经这么做了,是为了让第一个声子密码生效。所有内容仍然从同一进程和目录运行。