Other: Worker/Overseer/Threads improvements.

Added cancelled signal to worker and improved Overseer::wait.
Renamed Overseer::release() to Overseer::releaseWorker().
This commit is contained in:
Xavier Michelon
2022-08-20 10:22:35 +02:00
committed by Jakub
parent 090aaf8ee3
commit a520d636e8
3 changed files with 31 additions and 12 deletions

View File

@ -43,7 +43,7 @@ Overseer::Overseer(Worker *worker, QObject *parent)
//**************************************************************************************************************************************************** //****************************************************************************************************************************************************
Overseer::~Overseer() Overseer::~Overseer()
{ {
this->release(); this->releaseWorker();
} }
@ -61,11 +61,13 @@ void Overseer::startWorker(bool autorelease) const
connect(thread_, &QThread::started, worker_, &Worker::run); connect(thread_, &QThread::started, worker_, &Worker::run);
connect(worker_, &Worker::finished, [&]() {thread_->quit(); }); // Safety, normally the thread already properly quits. connect(worker_, &Worker::finished, [&]() {thread_->quit(); }); // Safety, normally the thread already properly quits.
connect(worker_, &Worker::error, [&]() { thread_->quit(); }); connect(worker_, &Worker::error, [&]() { thread_->quit(); });
connect(worker_, &Worker::cancelled, [&]() { thread_->quit(); });
if (autorelease) if (autorelease)
{ {
connect(worker_, &Worker::error, this, &Overseer::release); connect(worker_, &Worker::error, this, &Overseer::releaseWorker);
connect(worker_, &Worker::finished, this, &Overseer::release); connect(worker_, &Worker::cancelled, this, &Overseer::releaseWorker);
connect(worker_, &Worker::finished, this, &Overseer::releaseWorker);
} }
thread_->start(); thread_->start();
@ -75,7 +77,7 @@ void Overseer::startWorker(bool autorelease) const
//**************************************************************************************************************************************************** //****************************************************************************************************************************************************
// //
//**************************************************************************************************************************************************** //****************************************************************************************************************************************************
void Overseer::release() void Overseer::releaseWorker()
{ {
if (worker_) if (worker_)
{ {
@ -115,16 +117,32 @@ bool Overseer::isFinished() const
//**************************************************************************************************************************************************** //****************************************************************************************************************************************************
bool Overseer::wait(qint32 timeoutMs) const bool Overseer::wait(qint32 timeoutMs) const
{ {
QElapsedTimer timer; if (this->isFinished())
timer.start(); return true;
while (!this->isFinished()) { QEventLoop loop;
if ((timeoutMs >= 0) && (timer.elapsed() > timeoutMs)) QTimer timer;
return false; bool inTime = true;
QThread::msleep(10); if (timeoutMs >= 0)
{
connect(&timer, &QTimer::timeout, &loop, [&]() { loop.quit(); inTime = false; } );
timer.setSingleShot(true);
timer.start(timeoutMs);
} }
return true; QTimer repeatTimer; // safety timer, used if for some reason the worker does not emit finished(), error() or cancelled()
repeatTimer.setSingleShot(false);
repeatTimer.setInterval(100);
connect(&repeatTimer, &QTimer::timeout, [&]() { if (this->isFinished()) { loop.quit(); }});
repeatTimer.start();
connect(worker_, &Worker::finished, &loop, &QEventLoop::quit);
connect(worker_, &Worker::error, &loop, &QEventLoop::quit);
connect(worker_, &Worker::cancelled, &loop, &QEventLoop::quit);
loop.exec();
return inTime;
} }

View File

@ -46,7 +46,7 @@ public: // member functions.
public slots: public slots:
void startWorker(bool autorelease) const; ///< Run the worker. void startWorker(bool autorelease) const; ///< Run the worker.
void release(); ///< Delete the worker and its thread. void releaseWorker(); ///< Delete the worker and its thread.
public: // data members. public: // data members.
QThread *thread_{nullptr}; ///< The thread. QThread *thread_{nullptr}; ///< The thread.

View File

@ -47,6 +47,7 @@ signals:
void started(); ///< Signal for the start of the worker void started(); ///< Signal for the start of the worker
void finished(); ///< Signal for the end of the worker void finished(); ///< Signal for the end of the worker
void error(QString const &message); ///< Signal for errors. After an error, worker ends and finished is NOT emitted. void error(QString const &message); ///< Signal for errors. After an error, worker ends and finished is NOT emitted.
void cancelled(); ///< Signal for the cancellation of the worker.
}; };