T102 Implement move constructor and move assignment for CWorkerPointer

so the connection to the worker's aboutToStart signal remains valid.
This commit is contained in:
Mathew Sutcliffe
2017-07-05 00:31:06 +01:00
parent a37b12c8bc
commit 7d7ce055ef
2 changed files with 43 additions and 4 deletions

View File

@@ -25,10 +25,8 @@ namespace BlackMisc
* be disconnected when the object is destroyed. So it can be used with lambdas or bind which feature
* non QObjects, if those might be destroyed before the signaling QObject.
*/
class BLACKMISC_EXPORT CConnectionGuard : public QObject
class BLACKMISC_EXPORT CConnectionGuard
{
Q_OBJECT
public:
//! Constructor
CConnectionGuard() = default;
@@ -36,6 +34,18 @@ namespace BlackMisc
//! Constructor
CConnectionGuard(const QMetaObject::Connection &connection);
//! Move constructor
CConnectionGuard(CConnectionGuard &&) = default;
//! Move assignment operator
CConnectionGuard &operator =(CConnectionGuard &&) = default;
//! Not copyable
//! @{
CConnectionGuard(const CConnectionGuard &) = delete;
CConnectionGuard &operator =(const CConnectionGuard &) = delete;
//! @}
//! Destructor
~CConnectionGuard();

View File

@@ -13,6 +13,7 @@
#define BLACKMISC_WORKER_H
#include "blackmisc/blackmiscexport.h"
#include "blackmisc/connectionguard.h"
#include "blackmisc/logcategorylist.h"
#include "blackmisc/invoke.h"
#include "blackmisc/stacktrace.h"
@@ -329,7 +330,7 @@ namespace BlackMisc
{
if (!ptr || static_cast<const CContinuousWorker *>(ptr)->hasStarted()) { return; }
m_strong.reset(ptr);
QObject::connect(ptr, &CWorkerBase::aboutToStart, [this] { m_strong.release(); });
connect();
}
//! Construct a null pointer.
@@ -338,6 +339,27 @@ namespace BlackMisc
CWorkerPointer(std::nullptr_t) {}
//! @}
//! Move constructor.
CWorkerPointer(CWorkerPointer &&other) : m_strong(std::move(other.m_strong)), m_weak(other.m_weak), m_guard()
{
connect();
}
//! Move assignment operator.
CWorkerPointer &operator =(CWorkerPointer &&other)
{
m_strong = std::move(other.m_strong);
m_weak = other.m_weak;
connect();
return *this;
}
//! Not copyable.
//! @{
CWorkerPointer(const CWorkerPointer &) = delete;
CWorkerPointer &operator =(const CWorkerPointer &) = delete;
//! @}
//! Factory method.
//! Arguments are forwarded to the constructor of T. Strictly more exception-safe than calling the constructor with new.
template <typename... Ts>
@@ -360,8 +382,15 @@ namespace BlackMisc
bool isOwner() const { return m_strong; }
private:
void connect()
{
if (!m_strong) { return; }
m_guard = QObject::connect(m_strong.get(), &CWorkerBase::aboutToStart, [this] { m_strong.release(); });
}
std::unique_ptr<T> m_strong;
QPointer<T> m_weak;
CConnectionGuard m_guard;
};
}