본문 바로가기
C++ 200제/코딩 IT 정보

[Qt프로그래밍] Thread를 GUI에서 효율적으로 사용 방법 [Qt5]

by vicddory 2017. 1. 8.

[Qt프로그래밍] Thread를 GUI에서 효율적으로 사용 방법 [Qt5]


C#도 그렇고 Qt도 그렇고 버전이 올라갈 때마다 더 많고 합리적인 라이브러리가 추가(수정)됩니다. (C# 스레드풀 예제[링크]) Qt는 이전부터 그래왔지만, 기본 스레드에서 GUI의 도구에 접근할 때면 여러 경고 메시지를 내뿜습니다.


가령, 아래처럼 말이죠. Qt프로그래밍 중 자주 보게 될 에러입니다.


1
2
QCoreApplication::sendPostedEvents: 
Cannot send posted events for objects in another thread

cs


그렇기에, 굳이 스레드가 필요하다면 아래 사이트를 참조해 별도의 스레드를 구현할 필요가 있습니다.

Timer는 독립적으로 구동되어야 합니다. GUI 도구에 영향을 미쳐서도 안 되겠죠.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
int main(int argc, char *argv[])
{
     QApplication app(argc, argv);
 
     // build gui
     QWidget widget;
     QLabel *label = new QLabel;
     QHBoxLayout *layout = new QHBoxLayout(&widget);
     layout->addWidget(label);
     widget.setWindowTitle("clock");
 
     //instantiate thread object
     ClockThread clockThread;
     QObject::connect(&clockThread, SIGNAL(sendTime(QString)), label, 
                            SLOT(setText(QString)), Qt::QueuedConnection);
 
     clockThread.start();
     widget.show();
     app.exec();
     clockThread.quit();
     clockThread.wait();
 
     return 0;
}
cs


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// clock/clockthread.h
 class ClockThread : public QThread
 {
     Q_OBJECT
 
 signals:
     void sendTime(QString time);
 
 private:
     void run();
     QString m_lastTime;
 
 private slots:
     void timerHit();
 };
 
cs


Still it is safe to access ClockThread::timerHit() from the worker thread because ClockThread::timerHit() is private and only touches local variables and a private member that isn't touched by public methods.


QDateTime::currentDateTime() isn't marked as thread-safe in Qt documentation, however we can get away with using it in this small example because we know that the QDateTime::currentDateTime() static method isn't used in any other threads.


Qt 스레드 사용 예제[Qt프로그래밍] Thread를 GUI에서 효율적으로 사용 방법 [Qt5]


Qt프로그래밍에서 한 스레드는 다른 스레드에 영향을 주어선 안 됩니다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 // clock/clockthread.cpp
 void ClockThread::run()
 {
     QTimer timer;
     connect(&timer, SIGNAL(timeout()), this, SLOT(timerHit()), Qt::DirectConnection);
 
     timer.setInterval(10);
     timer.start();   // puts one event in the threads event queue
     exec();
 
     timer.stop();
 }
 
 void ClockThread::timerHit()
 {
     QString newTime= QDateTime::currentDateTime().toString("ddd MMMM d yy, hh:mm:ss");
 
     if(m_lastTime != newTime ){
         m_lastTime = newTime;
         emit sendTime(newTime) ;
     }
 }
cs


그래서 C#의 await/async는 정말이지 획기적일 수밖에 없다는 생각이 듭니다. Qt로 구현한 멀티스레드 예제는 여기[링크]를 참조하세요.


참조 사이트 - Qt - Project : Threading Basics [클릭]

[Qt프로그래밍] Thread를 GUI에서 효율적으로 사용 방법 [Qt5]

댓글