diff options
author | Paul Lemire <paul.lemire@kdab.com> | 2016-05-20 17:11:37 +0200 |
---|---|---|
committer | Sean Harmer <sean.harmer@kdab.com> | 2016-05-23 16:31:55 +0000 |
commit | 073930f2ef030b3019c323999d910185f4639d9b (patch) | |
tree | 0c2bba252f7a92d4f3841fbe42eeca27e2a8a838 /src/input/frontend | |
parent | 15dace7c02bc5acdf02f94c8be08fec1a792383c (diff) | |
download | qt3d-073930f2ef030b3019c323999d910185f4639d9b.tar.gz |
Shared node bookkeeping
Any time a property references a QNode there is a risk that the node gets
destroyed and then the property is left pointing to a dangling pointer.
To handle such cases, setters of such properties are able to use a helper
that internally connect QObject::destroyed signal to a setter removal method.
Change-Id: I42428c851d0e3d2d88ab0cf6a5b75605334ec648
Task-number: QTBUG-53456
Reviewed-by: Sean Harmer <sean.harmer@kdab.com>
Diffstat (limited to 'src/input/frontend')
-rw-r--r-- | src/input/frontend/qabstractaxisinput.cpp | 11 | ||||
-rw-r--r-- | src/input/frontend/qaction.cpp | 6 | ||||
-rw-r--r-- | src/input/frontend/qactioninput.cpp | 8 | ||||
-rw-r--r-- | src/input/frontend/qaxis.cpp | 6 | ||||
-rw-r--r-- | src/input/frontend/qinputchord.cpp | 6 | ||||
-rw-r--r-- | src/input/frontend/qinputsequence.cpp | 6 | ||||
-rw-r--r-- | src/input/frontend/qkeyboardhandler.cpp | 8 | ||||
-rw-r--r-- | src/input/frontend/qlogicaldevice.cpp | 12 |
8 files changed, 63 insertions, 0 deletions
diff --git a/src/input/frontend/qabstractaxisinput.cpp b/src/input/frontend/qabstractaxisinput.cpp index 77966eb1d..ff7c69c12 100644 --- a/src/input/frontend/qabstractaxisinput.cpp +++ b/src/input/frontend/qabstractaxisinput.cpp @@ -73,10 +73,21 @@ void QAbstractAxisInput::setSourceDevice(QAbstractPhysicalDevice *sourceDevice) Q_D(QAbstractAxisInput); if (d->m_sourceDevice != sourceDevice) { + if (d->m_sourceDevice) + d->unregisterDestructionHelper(d->m_sourceDevice); + + // We need to add it as a child of the current node if it has been declared inline + // Or not previously added as a child of the current node so that + // 1) The backend gets notified about it's creation + // 2) When the current node is destroyed, it gets destroyed as well if (sourceDevice && !sourceDevice->parent()) sourceDevice->setParent(this); d->m_sourceDevice = sourceDevice; + // Ensures proper bookkeeping + if (d->m_sourceDevice) + d->registerDestructionHelper(sourceDevice, &QAbstractAxisInput::setSourceDevice, d->m_sourceDevice); + emit sourceDeviceChanged(sourceDevice); } } diff --git a/src/input/frontend/qaction.cpp b/src/input/frontend/qaction.cpp index 11a8d3ab6..2d98cc9e8 100644 --- a/src/input/frontend/qaction.cpp +++ b/src/input/frontend/qaction.cpp @@ -125,6 +125,9 @@ void QAction::addInput(QAbstractActionInput *input) if (!input->parent()) input->setParent(this); + // Ensures proper bookkeeping + d->registerDestructionHelper(input, &QAction::removeInput, d->m_inputs); + if (d->m_changeArbiter != nullptr) { const auto change = Qt3DCore::QPropertyNodeAddedChangePtr::create(id(), input); change->setPropertyName("input"); @@ -148,6 +151,9 @@ void QAction::removeInput(QAbstractActionInput *input) } d->m_inputs.removeOne(input); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(input); } } diff --git a/src/input/frontend/qactioninput.cpp b/src/input/frontend/qactioninput.cpp index d3441d284..0be75ec07 100644 --- a/src/input/frontend/qactioninput.cpp +++ b/src/input/frontend/qactioninput.cpp @@ -137,12 +137,20 @@ void QActionInput::setSourceDevice(QAbstractPhysicalDevice *sourceDevice) Q_D(QActionInput); if (d->m_sourceDevice != sourceDevice) { + if (d->m_sourceDevice) + d->unregisterDestructionHelper(d->m_sourceDevice); + // Check and set parent if needed // to force creation in the backend if (sourceDevice && !sourceDevice->parent()) sourceDevice->setParent(this); d->m_sourceDevice = sourceDevice; + + // Ensures proper bookkeeping + if (d->m_sourceDevice) + d->registerDestructionHelper(sourceDevice, &QActionInput::setSourceDevice, d->m_sourceDevice); + emit sourceDeviceChanged(sourceDevice); } } diff --git a/src/input/frontend/qaxis.cpp b/src/input/frontend/qaxis.cpp index a12b277e9..3b84e0205 100644 --- a/src/input/frontend/qaxis.cpp +++ b/src/input/frontend/qaxis.cpp @@ -83,6 +83,9 @@ void QAxis::addInput(QAbstractAxisInput *input) if (!input->parent()) input->setParent(this); + // Ensures proper bookkeeping + d->registerDestructionHelper(input, &QAxis::removeInput, d->m_inputs); + if (d->m_changeArbiter != nullptr) { const auto change = Qt3DCore::QPropertyNodeAddedChangePtr::create(id(), input); change->setPropertyName("input"); @@ -103,6 +106,9 @@ void QAxis::removeInput(QAbstractAxisInput *input) } d->m_inputs.removeOne(input); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(input); } } diff --git a/src/input/frontend/qinputchord.cpp b/src/input/frontend/qinputchord.cpp index a85efa0d2..8260e66da 100644 --- a/src/input/frontend/qinputchord.cpp +++ b/src/input/frontend/qinputchord.cpp @@ -152,6 +152,9 @@ void QInputChord::addChord(QAbstractActionInput *input) if (!d->m_chords.contains(input)) { d->m_chords.push_back(input); + // Ensures proper bookkeeping + d->registerDestructionHelper(input, &QInputChord::removeChord, d->m_chords); + if (!input->parent()) input->setParent(this); @@ -180,6 +183,9 @@ void QInputChord::removeChord(QAbstractActionInput *input) } d->m_chords.removeOne(input); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(input); } } diff --git a/src/input/frontend/qinputsequence.cpp b/src/input/frontend/qinputsequence.cpp index 1786a9584..27f440ec7 100644 --- a/src/input/frontend/qinputsequence.cpp +++ b/src/input/frontend/qinputsequence.cpp @@ -205,6 +205,9 @@ void QInputSequence::addSequence(QAbstractActionInput *input) if (!d->m_sequences.contains(input)) { d->m_sequences.push_back(input); + // Ensures proper bookkeeping + d->registerDestructionHelper(input, &QInputSequence::removeSequence, d->m_sequences); + if (!input->parent()) input->setParent(this); @@ -232,6 +235,9 @@ void QInputSequence::removeSequence(QAbstractActionInput *input) } d->m_sequences.removeOne(input); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(input); } } diff --git a/src/input/frontend/qkeyboardhandler.cpp b/src/input/frontend/qkeyboardhandler.cpp index a55e8ce9e..59128ad4d 100644 --- a/src/input/frontend/qkeyboardhandler.cpp +++ b/src/input/frontend/qkeyboardhandler.cpp @@ -196,10 +196,18 @@ void QKeyboardHandler::setSourceDevice(QKeyboardDevice *keyboardDevice) Q_D(QKeyboardHandler); if (d->m_keyboardDevice != keyboardDevice) { + if (d->m_keyboardDevice) + d->unregisterDestructionHelper(d->m_keyboardDevice); + if (keyboardDevice && !keyboardDevice->parent()) keyboardDevice->setParent(this); d->m_keyboardDevice = keyboardDevice; + + // Ensures proper bookkeeping + if (d->m_keyboardDevice) + d->registerDestructionHelper(keyboardDevice, &QKeyboardHandler::setSourceDevice, d->m_keyboardDevice); + emit sourceDeviceChanged(keyboardDevice); } } diff --git a/src/input/frontend/qlogicaldevice.cpp b/src/input/frontend/qlogicaldevice.cpp index f84b45001..90c2e4b05 100644 --- a/src/input/frontend/qlogicaldevice.cpp +++ b/src/input/frontend/qlogicaldevice.cpp @@ -171,6 +171,9 @@ void QLogicalDevice::addAction(QAction *action) if (!action->parent()) action->setParent(this); + // Ensures proper bookkeeping + d->registerDestructionHelper(action, &QLogicalDevice::removeAction, d->m_actions); + if (d->m_changeArbiter != nullptr) { const auto change = Qt3DCore::QPropertyNodeAddedChangePtr::create(id(), action); change->setPropertyName("action"); @@ -194,6 +197,9 @@ void QLogicalDevice::removeAction(QAction *action) } d->m_actions.removeOne(action); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(action); } } @@ -225,6 +231,9 @@ void QLogicalDevice::addAxis(QAxis *axis) if (!axis->parent()) axis->setParent(this); + // Ensures proper bookkeeping + d->registerDestructionHelper(axis, &QLogicalDevice::removeAxis, d->m_axes); + if (d->m_changeArbiter != nullptr) { const auto change = Qt3DCore::QPropertyNodeAddedChangePtr::create(id(), axis); change->setPropertyName("axis"); @@ -247,6 +256,9 @@ void QLogicalDevice::removeAxis(QAxis *axis) } d->m_axes.removeOne(axis); + + // Remove bookkeeping connection + d->unregisterDestructionHelper(axis); } } |