QT线程间阻塞通信
最近在研究QT线程间同步问题,遇到了如下问题:
启动一个界面线程uiThread和一个工作线程workThread
因为工作线程中不能弹出对话框,但是在遇到问题的时候需要进行弹窗提示,于是想使用uiThread来进行弹窗。
1.使用信号和槽:如果使用QueuedConnection和AutoConnection都可以实现让uiThread弹窗,但是这样做的问题是弹窗的时候线程还是在执行,希望他能够停下来等待用户指令。于是尝试使用DirectConnection,当workThread向uiThread发送信号的时候就崩溃了。
2.信号和槽不行了,于是想到事件机制,同样的,使用postEvent可以在两个线程之间发送事件,但是不能阻塞,使用sendEvent直接崩溃,提示不能向属于其他线程的对象发送信号。
请问各位大神有什么方法能够实现两个线程之间的阻塞通信? QT 线程 阻塞 postevent sendevent
[解决办法]
贴个简单的例子,用到了C++ 2011
######pro file
QT += core gui
CONFIG += c++11
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
TARGET = qtgui
TEMPLATE = app
SOURCES += main.cpp\
mainwindow.cpp
HEADERS += mainwindow.h
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include <QThread>
#include <QMainWindow>
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
MainWindow(QWidget *parent = 0);
~MainWindow();
virtual void paintEvent(QPaintEvent*);
public slots:
void onRequestInput(QString prompt);
};
class WorkerThread : public QThread{
Q_OBJECT
public:
void run();
signals:
void requestInput(QString prompt);
};
#endif // MAINWINDOW_H
#include "mainwindow.h"
#include <QtGui/QPainter>
#include <QTime>
#include <QApplication>
#include <QInputDialog>
#include <QLineEdit>
#include <condition_variable>
#include <mutex>
#include <QDebug>
std::mutex m;
std::condition_variable cv;
QString msg;
void WorkerThread::run() {
emit requestInput("Enter some message for WorkerThread!");
qDebug() << QString("Current time: ") << QTime::currentTime() <<QString("in thread ")
<<QThread::currentThreadId() << " waiting for input\n";
{
std::unique_lock<std::mutex> lk(m);
cv.wait(lk);
}
qDebug() << "Got input: "<< msg;
}
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
}
MainWindow::~MainWindow()
{
}
void MainWindow::paintEvent( QPaintEvent* )
{
QTime now=QTime::currentTime();
QPainter painter(this);
painter.begin(this);
QRect rc = QRect(10, 10, 180, 20);
qint64 pid= QCoreApplication::applicationPid () ;
QString msg = now.toString();
msg.append(" process id: ");
msg.append( QString::number(pid));
painter.drawText(rc, msg);
painter.end();
}
void MainWindow::onRequestInput(QString prompt){
bool ok;
msg = QInputDialog::getText(this, tr("masterz:Enter input"),prompt, QLineEdit::Normal,"", &ok);
cv.notify_one();
}
//main.cpp
#include "mainwindow.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();
WorkerThread thread;
w.connect(&thread,SIGNAL(requestInput(const QString&)),SLOT(onRequestInput(const QString&)) );
thread.start();
return a.exec();
}
与
QMutex Mutex;
QWaitCondition WaitCond;
类似。
建议Qt中用后者,可移植性好一点。