From de8a9dee5aa7c8db3b390c9a19f65c919d201c3c Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Fri, 25 Jul 2014 23:17:55 +0200 Subject: QPalette: add move constructor As with many other implicitly shared classes, efficient move semantics requires setting the d-pointer to nullptr, which then needs to be checked for in the dtor and the copy assignment operator. Change-Id: I654d181a1dfdd9a16e2f9fb96b57475cdd0b4561 Reviewed-by: J-P Nurmi Reviewed-by: Olivier Goffart --- src/gui/kernel/qpalette.cpp | 15 +++++++++++++-- src/gui/kernel/qpalette.h | 2 ++ tests/auto/gui/kernel/qpalette/tst_qpalette.cpp | 8 ++++++++ 3 files changed, 23 insertions(+), 2 deletions(-) diff --git a/src/gui/kernel/qpalette.cpp b/src/gui/kernel/qpalette.cpp index 62e555b821..52b0372ea8 100644 --- a/src/gui/kernel/qpalette.cpp +++ b/src/gui/kernel/qpalette.cpp @@ -642,12 +642,23 @@ QPalette::QPalette(const QPalette &p) d->ref.ref(); } +/*! + \fn QPalette::QPalette(QPalette &&other) + \since 5.4 + + Move-constructs a QPalette instance, making it point at the same + object that \a other was pointing to. + + After being moved from, you can only assign to or destroy \a other. + Any other operation will result in undefined behavior. +*/ + /*! Destroys the palette. */ QPalette::~QPalette() { - if(!d->ref.deref()) + if (d && !d->ref.deref()) delete d; } @@ -668,7 +679,7 @@ QPalette &QPalette::operator=(const QPalette &p) { p.d->ref.ref(); data = p.data; - if(!d->ref.deref()) + if (d && !d->ref.deref()) delete d; d = p.d; return *this; diff --git a/src/gui/kernel/qpalette.h b/src/gui/kernel/qpalette.h index 8d9754d388..8c344be1e6 100644 --- a/src/gui/kernel/qpalette.h +++ b/src/gui/kernel/qpalette.h @@ -70,6 +70,8 @@ public: ~QPalette(); QPalette &operator=(const QPalette &palette); #ifdef Q_COMPILER_RVALUE_REFS + QPalette(QPalette &&other) Q_DECL_NOTHROW + : d(other.d), data(other.data) { other.d = Q_NULLPTR; } inline QPalette &operator=(QPalette &&other) { for_faster_swapping_dont_use = other.for_faster_swapping_dont_use; diff --git a/tests/auto/gui/kernel/qpalette/tst_qpalette.cpp b/tests/auto/gui/kernel/qpalette/tst_qpalette.cpp index b2c0ff979c..662e35dfaf 100644 --- a/tests/auto/gui/kernel/qpalette/tst_qpalette.cpp +++ b/tests/auto/gui/kernel/qpalette/tst_qpalette.cpp @@ -106,6 +106,14 @@ void tst_QPalette::moveSemantics() src = control; // check moved-from 'src' can still be assigned to (doesn't crash) QVERIFY(src.isCopyOf(dst)); QVERIFY(src.isCopyOf(control)); + QPalette dst2(qMove(src)); // move construction + QVERIFY(!src.isCopyOf(dst)); + QVERIFY(!src.isCopyOf(dst2)); + QVERIFY(!src.isCopyOf(control)); + QCOMPARE(dst2, control); + QVERIFY(dst2.isCopyOf(dst)); + QVERIFY(dst2.isCopyOf(control)); + // check moved-from 'src' can still be destroyed (doesn't crash) #else QSKIP("Compiler doesn't support C++11 move semantics"); #endif -- cgit v1.2.3