diff --git a/src/advancebuttondialog.cpp b/src/advancebuttondialog.cpp index feebd5e0..978f3a34 100644 --- a/src/advancebuttondialog.cpp +++ b/src/advancebuttondialog.cpp @@ -28,6 +28,7 @@ #include "ui_advancebuttondialog.h" #include "event.h" #include "inputdevice.h" +//#include "logger.h" const int AdvanceButtonDialog::MINIMUMTURBO = 2; @@ -261,22 +262,29 @@ void AdvanceButtonDialog::connectButtonEvents(SimpleKeyGrabberButton *button) void AdvanceButtonDialog::updateSelectedSlot(int value) { + PadderCommon::lockInputDevices(); + SimpleKeyGrabberButton *grabbutton = static_cast(sender()); JoyButtonSlot *tempbuttonslot = grabbutton->getValue(); int index = ui->slotListWidget->currentRow(); // Stop all events on JoyButton - this->button->eventReset(); + //this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset"); this->button->setAssignedSlot(tempbuttonslot->getSlotCode(), tempbuttonslot->getSlotCodeAlias(), index, tempbuttonslot->getSlotMode()); updateSlotsScrollArea(value); + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::deleteSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); int itemcount = ui->slotListWidget->count(); @@ -293,10 +301,14 @@ void AdvanceButtonDialog::deleteSlot() changeTurboForSequences(); // Stop all events on JoyButton - button->eventReset(); + QMetaObject::invokeMethod(button, "eventReset", Qt::BlockingQueuedConnection); + //button->eventReset(); button->removeAssignedSlot(index); performStatsWidgetRefresh(ui->slotListWidget->currentItem()); + + PadderCommon::unlockInputDevices(); + emit slotsChanged(); } @@ -348,6 +360,8 @@ void AdvanceButtonDialog::insertSlot() if (slotTypeIndex == KBMouseSlot) { + PadderCommon::lockInputDevices(); + if (current != (count - 1)) { SimpleKeyGrabberButton *blankButton = new SimpleKeyGrabberButton(this); @@ -365,9 +379,15 @@ void AdvanceButtonDialog::insertSlot() connectButtonEvents(blankButton); blankButton->refreshButtonLabel(); - this->button->insertAssignedSlot(0, 0, current); + QMetaObject::invokeMethod(this->button, "insertAssignedSlot", + Qt::BlockingQueuedConnection, + Q_ARG(int, 0), Q_ARG(uint, 0), + Q_ARG(int, current)); + //this->button->insertAssignedSlot(0, 0, current); updateSlotsScrollArea(0); } + + PadderCommon::unlockInputDevices(); } else if (slotTypeIndex == CycleSlot) { @@ -421,6 +441,8 @@ void AdvanceButtonDialog::insertSlot() void AdvanceButtonDialog::insertPauseSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -429,15 +451,20 @@ void AdvanceButtonDialog::insertPauseSlot() { tempbutton->setValue(actionTime, JoyButtonSlot::JoyPause); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, JoyButtonSlot::JoyPause); updateSlotsScrollArea(actionTime); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertReleaseSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -446,15 +473,20 @@ void AdvanceButtonDialog::insertReleaseSlot() { tempbutton->setValue(actionTime, JoyButtonSlot::JoyRelease); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, JoyButtonSlot::JoyRelease); updateSlotsScrollArea(actionTime); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertHoldSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -463,15 +495,20 @@ void AdvanceButtonDialog::insertHoldSlot() { tempbutton->setValue(actionTime, JoyButtonSlot::JoyHold); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, JoyButtonSlot::JoyHold); updateSlotsScrollArea(actionTime); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertSetChangeSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -482,11 +519,14 @@ void AdvanceButtonDialog::insertSetChangeSlot() { tempbutton->setValue(setIndex, JoyButtonSlot::JoySetChange); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(setIndex, 0, index, JoyButtonSlot::JoySetChange); updateSlotsScrollArea(setIndex); } + + PadderCommon::unlockInputDevices(); } int AdvanceButtonDialog::actionTimeConvert() @@ -536,12 +576,17 @@ void AdvanceButtonDialog::updateActionTimeLabel() void AdvanceButtonDialog::clearAllSlots() { + PadderCommon::lockInputDevices(); + ui->slotListWidget->clear(); appendBlankKeyGrabber(); changeTurboForSequences(); - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); performStatsWidgetRefresh(ui->slotListWidget->currentItem()); + + PadderCommon::unlockInputDevices(); emit slotsChanged(); } @@ -591,20 +636,31 @@ void AdvanceButtonDialog::changeTurboForSequences() void AdvanceButtonDialog::insertCycleSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); tempbutton->setValue(1, JoyButtonSlot::JoyCycle); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); + /*QMetaObject::invokeMethod(this->button, "setAssignedSlot", Q_ARG(int, 1), + Q_ARG(uint, 0), Q_ARG(int, index), + Q_ARG(JoyButtonSlot::JoySlotInputAction, JoyButtonSlot::JoyCycle)); + */ this->button->setAssignedSlot(1, 0, index, JoyButtonSlot::JoyCycle); updateSlotsScrollArea(1); + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertDistanceSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -631,11 +687,14 @@ void AdvanceButtonDialog::insertDistanceSlot() tempbutton->setValue(testDistance, JoyButtonSlot::JoyDistance); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(testDistance, 0, index, JoyButtonSlot::JoyDistance); updateSlotsScrollArea(testDistance); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::placeNewSlot(JoyButtonSlot *slot) @@ -646,7 +705,8 @@ void AdvanceButtonDialog::placeNewSlot(JoyButtonSlot *slot) tempbutton->setValue(slot->getSlotCode(), slot->getSlotCodeAlias(), slot->getSlotMode()); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(slot->getSlotCode(), slot->getSlotCodeAlias(), index, @@ -786,6 +846,8 @@ void AdvanceButtonDialog::fillTimeComboBoxes() void AdvanceButtonDialog::insertMouseSpeedModSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -795,15 +857,20 @@ void AdvanceButtonDialog::insertMouseSpeedModSlot() tempbutton->setValue(tempMouseMod, JoyButtonSlot::JoyMouseSpeedMod); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(tempMouseMod, 0, index, JoyButtonSlot::JoyMouseSpeedMod); updateSlotsScrollArea(tempMouseMod); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertKeyPressSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -813,15 +880,20 @@ void AdvanceButtonDialog::insertKeyPressSlot() tempbutton->setValue(actionTime, JoyButtonSlot::JoyKeyPress); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, JoyButtonSlot::JoyKeyPress); updateSlotsScrollArea(actionTime); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertDelaySlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -830,15 +902,20 @@ void AdvanceButtonDialog::insertDelaySlot() { tempbutton->setValue(actionTime, JoyButtonSlot::JoyDelay); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, JoyButtonSlot::JoyDelay); updateSlotsScrollArea(actionTime); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertTextEntrySlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -847,16 +924,21 @@ void AdvanceButtonDialog::insertTextEntrySlot() { tempbutton->setValue(temp, JoyButtonSlot::JoyTextEntry); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(tempbutton->getValue(), index); tempbutton->setToolTip(temp); updateSlotsScrollArea(0); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::insertExecuteSlot() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -868,13 +950,16 @@ void AdvanceButtonDialog::insertExecuteSlot() { tempbutton->setValue(temp, JoyButtonSlot::JoyExecute); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(tempbutton->getValue(), index); tempbutton->setToolTip(temp); updateSlotsScrollArea(0); } } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::performStatsWidgetRefresh(QListWidgetItem *item) @@ -980,6 +1065,8 @@ void AdvanceButtonDialog::performStatsWidgetRefresh(QListWidgetItem *item) void AdvanceButtonDialog::checkSlotTimeUpdate() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -996,16 +1083,21 @@ void AdvanceButtonDialog::checkSlotTimeUpdate() tempbutton->setValue(actionTime, tempbuttonslot->getSlotMode()); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(actionTime, 0, index, tempbuttonslot->getSlotMode()); updateSlotsScrollArea(actionTime); } } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::checkSlotMouseModUpdate() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -1019,15 +1111,20 @@ void AdvanceButtonDialog::checkSlotMouseModUpdate() tempbutton->setValue(tempMouseMod, tempbuttonslot->getSlotMode()); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(tempMouseMod, 0, index, tempbuttonslot->getSlotMode()); updateSlotsScrollArea(tempMouseMod); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::checkSlotSetChangeUpdate() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -1041,16 +1138,21 @@ void AdvanceButtonDialog::checkSlotSetChangeUpdate() { tempbutton->setValue(setIndex, buttonslot->getSlotMode()); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(setIndex, 0, index, buttonslot->getSlotMode()); updateSlotsScrollArea(setIndex); } } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::checkSlotDistanceUpdate() { + PadderCommon::lockInputDevices(); + int index = ui->slotListWidget->currentRow(); SimpleKeyGrabberButton *tempbutton = ui->slotListWidget->currentItem() ->data(Qt::UserRole).value(); @@ -1082,12 +1184,15 @@ void AdvanceButtonDialog::checkSlotDistanceUpdate() tempbutton->setValue(testDistance, buttonslot->getSlotMode()); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(testDistance, 0, index, buttonslot->getSlotMode()); updateSlotsScrollArea(testDistance); } } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::updateWindowTitleButtonName() @@ -1318,6 +1423,8 @@ void AdvanceButtonDialog::setButtonTurboMode(int value) void AdvanceButtonDialog::showSelectProfileWindow() { + PadderCommon::lockInputDevices(); + AntiMicroSettings *settings = this->button->getParentSet()->getInputDevice()->getSettings(); QString lookupDir = PadderCommon::preferredProfileDir(settings); @@ -1330,12 +1437,15 @@ void AdvanceButtonDialog::showSelectProfileWindow() ->data(Qt::UserRole).value(); tempbutton->setValue(filename, JoyButtonSlot::JoyLoadProfile); // Stop all events on JoyButton - this->button->eventReset(); + QMetaObject::invokeMethod(this->button, "eventReset", Qt::BlockingQueuedConnection); + //this->button->eventReset(); this->button->setAssignedSlot(tempbutton->getValue(), index); tempbutton->setToolTip(filename); updateSlotsScrollArea(0); } + + PadderCommon::unlockInputDevices(); } void AdvanceButtonDialog::showFindExecutableWindow(bool) diff --git a/src/axiseditdialog.cpp b/src/axiseditdialog.cpp index dc16586c..c107bc4b 100644 --- a/src/axiseditdialog.cpp +++ b/src/axiseditdialog.cpp @@ -25,6 +25,7 @@ #include "event.h" #include "antkeymapper.h" #include "setjoystick.h" +#include "common.h" AxisEditDialog::AxisEditDialog(JoyAxis *axis, QWidget *parent) : QDialog(parent, Qt::Window), @@ -174,6 +175,8 @@ void AxisEditDialog::implementAxisPresets(int index) JoyButtonSlot *nbuttonslot = 0; JoyButtonSlot *pbuttonslot = 0; + PadderCommon::lockInputDevices(); + if (index == 1) { nbuttonslot = new JoyButtonSlot(JoyButtonSlot::MouseLeft, JoyButtonSlot::JoyMouseMovement, this); @@ -228,17 +231,22 @@ void AxisEditDialog::implementAxisPresets(int index) { JoyAxisButton *nbutton = axis->getNAxisButton(); JoyAxisButton *pbutton = axis->getPAxisButton(); - nbutton->clearSlotsEventReset(); + + QMetaObject::invokeMethod(nbutton, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //nbutton->clearSlotsEventReset(); refreshNButtonLabel(); - pbutton->clearSlotsEventReset(); + QMetaObject::invokeMethod(pbutton, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //pbutton->clearSlotsEventReset(); refreshPButtonLabel(); } if (nbuttonslot) { JoyAxisButton *button = axis->getNAxisButton(); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(nbuttonslot->getSlotCode(), nbuttonslot->getSlotCodeAlias(), nbuttonslot->getSlotMode()); refreshNButtonLabel(); nbuttonslot->deleteLater(); @@ -247,11 +255,15 @@ void AxisEditDialog::implementAxisPresets(int index) if (pbuttonslot) { JoyAxisButton *button = axis->getPAxisButton(); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(pbuttonslot->getSlotCode(), pbuttonslot->getSlotCodeAlias(), pbuttonslot->getSlotMode()); refreshPButtonLabel(); pbuttonslot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } void AxisEditDialog::updateDeadZoneBox(int value) diff --git a/src/buttoneditdialog.cpp b/src/buttoneditdialog.cpp index a9a3cdc6..123082d0 100644 --- a/src/buttoneditdialog.cpp +++ b/src/buttoneditdialog.cpp @@ -36,6 +36,7 @@ #include "antkeymapper.h" #include "eventhandlerfactory.h" #include "setjoystick.h" +#include "common.h" ButtonEditDialog::ButtonEditDialog(JoyButton *button, QWidget *parent) : QDialog(parent, Qt::Window), @@ -399,15 +400,22 @@ void ButtonEditDialog::closedAdvancedDialog() void ButtonEditDialog::processSlotAssignment(JoyButtonSlot *tempslot) { - button->clearSlotsEventReset(false); + PadderCommon::lockInputDevices(); + + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(tempslot->getSlotCode(), tempslot->getSlotCodeAlias(), tempslot->getSlotMode()); this->close(); tempslot->deleteLater(); + + PadderCommon::unlockInputDevices(); } void ButtonEditDialog::clearButtonSlots() { - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Q_ARG(bool, false)); + //button->clearSlotsEventReset(); } void ButtonEditDialog::sendSelectionFinished() diff --git a/src/common.cpp b/src/common.cpp index 8963632f..0fd7d833 100644 --- a/src/common.cpp +++ b/src/common.cpp @@ -123,4 +123,29 @@ namespace PadderCommon #endif qApp->installTranslator(translator); } + + void lockInputDevices() + { + editingLock.lockForWrite(); + editingBindings = true; + editingLock.unlock(); + + waitMutex.lock(); + //editingBindings = true; + waitThisOut.wait(&waitMutex); + } + + void unlockInputDevices() + { + editingLock.lockForWrite(); + editingBindings = false; + editingLock.unlock(); + + waitMutex.unlock(); + } + + QWaitCondition waitThisOut; + QMutex waitMutex; + QReadWriteLock editingLock; + bool editingBindings = false; } diff --git a/src/common.h b/src/common.h index 3fb356d1..2954b39d 100644 --- a/src/common.h +++ b/src/common.h @@ -24,6 +24,9 @@ #include #include #include +#include +#include +#include #include "config.h" #include "antimicrosettings.h" @@ -122,11 +125,18 @@ namespace PadderCommon QString("%1.%2").arg(ANTIMICRO_MAJOR_VERSION) .arg(ANTIMICRO_MINOR_VERSION); + extern QWaitCondition waitThisOut; + extern QMutex waitMutex; + extern bool editingBindings; + extern QReadWriteLock editingLock; + QString preferredProfileDir(AntiMicroSettings *settings); QStringList arguments(int &argc, char **argv); void reloadTranslations(QTranslator *translator, QTranslator *appTranslator, QString language); + void lockInputDevices(); + void unlockInputDevices(); } #endif // COMMON_H diff --git a/src/dpadcontextmenu.cpp b/src/dpadcontextmenu.cpp index c363342d..22ac5510 100644 --- a/src/dpadcontextmenu.cpp +++ b/src/dpadcontextmenu.cpp @@ -18,6 +18,7 @@ #include "dpadcontextmenu.h" #include "mousedialog/mousedpadsettingsdialog.h" #include "antkeymapper.h" +#include "common.h" DPadContextMenu::DPadContextMenu(JoyDPad *dpad, QWidget *parent) : QMenu(parent) @@ -161,6 +162,8 @@ void DPadContextMenu::setDPadMode() */ void DPadContextMenu::setDPadPreset() { + PadderCommon::lockInputDevices(); + QAction *action = static_cast(sender()); int item = action->data().toInt(); @@ -258,14 +261,17 @@ void DPadContextMenu::setDPadPreset() while (iter.hasNext()) { JoyDPadButton *button = iter.next().value(); - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); } } if (upButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upButtonSlot->getSlotCode(), upButtonSlot->getSlotCodeAlias(), upButtonSlot->getSlotMode()); upButtonSlot->deleteLater(); } @@ -273,7 +279,9 @@ void DPadContextMenu::setDPadPreset() if (downButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downButtonSlot->getSlotCode(), downButtonSlot->getSlotCodeAlias(), downButtonSlot->getSlotMode()); downButtonSlot->deleteLater(); } @@ -281,7 +289,9 @@ void DPadContextMenu::setDPadPreset() if (leftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeft); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(leftButtonSlot->getSlotCode(), leftButtonSlot->getSlotCodeAlias(), leftButtonSlot->getSlotMode()); leftButtonSlot->deleteLater(); } @@ -289,7 +299,9 @@ void DPadContextMenu::setDPadPreset() if (rightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRight); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(rightButtonSlot->getSlotCode(), rightButtonSlot->getSlotCodeAlias(), rightButtonSlot->getSlotMode()); rightButtonSlot->deleteLater(); } @@ -297,7 +309,9 @@ void DPadContextMenu::setDPadPreset() if (upLeftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeftUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upLeftButtonSlot->getSlotCode(), upLeftButtonSlot->getSlotCodeAlias(), upLeftButtonSlot->getSlotMode()); upLeftButtonSlot->deleteLater(); } @@ -305,7 +319,9 @@ void DPadContextMenu::setDPadPreset() if (upRightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRightUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upRightButtonSlot->getSlotCode(), upRightButtonSlot->getSlotCodeAlias(), upRightButtonSlot->getSlotMode()); upRightButtonSlot->deleteLater(); } @@ -313,7 +329,9 @@ void DPadContextMenu::setDPadPreset() if (downLeftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeftDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downLeftButtonSlot->getSlotCode(), downLeftButtonSlot->getSlotCodeAlias(), downLeftButtonSlot->getSlotMode()); downLeftButtonSlot->deleteLater(); } @@ -321,10 +339,14 @@ void DPadContextMenu::setDPadPreset() if (downRightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRightDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downRightButtonSlot->getSlotCode(), downRightButtonSlot->getSlotCodeAlias(), downRightButtonSlot->getSlotMode()); downRightButtonSlot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } /** diff --git a/src/dpadeditdialog.cpp b/src/dpadeditdialog.cpp index cac4deae..77fccb3f 100644 --- a/src/dpadeditdialog.cpp +++ b/src/dpadeditdialog.cpp @@ -25,6 +25,7 @@ #include "event.h" #include "antkeymapper.h" #include "setjoystick.h" +#include "common.h" DPadEditDialog::DPadEditDialog(JoyDPad *dpad, QWidget *parent) : QDialog(parent, Qt::Window), @@ -81,6 +82,8 @@ DPadEditDialog::~DPadEditDialog() void DPadEditDialog::implementPresets(int index) { + PadderCommon::lockInputDevices(); + JoyButtonSlot *upButtonSlot = 0; JoyButtonSlot *downButtonSlot = 0; JoyButtonSlot *leftButtonSlot = 0; @@ -175,14 +178,17 @@ void DPadEditDialog::implementPresets(int index) while (iter.hasNext()) { JoyDPadButton *button = iter.next().value(); - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); } } if (upButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upButtonSlot->getSlotCode(), upButtonSlot->getSlotCodeAlias(), upButtonSlot->getSlotMode()); upButtonSlot->deleteLater(); } @@ -190,7 +196,9 @@ void DPadEditDialog::implementPresets(int index) if (downButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downButtonSlot->getSlotCode(), downButtonSlot->getSlotCodeAlias(), downButtonSlot->getSlotMode()); downButtonSlot->deleteLater(); } @@ -198,7 +206,9 @@ void DPadEditDialog::implementPresets(int index) if (leftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeft); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(leftButtonSlot->getSlotCode(), leftButtonSlot->getSlotCodeAlias(), leftButtonSlot->getSlotMode()); leftButtonSlot->deleteLater(); } @@ -206,7 +216,9 @@ void DPadEditDialog::implementPresets(int index) if (rightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRight); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(rightButtonSlot->getSlotCode(), rightButtonSlot->getSlotCodeAlias(), rightButtonSlot->getSlotMode()); rightButtonSlot->deleteLater(); } @@ -214,7 +226,9 @@ void DPadEditDialog::implementPresets(int index) if (upLeftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeftUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upLeftButtonSlot->getSlotCode(), upLeftButtonSlot->getSlotCodeAlias(), upLeftButtonSlot->getSlotMode()); upLeftButtonSlot->deleteLater(); } @@ -222,7 +236,9 @@ void DPadEditDialog::implementPresets(int index) if (upRightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRightUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upRightButtonSlot->getSlotCode(), upRightButtonSlot->getSlotCodeAlias(), upRightButtonSlot->getSlotMode()); upRightButtonSlot->deleteLater(); } @@ -230,7 +246,9 @@ void DPadEditDialog::implementPresets(int index) if (downLeftButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadLeftDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downLeftButtonSlot->getSlotCode(), downLeftButtonSlot->getSlotCodeAlias(), downLeftButtonSlot->getSlotMode()); downLeftButtonSlot->deleteLater(); } @@ -238,10 +256,14 @@ void DPadEditDialog::implementPresets(int index) if (downRightButtonSlot) { JoyDPadButton *button = dpad->getJoyButton(JoyDPadButton::DpadRightDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downRightButtonSlot->getSlotCode(), downRightButtonSlot->getSlotCodeAlias(), downRightButtonSlot->getSlotMode()); downRightButtonSlot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } void DPadEditDialog::implementModes(int index) diff --git a/src/gamecontroller/gamecontroller.h b/src/gamecontroller/gamecontroller.h index e6de4f16..52b2b106 100644 --- a/src/gamecontroller/gamecontroller.h +++ b/src/gamecontroller/gamecontroller.h @@ -57,9 +57,6 @@ public: bool isRelevantGUID(QString tempGUID); - virtual void readConfig(QXmlStreamReader *xml); - virtual void writeConfig(QXmlStreamWriter *xml); - static const QString xmlName; protected: @@ -71,6 +68,8 @@ signals: public slots: + virtual void readConfig(QXmlStreamReader *xml); + virtual void writeConfig(QXmlStreamWriter *xml); protected slots: virtual void axisActivatedEvent(int setindex, int axisindex, int value); diff --git a/src/gamecontrollermappingdialog.cpp b/src/gamecontrollermappingdialog.cpp index 3f15e8c2..7534da48 100644 --- a/src/gamecontrollermappingdialog.cpp +++ b/src/gamecontrollermappingdialog.cpp @@ -106,6 +106,8 @@ GameControllerMappingDialog::GameControllerMappingDialog(InputDevice *device, An this->device = device; this->settings = settings; + PadderCommon::lockInputDevices(); + device->getActiveSetJoystick()->setIgnoreEventState(true); device->getActiveSetJoystick()->release(); @@ -142,6 +144,8 @@ GameControllerMappingDialog::GameControllerMappingDialog(InputDevice *device, An connect(ui->buttonMappingTableWidget, SIGNAL(itemSelectionChanged()), this, SLOT(changeButtonDisplay())); connect(ui->axisDeadZoneComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(changeAxisDeadZone(int))); connect(this, SIGNAL(finished(int)), this, SLOT(enableButtonEvents(int))); + + PadderCommon::unlockInputDevices(); } GameControllerMappingDialog::~GameControllerMappingDialog() @@ -431,9 +435,13 @@ void GameControllerMappingDialog::discardMapping(QAbstractButton *button) } else { + PadderCommon::lockInputDevices(); + connect(device, SIGNAL(rawButtonClick(int)), this, SLOT(buttonAssign(int))); connect(device, SIGNAL(rawAxisActivated(int,int)), this, SLOT(axisAssign(int,int))); connect(device, SIGNAL(rawDPadButtonClick(int,int)), this, SLOT(dpadAssign(int,int))); + + PadderCommon::unlockInputDevices(); } } } @@ -469,6 +477,8 @@ void GameControllerMappingDialog::enableDeviceConnections() void GameControllerMappingDialog::disableDeviceConnections() { + PadderCommon::lockInputDevices(); + disconnect(device, SIGNAL(rawButtonClick(int)), this, SLOT(buttonAssign(int))); disconnect(device, SIGNAL(rawAxisActivated(int,int)), this, SLOT(axisAssign(int,int))); for (int i=0; i < device->getActiveSetJoystick()->getNumberAxes(); i++) @@ -485,18 +495,24 @@ void GameControllerMappingDialog::disableDeviceConnections() disconnect(device, SIGNAL(rawButtonRelease(int)), this, SLOT(buttonRelease(int))); disconnect(device, SIGNAL(rawAxisReleased(int,int)), this, SLOT(axisRelease(int,int))); disconnect(device, SIGNAL(rawDPadButtonRelease(int,int)), this, SLOT(dpadRelease(int,int))); + + PadderCommon::unlockInputDevices(); } void GameControllerMappingDialog::enableButtonEvents(int code) { Q_UNUSED(code); + PadderCommon::lockInputDevices(); + //if (code == QDialogButtonBox::AcceptRole) //{ device->getActiveSetJoystick()->setIgnoreEventState(false); device->getActiveSetJoystick()->release(); device->getActiveSetJoystick()->setAxesDeadZones(&originalAxesDeadZones); //} + + PadderCommon::unlockInputDevices(); } QString GameControllerMappingDialog::generateSDLMappingString() @@ -606,11 +622,15 @@ void GameControllerMappingDialog::populateAxisDeadZoneComboBox() void GameControllerMappingDialog::changeAxisDeadZone(int index) { + PadderCommon::lockInputDevices(); + unsigned int value = ui->axisDeadZoneComboBox->itemData(index).toInt(); if (value >= 5000 && value <= 32000) { device->getActiveSetJoystick()->raiseAxesDeadZones(value); } + + PadderCommon::unlockInputDevices(); } void GameControllerMappingDialog::updateLastAxisLineEdit(int value) diff --git a/src/inputdaemon.cpp b/src/inputdaemon.cpp index 61c97235..6e014dff 100644 --- a/src/inputdaemon.cpp +++ b/src/inputdaemon.cpp @@ -23,13 +23,15 @@ #include "inputdaemon.h" #include "logger.h" +#include "common.h" const int InputDaemon::GAMECONTROLLERTRIGGERRELEASE = 16384; InputDaemon::InputDaemon(QMap *joysticks, AntiMicroSettings *settings, bool graphical, QObject *parent) : - QObject(parent) + QObject(parent), + pollResetTimer(this) { this->joysticks = joysticks; this->stopped = false; @@ -49,6 +51,7 @@ InputDaemon::InputDaemon(QMap *joysticks, if (graphical) { + connect(thread, SIGNAL(started()), this, SLOT(refreshJoysticks())); connect(thread, SIGNAL(started()), eventWorker, SLOT(performWork())); connect(eventWorker, SIGNAL(eventRaised()), this, SLOT(run())); @@ -72,8 +75,10 @@ InputDaemon::InputDaemon(QMap *joysticks, SLOT(resetActiveButtonMouseDistances())); thread->start(); } - - refreshJoysticks(); + else + { + refreshJoysticks(); + } } InputDaemon::~InputDaemon() @@ -99,10 +104,10 @@ void InputDaemon::startWorker() { if (!thread->isRunning()) { - connect(thread, SIGNAL(started()), eventWorker, SLOT(performWork())); - connect(eventWorker, SIGNAL(eventRaised()), this, SLOT(run())); + //connect(thread, SIGNAL(started()), eventWorker, SLOT(performWork())); + //connect(eventWorker, SIGNAL(eventRaised()), this, SLOT(run())); thread->start(); - pollResetTimer.start(); + //pollResetTimer.start(); } } @@ -131,7 +136,7 @@ void InputDaemon::run () if (stopped) { - if (joysticks->count() > 0) + if (joysticks->size() > 0) { emit complete(joysticks->value(0)); } @@ -213,6 +218,27 @@ void InputDaemon::refreshJoysticks() emit joysticksRefreshed(joysticks); } +void InputDaemon::deleteJoysticks() +{ + QMapIterator iter(*joysticks); + + while (iter.hasNext()) + { + InputDevice *joystick = iter.next().value(); + if (joystick) + { + delete joystick; + joystick = 0; + } + } + + joysticks->clear(); +#ifdef USE_SDL_2 + trackjoysticks.clear(); + trackcontrollers.clear(); +#endif +} + void InputDaemon::stop() { stopped = true; @@ -350,6 +376,18 @@ void InputDaemon::removeDevice(InputDevice *device) { if (device) { + PadderCommon::editingLock.lockForRead(); + bool isEditing = PadderCommon::editingBindings; + PadderCommon::editingLock.unlock(); + + if (isEditing) + { + QMutex *dismutex = &PadderCommon::waitMutex; + dismutex->lock(); + PadderCommon::waitThisOut.wakeAll(); + dismutex->unlock(); + } + SDL_JoystickID deviceID = device->getSDLJoystickID(); joysticks->remove(deviceID); @@ -358,7 +396,7 @@ void InputDaemon::removeDevice(InputDevice *device) refreshIndexes(); - emit deviceRemoved(deviceID); + emit deviceRemoved(static_cast(deviceID)); device->deleteLater(); } } @@ -907,6 +945,8 @@ void InputDaemon::secondInputPass(QQueue *sdlEventQueue) Logger::LogInfo(QString("Removing joystick #%1 [%2]") .arg(device->getRealJoyNumber()) .arg(QTime::currentTime().toString("hh:mm:ss.zzz"))); + + //activeDevices.remove(event.jdevice.which); removeDevice(device); } @@ -933,7 +973,7 @@ void InputDaemon::secondInputPass(QQueue *sdlEventQueue) break; } - // Active possible queued stick and vdpad events. + // Active possible queued events. QHashIterator activeDevIter(activeDevices); while (activeDevIter.hasNext()) { @@ -944,6 +984,12 @@ void InputDaemon::secondInputPass(QQueue *sdlEventQueue) tempDevice->activatePossibleVDPadEvents(); tempDevice->activatePossibleButtonEvents(); } + + if (JoyButton::shouldInvokeMouseEvents()) + { + // Do not wait for next event loop run. Execute immediately. + JoyButton::invokeMouseEvents(); + } } } diff --git a/src/inputdaemon.h b/src/inputdaemon.h index df099c58..011c52e8 100644 --- a/src/inputdaemon.h +++ b/src/inputdaemon.h @@ -47,8 +47,6 @@ public: explicit InputDaemon (QMap *joysticks, AntiMicroSettings *settings, bool graphical=true, QObject *parent=0); ~InputDaemon(); - void startWorker(); - protected: InputDeviceBitArrayStatus* createOrGrabBitStatusEntry( QHash *statusHash, @@ -92,7 +90,7 @@ signals: #ifdef USE_SDL_2 void deviceUpdated(int index, InputDevice *device); - void deviceRemoved(SDL_JoystickID deviceID); + void deviceRemoved(int deviceID); void deviceAdded(InputDevice *device); #endif @@ -102,6 +100,9 @@ public slots: void refresh(); void refreshJoystick(InputDevice *joystick); void refreshJoysticks(); + void deleteJoysticks(); + void startWorker(); + #ifdef USE_SDL_2 void refreshMapping(QString mapping, InputDevice *device); void removeDevice(InputDevice *device); diff --git a/src/inputdevice.h b/src/inputdevice.h index 5f5fcf43..e0a6833e 100644 --- a/src/inputdevice.h +++ b/src/inputdevice.h @@ -86,9 +86,6 @@ public: void setDPadName(int dpadIndex, QString tempName); void setVDPadName(int vdpadIndex, QString tempName); - virtual void readConfig(QXmlStreamReader *xml); - virtual void writeConfig(QXmlStreamWriter *xml); - virtual int getNumberRawButtons() = 0; virtual int getNumberRawAxes() = 0; virtual int getNumberRawHats() = 0; @@ -115,7 +112,6 @@ public: void sendLoadProfileRequest(QString location); AntiMicroSettings *getSettings(); - void transferReset(); void reInitButtons(); void activatePossiblePendingEvents(); @@ -180,6 +176,7 @@ signals: public slots: void reset(); + void transferReset(); void resetButtonDownCount(); void setActiveSetNumber(int index); void changeSetButtonAssociation(int button_index, int originset, int newset, int mode); @@ -191,6 +188,9 @@ public slots: void profileEdited(); void setProfileName(QString value); + virtual void readConfig(QXmlStreamReader *xml); + virtual void writeConfig(QXmlStreamWriter *xml); + void establishPropertyUpdatedConnection(); void disconnectPropertyUpdatedConnection(); diff --git a/src/joyaxiscontextmenu.cpp b/src/joyaxiscontextmenu.cpp index f9549c5e..3bb4a5ae 100644 --- a/src/joyaxiscontextmenu.cpp +++ b/src/joyaxiscontextmenu.cpp @@ -18,6 +18,7 @@ #include "joyaxiscontextmenu.h" #include "mousedialog/mouseaxissettingsdialog.h" #include "antkeymapper.h" +#include "common.h" JoyAxisContextMenu::JoyAxisContextMenu(JoyAxis *axis, QWidget *parent) : QMenu(parent) @@ -222,6 +223,8 @@ int JoyAxisContextMenu::getPresetIndex() void JoyAxisContextMenu::setAxisPreset() { + PadderCommon::lockInputDevices(); + QAction *action = static_cast(sender()); int item = action->data().toInt(); @@ -282,14 +285,18 @@ void JoyAxisContextMenu::setAxisPreset() { JoyAxisButton *nbutton = axis->getNAxisButton(); JoyAxisButton *pbutton = axis->getPAxisButton(); - nbutton->clearSlotsEventReset(); - pbutton->clearSlotsEventReset(); + QMetaObject::invokeMethod(nbutton, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + QMetaObject::invokeMethod(pbutton, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //nbutton->clearSlotsEventReset(); + //pbutton->clearSlotsEventReset(); } if (nbuttonslot) { JoyAxisButton *button = axis->getNAxisButton(); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(nbuttonslot->getSlotCode(), nbuttonslot->getSlotCodeAlias(), nbuttonslot->getSlotMode()); nbuttonslot->deleteLater(); } @@ -297,10 +304,14 @@ void JoyAxisContextMenu::setAxisPreset() if (pbuttonslot) { JoyAxisButton *button = axis->getPAxisButton(); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(pbuttonslot->getSlotCode(), pbuttonslot->getSlotCodeAlias(), pbuttonslot->getSlotMode()); pbuttonslot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } void JoyAxisContextMenu::openMouseSettingsDialog() @@ -392,13 +403,16 @@ void JoyAxisContextMenu::setTriggerPreset() else if (item == 2) { JoyAxisButton *pbutton = axis->getPAxisButton(); - pbutton->clearSlotsEventReset(); + QMetaObject::invokeMethod(pbutton, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //pbutton->clearSlotsEventReset(); } if (pbuttonslot) { JoyAxisButton *button = axis->getPAxisButton(); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(pbuttonslot->getSlotCode(), pbuttonslot->getSlotCodeAlias(), pbuttonslot->getSlotMode()); pbuttonslot->deleteLater(); } diff --git a/src/joybutton.cpp b/src/joybutton.cpp index 0404d334..9d34c7c1 100644 --- a/src/joybutton.cpp +++ b/src/joybutton.cpp @@ -612,6 +612,8 @@ bool JoyButton::distanceEvent() if (slotiter) { + QReadLocker tempLocker(&assignmentsLock); + bool distanceFound = containsDistanceSlots(); if (distanceFound) @@ -716,7 +718,10 @@ void JoyButton::createDeskEvent() if (!slotiter) { - slotiter = new QListIterator (assignments); + assignmentsLock.lockForRead(); + slotiter = new QListIterator(assignments); + assignmentsLock.unlock(); + distanceEvent(); } else if (!slotiter->hasPrevious()) @@ -729,7 +734,9 @@ void JoyButton::createDeskEvent() distanceEvent(); } + assignmentsLock.lockForRead(); activateSlots(); + assignmentsLock.unlock(); if (currentCycle) { @@ -745,6 +752,8 @@ void JoyButton::activateSlots() { if (slotiter) { + QWriteLocker tempLocker(&activeZoneLock); + bool exit = false; //bool delaySequence = checkForDelaySequence(); bool delaySequence = false; @@ -826,31 +835,12 @@ void JoyButton::activateSlots() { if (!staticMouseEventTimer.isActive() || staticMouseEventTimer.interval() == IDLEMOUSEREFRESHRATE) { - /*int tempRate = 0; - int mousePollTime = lastMouseTime.elapsed(); - if (mousePollTime <= mouseRefreshRate) - { - tempRate = qMax(0, mouseRefreshRate - mousePollTime); - } - else - { - mousePollTime = mousePollTime % mouseRefreshRate; - if (mousePollTime == 0) - { - tempRate = mousePollTime; - } - else - { - tempRate = mouseRefreshRate - mousePollTime; - } - }*/ + int tempRate = qBound(0, mouseRefreshRate - gamepadRefreshRate, MAXIMUMMOUSEREFRESHRATE); + //Logger::LogInfo(QString("STARTING OVER: %1 %2").arg(QTime::currentTime().toString("hh:mm:ss.zzz")).arg(tempRate)); + staticMouseEventTimer.start(tempRate); lastMouseTime.restart(); accelExtraDurationTime.restart(); - int tempRate = qBound(0, mouseRefreshRate - gamepadRefreshRate, MAXIMUMMOUSEREFRESHRATE); - //Logger::LogInfo(QString("STARTING OVER: %1 %2").arg(QTime::currentTime().toString("hh:mm:ss.zzz")).arg(tempRate)); - - staticMouseEventTimer.start(tempRate); } } } @@ -2395,16 +2385,20 @@ QString JoyButton::buildActiveZoneSummary(QList &tempList) QList JoyButton::getActiveZoneList() { + QReadLocker *tempLocker = 0; + QListIterator activeSlotsIter(activeSlots); QListIterator assignmentsIter(assignments); QListIterator *iter = 0; - bool slotsActive = !activeSlots.isEmpty(); - if (slotsActive) + //bool slotsActive = !activeSlots.isEmpty(); + if (getButtonState()) { + tempLocker = new QReadLocker(&activeZoneLock); iter = &activeSlotsIter; } else { + tempLocker = new QReadLocker(&assignmentsLock); iter = &assignmentsIter; if (previousCycle) { @@ -2457,6 +2451,9 @@ QList JoyButton::getActiveZoneList() } } + delete tempLocker; + tempLocker = 0; + return tempSlotList; } @@ -2557,6 +2554,8 @@ bool JoyButton::setAssignedSlot(int code, JoyButtonSlot::JoySlotInputAction mode bool JoyButton::setAssignedSlot(int code, unsigned int alias, JoyButtonSlot::JoySlotInputAction mode) { + assignmentsLock.lockForWrite(); + bool slotInserted = false; JoyButtonSlot *slot = new JoyButtonSlot(code, alias, mode, this); if (slot->getSlotMode() == JoyButtonSlot::JoyDistance) @@ -2591,6 +2590,8 @@ bool JoyButton::setAssignedSlot(int code, unsigned int alias, } } + assignmentsLock.unlock(); + return slotInserted; } @@ -2631,6 +2632,8 @@ bool JoyButton::setAssignedSlot(int code, unsigned int alias, int index, if (permitSlot) { + assignmentsLock.lockForWrite(); + if (index >= 0 && index < assignments.count()) { // Insert slot and move existing slots. @@ -2650,6 +2653,8 @@ bool JoyButton::setAssignedSlot(int code, unsigned int alias, int index, } checkTurboCondition(slot); + assignmentsLock.unlock(); + emit slotsChanged(); } else @@ -2701,6 +2706,8 @@ bool JoyButton::insertAssignedSlot(int code, unsigned int alias, int index, if (permitSlot) { + assignmentsLock.lockForWrite(); + if (index >= 0 && index < assignments.count()) { // Insert new slot into list. Move old slots if needed. @@ -2713,6 +2720,8 @@ bool JoyButton::insertAssignedSlot(int code, unsigned int alias, int index, } checkTurboCondition(slot); + + assignmentsLock.unlock(); emit slotsChanged(); } else @@ -2763,8 +2772,10 @@ bool JoyButton::insertAssignedSlot(JoyButtonSlot *newSlot) if (permitSlot) { + assignmentsLock.lockForWrite(); checkTurboCondition(newSlot); assignments.append(newSlot); + assignmentsLock.unlock(); emit slotsChanged(); } @@ -2809,6 +2820,8 @@ bool JoyButton::setAssignedSlot(JoyButtonSlot *otherSlot, int index) if (permitSlot) { + assignmentsLock.lockForWrite(); + checkTurboCondition(newslot); if (index >= 0 && index < assignments.count()) @@ -2830,6 +2843,8 @@ bool JoyButton::setAssignedSlot(JoyButtonSlot *otherSlot, int index) assignments.append(newslot); } + assignmentsLock.unlock(); + emit slotsChanged(); } else @@ -3459,8 +3474,6 @@ void JoyButton::releaseDeskEvent(bool skipsetchange) this->currentDistance = 0; this->currentKeyPress = 0; quitEvent = true; - - emit activeZoneChanged(); } @@ -3580,6 +3593,8 @@ void JoyButton::removeAssignedSlot(int index) void JoyButton::clearSlotsEventReset(bool clearSignalEmit) { + QWriteLocker tempAssignLocker(&assignmentsLock); + turboTimer.stop(); pauseWaitTimer.stop(); createDeskTimer.stop(); @@ -3631,6 +3646,8 @@ void JoyButton::clearSlotsEventReset(bool clearSignalEmit) void JoyButton::eventReset() { + QWriteLocker tempAssignLocker(&assignmentsLock); + turboTimer.stop(); pauseWaitTimer.stop(); createDeskTimer.stop(); @@ -3682,6 +3699,8 @@ void JoyButton::releaseActiveSlots() { if (!activeSlots.isEmpty()) { + QWriteLocker tempLocker(&activeZoneLock); + bool changeRepeatState = false; QListIterator iter(activeSlots); @@ -3937,10 +3956,12 @@ void JoyButton::releaseActiveSlots() if (pendingMouseButtons.length() == 0 && cursorXSpeeds.length() == 0 && springXSpeeds.length() == 0) { + //staticMouseEventTimer.setInterval(IDLEMOUSEREFRESHRATE); cursorRemainderX = 0; cursorRemainderY = 0; } + emit activeZoneChanged(); #ifdef Q_OS_WIN BaseEventHandler *handler = EventHandlerFactory::getInstance()->handler(); @@ -5513,3 +5534,45 @@ void JoyButton::restartLastMouseTime() { lastMouseTime.restart(); } + +void JoyButton::setStaticMouseThread(QThread *thread) +{ + //disconnect(&staticMouseEventTimer, 0, 0, 0); + + int oldInterval = staticMouseEventTimer.interval(); + staticMouseEventTimer.stop(); + staticMouseEventTimer.moveToThread(thread); + mouseHelper.moveToThread(thread); + + // Only one connection will be made for each. + //connect(&staticMouseEventTimer, SIGNAL(timeout()), &mouseHelper, + // SLOT(mouseEvent()), Qt::UniqueConnection); + + staticMouseEventTimer.start(oldInterval); + lastMouseTime.start(); +} + +bool JoyButton::shouldInvokeMouseEvents() +{ + bool result = false; + + if (pendingMouseButtons.size() > 0 && staticMouseEventTimer.isActive()) + { + int timerInterval = staticMouseEventTimer.interval(); + if (timerInterval == 0) + { + result = true; + } + else if (lastMouseTime.hasExpired(timerInterval)) + { + result = true; + } + } + + return result; +} + +void JoyButton::invokeMouseEvents() +{ + mouseHelper.mouseEvent(); +} diff --git a/src/joybutton.h b/src/joybutton.h index 9431393f..aa5c23af 100644 --- a/src/joybutton.h +++ b/src/joybutton.h @@ -26,6 +26,7 @@ #include #include #include +#include #include #include @@ -80,8 +81,7 @@ public: bool setAssignedSlot(int code, unsigned int alias, int index, JoyButtonSlot::JoySlotInputAction mode=JoyButtonSlot::JoyKeyboard); - bool insertAssignedSlot(int code, unsigned int alias, int index, - JoyButtonSlot::JoySlotInputAction mode=JoyButtonSlot::JoyKeyboard); + bool setAssignedSlot(JoyButtonSlot *otherSlot, int index); void removeAssignedSlot(int index); @@ -226,6 +226,11 @@ public: static void restartLastMouseTime(); + static void setStaticMouseThread(QThread *thread); + + static bool shouldInvokeMouseEvents(); + static void invokeMouseEvents(); + static const QString xmlName; // Define default values for many properties. @@ -463,6 +468,9 @@ protected: bool pendingEvent; bool pendingIgnoreSets; + QReadWriteLock activeZoneLock; + QReadWriteLock assignmentsLock; + static double mouseSpeedModifier; static QList mouseSpeedModList; @@ -533,6 +541,9 @@ public slots: virtual void clearSlotsEventReset(bool clearSignalEmit=true); virtual void eventReset(); + bool insertAssignedSlot(int code, unsigned int alias, int index, + JoyButtonSlot::JoySlotInputAction mode=JoyButtonSlot::JoyKeyboard); + void establishMouseTimerConnections(); void establishPropertyUpdatedConnections(); void disconnectPropertyUpdatedConnections(); diff --git a/src/joybuttoncontextmenu.cpp b/src/joybuttoncontextmenu.cpp index fac8e15e..ca7edad2 100644 --- a/src/joybuttoncontextmenu.cpp +++ b/src/joybuttoncontextmenu.cpp @@ -18,10 +18,12 @@ //#include #include -#include "inputdevice.h" - #include "joybuttoncontextmenu.h" +#include "inputdevice.h" +#include "common.h" + + JoyButtonContextMenu::JoyButtonContextMenu(JoyButton *button, QWidget *parent) : QMenu(parent) { @@ -163,5 +165,8 @@ void JoyButtonContextMenu::disableSetMode() void JoyButtonContextMenu::clearButton() { - button->clearSlotsEventReset(); + PadderCommon::lockInputDevices(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); + PadderCommon::unlockInputDevices(); } diff --git a/src/joycontrolstickbuttonpushbutton.cpp b/src/joycontrolstickbuttonpushbutton.cpp index 46e799d7..ce1f0597 100644 --- a/src/joycontrolstickbuttonpushbutton.cpp +++ b/src/joycontrolstickbuttonpushbutton.cpp @@ -19,6 +19,7 @@ #include "joycontrolstickbuttonpushbutton.h" #include "joybuttoncontextmenu.h" +#include "joycontrolstick.h" JoyControlStickButtonPushButton::JoyControlStickButtonPushButton(JoyControlStickButton *button, bool displayNames, QWidget *parent) : FlashButtonWidget(displayNames, parent) @@ -36,6 +37,8 @@ JoyControlStickButtonPushButton::JoyControlStickButtonPushButton(JoyControlStick connect(button, SIGNAL(slotsChanged()), this, SLOT(refreshLabel())); connect(button, SIGNAL(propertyUpdated()), this, SLOT(refreshLabel())); connect(button, SIGNAL(activeZoneChanged()), this, SLOT(refreshLabel()), Qt::QueuedConnection); + connect(button->getStick()->getModifierButton(), SIGNAL(activeZoneChanged()), + this, SLOT(refreshLabel())); } JoyControlStickButton* JoyControlStickButtonPushButton::getButton() diff --git a/src/joycontrolstickcontextmenu.cpp b/src/joycontrolstickcontextmenu.cpp index 1294895d..998721bc 100644 --- a/src/joycontrolstickcontextmenu.cpp +++ b/src/joycontrolstickcontextmenu.cpp @@ -21,6 +21,7 @@ #include "mousedialog/mousecontrolsticksettingsdialog.h" #include "antkeymapper.h" +#include "common.h" JoyControlStickContextMenu::JoyControlStickContextMenu(JoyControlStick *stick, QWidget *parent) : QMenu(parent) @@ -153,6 +154,8 @@ void JoyControlStickContextMenu::setStickMode() void JoyControlStickContextMenu::setStickPreset() { + PadderCommon::lockInputDevices(); + QAction *action = static_cast(sender()); int item = action->data().toInt(); @@ -258,7 +261,8 @@ void JoyControlStickContextMenu::setStickPreset() while (iter.hasNext()) { JoyControlStickButton *button = iter.next().value(); - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); } stick->setDiagonalRange(45); @@ -267,7 +271,9 @@ void JoyControlStickContextMenu::setStickPreset() if (upButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upButtonSlot->getSlotCode(), upButtonSlot->getSlotCodeAlias(), upButtonSlot->getSlotMode()); upButtonSlot->deleteLater(); } @@ -275,7 +281,9 @@ void JoyControlStickContextMenu::setStickPreset() if (downButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downButtonSlot->getSlotCode(), downButtonSlot->getSlotCodeAlias(), downButtonSlot->getSlotMode()); downButtonSlot->deleteLater(); } @@ -283,7 +291,9 @@ void JoyControlStickContextMenu::setStickPreset() if (leftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeft); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(leftButtonSlot->getSlotCode(), leftButtonSlot->getSlotCodeAlias(), leftButtonSlot->getSlotMode()); leftButtonSlot->deleteLater(); } @@ -291,7 +301,9 @@ void JoyControlStickContextMenu::setStickPreset() if (rightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRight); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(rightButtonSlot->getSlotCode(), rightButtonSlot->getSlotCodeAlias(), rightButtonSlot->getSlotMode()); rightButtonSlot->deleteLater(); } @@ -299,7 +311,9 @@ void JoyControlStickContextMenu::setStickPreset() if (upLeftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeftUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upLeftButtonSlot->getSlotCode(), upLeftButtonSlot->getSlotCodeAlias(), upLeftButtonSlot->getSlotMode()); upLeftButtonSlot->deleteLater(); } @@ -307,7 +321,9 @@ void JoyControlStickContextMenu::setStickPreset() if (upRightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRightUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upRightButtonSlot->getSlotCode(), upRightButtonSlot->getSlotCodeAlias(), upRightButtonSlot->getSlotMode()); upRightButtonSlot->deleteLater(); } @@ -315,7 +331,9 @@ void JoyControlStickContextMenu::setStickPreset() if (downLeftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeftDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downLeftButtonSlot->getSlotCode(), downLeftButtonSlot->getSlotCodeAlias(), downLeftButtonSlot->getSlotMode()); downLeftButtonSlot->deleteLater(); } @@ -323,10 +341,14 @@ void JoyControlStickContextMenu::setStickPreset() if (downRightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRightDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downRightButtonSlot->getSlotCode(), downRightButtonSlot->getSlotCodeAlias(), downRightButtonSlot->getSlotMode()); downRightButtonSlot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } int JoyControlStickContextMenu::getPresetIndex() diff --git a/src/joycontrolstickeditdialog.cpp b/src/joycontrolstickeditdialog.cpp index be0fc998..7a837e5c 100644 --- a/src/joycontrolstickeditdialog.cpp +++ b/src/joycontrolstickeditdialog.cpp @@ -26,6 +26,7 @@ #include "antkeymapper.h" #include "setjoystick.h" #include "buttoneditdialog.h" +#include "common.h" JoyControlStickEditDialog::JoyControlStickEditDialog(JoyControlStick *stick, QWidget *parent) : QDialog(parent, Qt::Window), @@ -141,6 +142,8 @@ JoyControlStickEditDialog::~JoyControlStickEditDialog() void JoyControlStickEditDialog::implementPresets(int index) { + PadderCommon::lockInputDevices(); + JoyButtonSlot *upButtonSlot = 0; JoyButtonSlot *downButtonSlot = 0; JoyButtonSlot *leftButtonSlot = 0; @@ -243,7 +246,8 @@ void JoyControlStickEditDialog::implementPresets(int index) while (iter.hasNext()) { JoyControlStickButton *button = iter.next().value(); - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); } ui->diagonalRangeSlider->setValue(45); @@ -252,7 +256,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (upButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upButtonSlot->getSlotCode(), upButtonSlot->getSlotCodeAlias(), upButtonSlot->getSlotMode()); upButtonSlot->deleteLater(); } @@ -260,7 +266,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (downButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downButtonSlot->getSlotCode(), downButtonSlot->getSlotCodeAlias(), downButtonSlot->getSlotMode()); downButtonSlot->deleteLater(); } @@ -268,7 +276,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (leftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeft); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(leftButtonSlot->getSlotCode(), leftButtonSlot->getSlotCodeAlias(), leftButtonSlot->getSlotMode()); leftButtonSlot->deleteLater(); } @@ -276,7 +286,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (rightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRight); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(rightButtonSlot->getSlotCode(), rightButtonSlot->getSlotCodeAlias(), rightButtonSlot->getSlotMode()); rightButtonSlot->deleteLater(); } @@ -284,7 +296,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (upLeftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeftUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upLeftButtonSlot->getSlotCode(), upLeftButtonSlot->getSlotCodeAlias(), upLeftButtonSlot->getSlotMode()); upLeftButtonSlot->deleteLater(); } @@ -292,7 +306,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (upRightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRightUp); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(upRightButtonSlot->getSlotCode(), upRightButtonSlot->getSlotCodeAlias(), upRightButtonSlot->getSlotMode()); upRightButtonSlot->deleteLater(); } @@ -300,7 +316,9 @@ void JoyControlStickEditDialog::implementPresets(int index) if (downLeftButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickLeftDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downLeftButtonSlot->getSlotCode(), downLeftButtonSlot->getSlotCodeAlias(), downLeftButtonSlot->getSlotMode()); downLeftButtonSlot->deleteLater(); } @@ -308,10 +326,14 @@ void JoyControlStickEditDialog::implementPresets(int index) if (downRightButtonSlot) { JoyControlStickButton *button = stick->getDirectionButton(JoyControlStick::StickRightDown); - button->clearSlotsEventReset(false); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection, + Q_ARG(bool, false)); + //button->clearSlotsEventReset(false); button->setAssignedSlot(downRightButtonSlot->getSlotCode(), downRightButtonSlot->getSlotCodeAlias(), downRightButtonSlot->getSlotMode()); downRightButtonSlot->deleteLater(); } + + PadderCommon::unlockInputDevices(); } void JoyControlStickEditDialog::refreshStickStats(int x, int y) diff --git a/src/joytabwidget.cpp b/src/joytabwidget.cpp index f875628b..dbb6bf6d 100644 --- a/src/joytabwidget.cpp +++ b/src/joytabwidget.cpp @@ -669,6 +669,8 @@ void JoyTabWidget::saveConfigFile() void JoyTabWidget::resetJoystick() { + PadderCommon::lockInputDevices(); + int currentIndex = configBox->currentIndex(); if (currentIndex != 0) { @@ -677,8 +679,10 @@ void JoyTabWidget::resetJoystick() removeCurrentButtons(); //joystick->reset(); joystick->revertProfileEdited(); - joystick->transferReset(); - joystick->reInitButtons(); + QMetaObject::invokeMethod(joystick, "transferReset", Qt::BlockingQueuedConnection); + //joystick->transferReset(); + QMetaObject::invokeMethod(joystick, "reInitButtons", Qt::BlockingQueuedConnection); + //joystick->reInitButtons(); XMLConfigReader reader; reader.setFileName(filename); @@ -722,14 +726,19 @@ void JoyTabWidget::resetJoystick() removeCurrentButtons(); joystick->revertProfileEdited(); //joystick->reset(); - joystick->transferReset(); - joystick->reInitButtons(); + + QMetaObject::invokeMethod(joystick, "transferReset", Qt::BlockingQueuedConnection); + //joystick->transferReset(); + QMetaObject::invokeMethod(joystick, "reInitButtons", Qt::BlockingQueuedConnection); + //joystick->reInitButtons(); fillButtons(); refreshSetButtons(); refreshCopySetActions(); } configBox->setItemIcon(currentIndex, QIcon()); + + PadderCommon::unlockInputDevices(); } void JoyTabWidget::saveAsConfig() @@ -834,6 +843,8 @@ void JoyTabWidget::saveAsConfig() void JoyTabWidget::changeJoyConfig(int index) { + PadderCommon::lockInputDevices(); + disconnect(joystick, SIGNAL(profileUpdated()), this, SLOT(displayProfileEditNotification())); QString filename; @@ -849,7 +860,9 @@ void JoyTabWidget::changeJoyConfig(int index) if (joystick->getActiveSetNumber() != 0) { - joystick->setActiveSetNumber(0); + QMetaObject::invokeMethod(joystick, "setActiveSetNumber", Qt::BlockingQueuedConnection, + Q_ARG(int, 0)); + //joystick->setActiveSetNumber(0); changeCurrentSet(0); } @@ -908,10 +921,14 @@ void JoyTabWidget::changeJoyConfig(int index) } //joystick->reset(); - joystick->transferReset(); + + QMetaObject::invokeMethod(joystick, "transferReset", Qt::BlockingQueuedConnection); + //joystick->transferReset(); joystick->resetButtonDownCount(); emit forceTabUnflash(this); - joystick->reInitButtons(); + + QMetaObject::invokeMethod(joystick, "reInitButtons", Qt::BlockingQueuedConnection); + //joystick->reInitButtons(); fillButtons(); refreshSetButtons(); @@ -924,6 +941,8 @@ void JoyTabWidget::changeJoyConfig(int index) comboBoxIndex = index; connect(joystick, SIGNAL(profileUpdated()), this, SLOT(displayProfileEditNotification())); + + PadderCommon::unlockInputDevices(); } void JoyTabWidget::saveSettings() @@ -1155,7 +1174,7 @@ void JoyTabWidget::loadSettings(bool forceRefresh) QHash* JoyTabWidget::recentConfigs() { - QHash *temp = new QHash (); + QHash *temp = new QHash(); for (int i=1; i < configBox->count(); i++) { QString current = configBox->itemText(i); diff --git a/src/keyboard/virtualkeyboardmousewidget.cpp b/src/keyboard/virtualkeyboardmousewidget.cpp index 483a87c5..d8d6bbe5 100644 --- a/src/keyboard/virtualkeyboardmousewidget.cpp +++ b/src/keyboard/virtualkeyboardmousewidget.cpp @@ -524,7 +524,8 @@ QPushButton* VirtualKeyboardMouseWidget::createNoneKey() void VirtualKeyboardMouseWidget::processSingleKeyboardSelection(int keycode, unsigned int alias) { - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); button->setAssignedSlot(keycode, alias); emit selectionFinished(); @@ -537,7 +538,8 @@ void VirtualKeyboardMouseWidget::processAdvancedKeyboardSelection(int keycode, u void VirtualKeyboardMouseWidget::processSingleMouseSelection(JoyButtonSlot *tempslot) { - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); button->setAssignedSlot(tempslot->getSlotCode(), tempslot->getSlotMode()); emit selectionFinished(); } @@ -640,13 +642,15 @@ void VirtualKeyboardMouseWidget::establishVirtualMouseAdvancedSignalConnections( void VirtualKeyboardMouseWidget::clearButtonSlots() { - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); emit selectionCleared(); } void VirtualKeyboardMouseWidget::clearButtonSlotsFinish() { - button->clearSlotsEventReset(); + QMetaObject::invokeMethod(button, "clearSlotsEventReset", Qt::BlockingQueuedConnection); + //button->clearSlotsEventReset(); emit selectionFinished(); } diff --git a/src/logger.cpp b/src/logger.cpp index 307173c0..630e3058 100644 --- a/src/logger.cpp +++ b/src/logger.cpp @@ -40,6 +40,7 @@ Logger::Logger(QTextStream *stream, LogLevel outputLevel, QObject *parent) : instance->pendingTimer.setSingleShot(true); instance->writeTime = false; + connect(instance, SIGNAL(pendingMessage()), instance, SLOT(startPendingTimer())); connect(&(instance->pendingTimer), SIGNAL(timeout()), instance, SLOT(Log())); } @@ -64,6 +65,7 @@ Logger::Logger(QTextStream *stream, QTextStream *errorStream, instance->pendingTimer.setSingleShot(true); instance->writeTime = false; + connect(instance, SIGNAL(pendingMessage()), instance, SLOT(startPendingTimer())); connect(&(instance->pendingTimer), SIGNAL(timeout()), instance, SLOT(Log())); } @@ -225,10 +227,12 @@ void Logger::appendLog(LogLevel level, const QString &message, bool newline) instance->pendingMessages.append(temp); - if (!instance->pendingTimer.isActive()) + /*if (!instance->pendingTimer.isActive()) { instance->pendingTimer.start(); } + */ + emit instance->pendingMessage(); } /** @@ -341,3 +345,13 @@ bool Logger::getWriteTime() return writeTime; } + +void Logger::startPendingTimer() +{ + Q_ASSERT(instance != 0); + + if (!instance->pendingTimer.isActive()) + { + instance->pendingTimer.start(); + } +} diff --git a/src/logger.h b/src/logger.h index 8600846e..c4a790be 100644 --- a/src/logger.h +++ b/src/logger.h @@ -139,9 +139,11 @@ protected: signals: void stringWritten(QString text); + void pendingMessage(); public slots: void Log(); + void startPendingTimer(); }; #endif // LOGGER_H diff --git a/src/main.cpp b/src/main.cpp index fe95a8fc..7c921214 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -37,6 +37,7 @@ #include #include #include +#include #ifdef Q_OS_WIN #include @@ -66,10 +67,9 @@ #include #include - - #ifdef WITH_X11 -#include "x11extras.h" - #endif + #ifdef WITH_X11 + #include "x11extras.h" + #endif #endif @@ -172,6 +172,7 @@ int main(int argc, char *argv[]) } QMap *joysticks = new QMap(); + QThread inputEventThread; // Cross-platform way of performing IPC. Currently, // only establish a connection and then disconnect. @@ -478,8 +479,9 @@ int main(int argc, char *argv[]) mainAppHelper.printControllerList(joysticks); joypad_worker->quit(); + joypad_worker->deleteJoysticks(); - deleteInputDevices(joysticks); + //deleteInputDevices(joysticks); delete joysticks; joysticks = 0; @@ -510,14 +512,21 @@ int main(int argc, char *argv[]) else if (cmdutility.shouldMapController()) { InputDaemon *joypad_worker = new InputDaemon(joysticks, &settings); + joypad_worker->moveToThread(&inputEventThread); + //QObject::connect(&inputEventThread, SIGNAL(started()), joypad_worker, SLOT(refreshJoysticks())); + inputEventThread.start(QThread::HighPriority); + MainWindow *w = new MainWindow(joysticks, &cmdutility, &settings); QObject::connect(a, SIGNAL(aboutToQuit()), w, SLOT(removeJoyTabs())); QObject::connect(a, SIGNAL(aboutToQuit()), joypad_worker, SLOT(quit())); + QObject::connect(a, SIGNAL(aboutToQuit()), joypad_worker, SLOT(deleteJoysticks())); + QObject::connect(a, SIGNAL(aboutToQuit()), &inputEventThread, SLOT(quit())); int app_result = a->exec(); + inputEventThread.wait(); - deleteInputDevices(joysticks); + //deleteInputDevices(joysticks); delete joysticks; joysticks = 0; @@ -637,8 +646,11 @@ int main(int argc, char *argv[]) } InputDaemon *joypad_worker = new InputDaemon(joysticks, &settings); - MainWindow *w = new MainWindow(joysticks, &cmdutility, &settings); + joypad_worker->moveToThread(&inputEventThread); + //QObject::connect(&inputEventThread, SIGNAL(started()), joypad_worker, SLOT(refreshJoysticks())); + inputEventThread.start(QThread::HighPriority); + MainWindow *w = new MainWindow(joysticks, &cmdutility, &settings); FirstRunWizard *runWillard = 0; if (w->getGraphicalStatus() && FirstRunWizard::shouldDisplay(&settings)) @@ -647,10 +659,6 @@ int main(int argc, char *argv[]) QObject::connect(runWillard, SIGNAL(finished(int)), w, SLOT(changeWindowStatus())); runWillard->show(); } - else - { - w->changeWindowStatus(); - } w->setAppTranslator(&qtTranslator); w->setTranslator(&myappTranslator); @@ -658,18 +666,19 @@ int main(int argc, char *argv[]) AppLaunchHelper mainAppHelper(&settings, w->getGraphicalStatus()); mainAppHelper.initRunMethods(); - QObject::connect(joypad_worker, - SIGNAL(joysticksRefreshed(QMap*)), - w, SLOT(fillButtons(QMap*))); - QObject::connect(w, SIGNAL(joystickRefreshRequested()), joypad_worker, SLOT(refresh())); QObject::connect(joypad_worker, SIGNAL(joystickRefreshed(InputDevice*)), w, SLOT(fillButtons(InputDevice*))); + QObject::connect(joypad_worker, + SIGNAL(joysticksRefreshed(QMap*)), + w, SLOT(fillButtons(QMap*))); QObject::connect(a, SIGNAL(aboutToQuit()), localServer, SLOT(close())); QObject::connect(a, SIGNAL(aboutToQuit()), w, SLOT(saveAppConfig())); QObject::connect(a, SIGNAL(aboutToQuit()), w, SLOT(removeJoyTabs())); QObject::connect(a, SIGNAL(aboutToQuit()), joypad_worker, SLOT(quit())); + QObject::connect(a, SIGNAL(aboutToQuit()), joypad_worker, SLOT(deleteJoysticks())); + QObject::connect(a, SIGNAL(aboutToQuit()), &inputEventThread, SLOT(quit())); #ifdef Q_OS_WIN QObject::connect(a, SIGNAL(aboutToQuit()), &mainAppHelper, SLOT(appQuitPointerPrecision())); @@ -679,8 +688,11 @@ int main(int argc, char *argv[]) #ifdef USE_SDL_2 QObject::connect(w, SIGNAL(mappingUpdated(QString,InputDevice*)), joypad_worker, SLOT(refreshMapping(QString,InputDevice*))); QObject::connect(joypad_worker, SIGNAL(deviceUpdated(int,InputDevice*)), w, SLOT(testMappingUpdateNow(int,InputDevice*))); - QObject::connect(joypad_worker, SIGNAL(deviceRemoved(SDL_JoystickID)), w, SLOT(removeJoyTab(SDL_JoystickID))); - QObject::connect(joypad_worker, SIGNAL(deviceAdded(InputDevice*)), w, SLOT(addJoyTab(InputDevice*))); + + QObject::connect(joypad_worker, SIGNAL(deviceRemoved(int)), w, SLOT(removeJoyTab(int)), + Qt::BlockingQueuedConnection); + QObject::connect(joypad_worker, SIGNAL(deviceAdded(InputDevice*)), w, SLOT(addJoyTab(InputDevice*)), + Qt::BlockingQueuedConnection); #endif #ifdef Q_OS_WIN @@ -697,14 +709,20 @@ int main(int argc, char *argv[]) QThread::currentThread()->setPriority(QThread::HighPriority); #endif + JoyButton::setStaticMouseThread(&inputEventThread); + + QTimer::singleShot(20, w, SLOT(changeWindowStatus())); + int app_result = a->exec(); + inputEventThread.wait(); // Log any remaining messages if they exist. appLogger.Log(); appLogger.LogInfo(QObject::tr("Quitting Program"), true, true); - deleteInputDevices(joysticks); + //deleteInputDevices(joysticks); + delete joysticks; joysticks = 0; diff --git a/src/mainsettingsdialog.cpp b/src/mainsettingsdialog.cpp index 11b00f0c..95d7f11e 100644 --- a/src/mainsettingsdialog.cpp +++ b/src/mainsettingsdialog.cpp @@ -97,11 +97,6 @@ MainSettingsDialog::MainSettingsDialog(AntiMicroSettings *settings, ui->closeToTrayCheckBox->setChecked(true); } - //findLocaleItem(); - - //delete ui->categoriesListWidget->item(2); - //ui->stackedWidget->removeWidget(ui->page); - changePresetLanguage(); #ifdef Q_OS_WIN @@ -667,6 +662,8 @@ void MainSettingsDialog::saveNewSettings() #endif + PadderCommon::lockInputDevices(); + bool smoothingEnabled = ui->smoothingEnableCheckBox->isChecked(); int historySize = ui->historySizeSpinBox->value(); double weightModifier = ui->weightModifierDoubleSpinBox->value(); @@ -721,6 +718,8 @@ void MainSettingsDialog::saveNewSettings() settings->setValue("GamepadPollRate", QString::number(gamepadPollRate)); } + PadderCommon::unlockInputDevices(); + settings->sync(); } diff --git a/src/mainwindow.cpp b/src/mainwindow.cpp index 29029bd6..b74d7a35 100644 --- a/src/mainwindow.cpp +++ b/src/mainwindow.cpp @@ -275,6 +275,11 @@ MainWindow::~MainWindow() delete ui; } +void MainWindow::fillButtons() +{ + fillButtons(joysticks); +} + void MainWindow::fillButtons(InputDevice *joystick) { int joyindex = joystick->getJoyNumber(); @@ -327,7 +332,7 @@ void MainWindow::fillButtons(QMap *joysticks) } } - if (joysticks->count() > 0) + if (joysticks->size() > 0) { loadAppConfig(); @@ -370,7 +375,7 @@ void MainWindow::populateTrayIcon() trayIconMenu->clear(); profileActions.clear(); - unsigned int joystickCount = joysticks->count(); + unsigned int joystickCount = joysticks->size(); if (joystickCount > 0) { @@ -397,89 +402,92 @@ void MainWindow::populateTrayIcon() } JoyTabWidget *widget = static_cast(ui->tabWidget->widget(i)); - QHash *configs = widget->recentConfigs(); - QHashIterator configIter(*configs); - QList tempProfileList; - while (configIter.hasNext()) + if (widget) { - configIter.next(); + QHash *configs = widget->recentConfigs(); + QHashIterator configIter(*configs); + QList tempProfileList; + while (configIter.hasNext()) + { + configIter.next(); + QAction *newaction = 0; + if (joysticksubMenu) + { + newaction = new QAction(configIter.value(), joysticksubMenu); + } + else + { + newaction = new QAction(configIter.value(), trayIconMenu); + } + + newaction->setCheckable(true); + newaction->setChecked(false); + + if (configIter.key() == widget->getCurrentConfigIndex()) + { + newaction->setChecked(true); + } + + QHash tempmap; + tempmap.insert(QString::number(i), QVariant (configIter.key())); + QVariant tempvar (tempmap); + newaction->setData(tempvar); + connect(newaction, SIGNAL(triggered(bool)), this, SLOT(profileTrayActionTriggered(bool))); + + if (useSingleList) + { + tempProfileList.append(newaction); + } + else + { + joysticksubMenu->addAction(newaction); + } + } + + delete configs; + configs = 0; + QAction *newaction = 0; if (joysticksubMenu) { - newaction = new QAction(configIter.value(), joysticksubMenu); + newaction = new QAction(tr("Open File"), joysticksubMenu); } else { - newaction = new QAction(configIter.value(), trayIconMenu); + newaction = new QAction(tr("Open File"), trayIconMenu); } - newaction->setCheckable(true); - newaction->setChecked(false); - - if (configIter.key() == widget->getCurrentConfigIndex()) - { - newaction->setChecked(true); - } - - QHash tempmap; - tempmap.insert(QString::number(i), QVariant (configIter.key())); - QVariant tempvar (tempmap); - newaction->setData(tempvar); - connect(newaction, SIGNAL(triggered(bool)), this, SLOT(profileTrayActionTriggered(bool))); + newaction->setIcon(QIcon::fromTheme("document-open")); + connect(newaction, SIGNAL(triggered()), widget, SLOT(openConfigFileDialog())); if (useSingleList) { - tempProfileList.append(newaction); + QAction *titleAction = new QAction(joytabName, trayIconMenu); + titleAction->setCheckable(false); + + QFont actionFont = titleAction->font(); + actionFont.setBold(true); + titleAction->setFont(actionFont); + + trayIconMenu->addAction(titleAction); + trayIconMenu->addActions(tempProfileList); + trayIconMenu->addAction(newaction); + + profileActions.insert(i, tempProfileList); + + if (iter.hasNext()) + { + trayIconMenu->addSeparator(); + } } else { joysticksubMenu->addAction(newaction); + connect(joysticksubMenu, SIGNAL(aboutToShow()), this, SLOT(joystickTrayShow())); } + + i++; } - - delete configs; - configs = 0; - - QAction *newaction = 0; - if (joysticksubMenu) - { - newaction = new QAction(tr("Open File"), joysticksubMenu); - } - else - { - newaction = new QAction(tr("Open File"), trayIconMenu); - } - - newaction->setIcon(QIcon::fromTheme("document-open")); - connect(newaction, SIGNAL(triggered()), widget, SLOT(openConfigFileDialog())); - - if (useSingleList) - { - QAction *titleAction = new QAction(joytabName, trayIconMenu); - titleAction->setCheckable(false); - - QFont actionFont = titleAction->font(); - actionFont.setBold(true); - titleAction->setFont(actionFont); - - trayIconMenu->addAction(titleAction); - trayIconMenu->addActions(tempProfileList); - trayIconMenu->addAction(newaction); - - profileActions.insert(i, tempProfileList); - - if (iter.hasNext()) - { - trayIconMenu->addSeparator(); - } - } - else - { - joysticksubMenu->addAction(newaction); - connect(joysticksubMenu, SIGNAL(aboutToShow()), this, SLOT(joystickTrayShow())); - } - - i++; } if (useSingleList) @@ -579,7 +587,7 @@ void MainWindow::mainMenuChange() void MainWindow::saveAppConfig() { - if (joysticks->count() > 0) + if (joysticks->size() > 0) { JoyTabWidget *temptabwidget = static_cast(ui->tabWidget->widget(0)); settings->setValue("DisplayNames", @@ -1376,7 +1384,7 @@ void MainWindow::testMappingUpdateNow(int index, InputDevice *device) } } -void MainWindow::removeJoyTab(SDL_JoystickID deviceID) +void MainWindow::removeJoyTab(int deviceID) { bool found = false; for (int i=0; i < ui->tabWidget->count() && !found; i++) diff --git a/src/mainwindow.h b/src/mainwindow.h index 33f47067..552ca83c 100644 --- a/src/mainwindow.h +++ b/src/mainwindow.h @@ -102,6 +102,7 @@ signals: #endif public slots: + void fillButtons(); void fillButtons(InputDevice *joystick); void fillButtons(QMap *joysticks); void startJoystickRefresh(); @@ -114,7 +115,7 @@ public slots: #ifdef USE_SDL_2 void testMappingUpdateNow(int index, InputDevice *device); - void removeJoyTab(SDL_JoystickID deviceID); + void removeJoyTab(int deviceID); void addJoyTab(InputDevice *device); void selectControllerJoyTab(QString GUID); void selectControllerJoyTab(unsigned int index); diff --git a/src/sdleventreader.cpp b/src/sdleventreader.cpp index 289bf243..ebc3d232 100644 --- a/src/sdleventreader.cpp +++ b/src/sdleventreader.cpp @@ -87,6 +87,7 @@ void SDLEventReader::initSDL() pollRateTimer.stop(); pollRateTimer.setInterval(pollRate); + //pollRateTimer.start(); //pollRateTimer.setSingleShot(true); emit sdlStarted(); @@ -126,6 +127,19 @@ void SDLEventReader::performWork() { //int status = SDL_WaitEvent(NULL); int status = CheckForEvents(); + + PadderCommon::editingLock.lockForRead(); + bool isEditing = PadderCommon::editingBindings; + PadderCommon::editingLock.unlock(); + + if (isEditing) + { + QMutex *dismutex = &PadderCommon::waitMutex; + dismutex->lock(); + PadderCommon::waitThisOut.wakeAll(); + dismutex->unlock(); + } + if (status) { pollRateTimer.stop(); @@ -187,6 +201,12 @@ int SDLEventReader::CheckForEvents() int result = 0; bool exit = false; + /*Logger::LogInfo( + QString("Gamepad Poll %1").arg( + QTime::currentTime().toString("hh:mm:ss.zzz")), + true, true); + */ + //while (!exit) //{ SDL_PumpEvents(); diff --git a/src/xmlconfigreader.cpp b/src/xmlconfigreader.cpp index 6927fc44..c8727215 100644 --- a/src/xmlconfigreader.cpp +++ b/src/xmlconfigreader.cpp @@ -22,6 +22,7 @@ #include "xmlconfigreader.h" #include "xmlconfigmigration.h" #include "xmlconfigwriter.h" +#include "common.h" XMLConfigReader::XMLConfigReader(QObject *parent) : @@ -133,7 +134,9 @@ bool XMLConfigReader::read() { if (xml->isStartElement() && deviceTypes.contains(xml->name().toString())) { - joystick->readConfig(xml); + QMetaObject::invokeMethod(joystick, "readConfig", Qt::BlockingQueuedConnection, + Q_ARG(QXmlStreamReader*, xml)); + //joystick->readConfig(xml); } else {