GUI线程中有一些耗时操作,直接在主线程中执行会使主gui卡死,后来放在QThread线程中执行,子进程中绑定信号槽更新,用进度条显示进程执行的状态,调试的时候是正常运行的,当把程序打包出来执行,子线程开始执行会使gui线程也卡死,界面未响应状态,进度条也不再更新,很让人卧槽的问题。
线程类定义:
#ifndef WORKERTHREAD_H
#define WORKERTHREAD_H
#include <QThread>
#include <QMutexLocker>
#include<QDebug>
#include <QApplication>
#include <QProcess>
class WorkerThread : public QThread
{
Q_OBJECT
public:
explicit WorkerThread(QObject *parent = 0,QString cmd="")
: QThread(parent),
m_bStopped(false),
commentStr(cmd)
{
qDebug() << "Worker Thread : " << QThread::currentThreadId();
}
~WorkerThread()
{
stop();
quit();
wait();
}
void stop()
{
qDebug() << "Worker Stop Thread : " << QThread::currentThreadId();
QMutexLocker locker(&m_mutex);
m_bStopped = true;
}
protected:
virtual void run() Q_DECL_OVERRIDE {
//qDebug() << "Worker Run Thread : " << QThread::currentThreadId();
int res=QProcess::execute(commentStr.toStdString().c_str());
// 准备更新
emit resultReady(commentStr);
// 检测是否停止
/* {
QMutexLocker locker(&m_mutex);
if (m_bStopped)
return;
}*/
// locker超出范围并释放互斥锁
}
signals:
void resultReady(QString value);
private:
bool m_bStopped;
QMutex m_mutex;
QString commentStr;
};
#endif // WORKERTHREAD_H
线程启动
workerThread = new WorkerThread(this,cmdXml);
connect(workerThread, SIGNAL(resultReady(QString)), this, SLOT(handleResults(QString)));
// 线程结束后,自动销毁
connect(workerThread, SIGNAL(finished()), workerThread, SLOT(deleteLater()));
workerThread->start();
线程执行结束响应
// 线程执行返回
void MainWindow::handleResults(QString cmd)
{
// qDebug() << "Handle Thread : " << QThread::currentThreadId();
statusProgressBar->hide() ; //隐藏状态栏进度条
.....
}
Qt线程创建有两种方法,一种是上面这种继承QThread,然后重写run的方式,但是这种方式官方已经不推荐了。不知道是不是Qt的bug,官方不推荐就不这样写了,下面开始换第二种方式。使用QObject的moveToThread方法开启线程试试会不会还是这样的问题
待续!
2020年7月11晚9点最后编辑
原文:https://www.cnblogs.com/pozhu15/p/13285891.html