From da4c55d5adf756ca7cc49a4a80a214f7347105bb Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Sat, 23 Jun 2018 17:51:32 +1000 Subject: [PATCH 01/11] prevent segfalt in QuickKeysMenu when item has been removed from player inventory added a MWWorld::ContainerStore to hold item copies which are then used to find real items with findReplacement(). (storing the RefId could be a better solution but would probably leave tooltips broken...) --- apps/openmw/mwgui/quickkeysmenu.cpp | 151 ++++++++++++++-------------- apps/openmw/mwgui/quickkeysmenu.hpp | 3 + 2 files changed, 80 insertions(+), 74 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 08192625f4..2271d25827 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -124,6 +124,13 @@ namespace MWGui void QuickKeysMenu::unassign(ItemWidget* key, int index) { + // cleanup refrance ItemContainer + if( mAssigned[index] == Type_Item || mAssigned[index] == Type_MagicItem) + { + MWWorld::Ptr refItem = *key->getUserData(); + mRefItemContainer.remove(refItem.getCellRef().getRefId(), 1, MWMechanics::getPlayer()); + } + key->clearUserStrings(); key->setItem(MWWorld::Ptr()); while (key->getChildCount()) // Destroy number label @@ -221,9 +228,11 @@ namespace MWGui mAssigned[mSelectedIndex] = Type_Item; - button->setItem(item, ItemWidget::Barter); + MWWorld::Ptr itemCopy = *mRefItemContainer.add(item, 1, MWMechanics::getPlayer()); + + button->setItem(itemCopy, ItemWidget::Barter); button->setUserString ("ToolTipType", "ItemPtr"); - button->setUserData(MWWorld::Ptr(item)); + button->setUserData(itemCopy); if (mItemSelectionDialog) mItemSelectionDialog->setVisible(false); @@ -334,29 +343,78 @@ namespace MWGui if (type == Type_Item || type == Type_MagicItem) { - MWWorld::Ptr item = *button->getUserData(); - // Make sure the item is available and is not broken - if (item.getRefData().getCount() < 1 || - (item.getClass().hasItemHealth(item) && - item.getClass().getItemHealth(item) <= 0)) + MWWorld::Ptr refItem = *button->getUserData(); + MWWorld::Ptr item = store.findReplacement(refItem.getCellRef().getRefId()); + + // check the item is available and not broken + if (!item || item.getRefData().getCount() < 1 || + (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) { - // Try searching for a compatible replacement - std::string id = item.getCellRef().getRefId(); - - item = store.findReplacement(id); - button->setUserData(MWWorld::Ptr(item)); - - if (item.getRefData().getCount() < 1) + if (!item || item.getRefData().getCount() < 1) { - // No replacement was found - MWBase::Environment::get().getWindowManager ()->messageBox ( - "#{sQuickMenu5} " + item.getClass().getName(item)); + // item not in plater inventory found + MWBase::Environment::get().getWindowManager()->messageBox( + "#{sQuickMenu5} " + refItem.getClass().getName(refItem)); + return; } } - } - if (type == Type_Magic) + if (type == Type_Item) + { + bool isWeapon = item.getTypeName() == typeid(ESM::Weapon).name(); + bool isTool = item.getTypeName() == typeid(ESM::Probe).name() || + item.getTypeName() == typeid(ESM::Lockpick).name(); + + // delay weapon switching if player is busy + if (isDelayNeeded && (isWeapon || isTool)) + { + mActivatedIndex = index; + return; + } + + // disable weapon switching if player is dead or paralyzed + if (isReturnNeeded && (isWeapon || isTool)) + { + return; + } + + MWBase::Environment::get().getWindowManager()->useItem(item); + MWWorld::ConstContainerStoreIterator rightHand = store.getSlot(MWWorld::InventoryStore::Slot_CarriedRight); + // change draw state only if the item is in player's right hand + if (rightHand != store.end() && item == *rightHand) + { + MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Weapon); + } + } + else if (type == Type_MagicItem) + { + // retrieve ContainerStoreIterator to the item + MWWorld::ContainerStoreIterator it = store.begin(); + for (; it != store.end(); ++it) + { + if (*it == item) + { + break; + } + } + assert(it != store.end()); + + // equip, if it can be equipped + if (!item.getClass().getEquipmentSlots(item).first.empty()) + { + MWBase::Environment::get().getWindowManager()->useItem(item); + + // make sure that item was successfully equipped + if (!store.isEquipped(item)) + return; + } + + store.setSelectedEnchantItem(it); + MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Spell); + } + } + else if (type == Type_Magic) { std::string spellId = button->getUserString("Spell"); @@ -374,61 +432,6 @@ namespace MWGui MWBase::Environment::get().getWindowManager()->setSelectedSpell(spellId, int(MWMechanics::getSpellSuccessChance(spellId, player))); MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Spell); } - else if (type == Type_Item) - { - MWWorld::Ptr item = *button->getUserData(); - bool isWeapon = item.getTypeName() == typeid(ESM::Weapon).name(); - bool isTool = item.getTypeName() == typeid(ESM::Probe).name() || item.getTypeName() == typeid(ESM::Lockpick).name(); - - // delay weapon switching if player is busy - if (isDelayNeeded && (isWeapon || isTool)) - { - mActivatedIndex = index; - return; - } - - // disable weapon switching if player is dead or paralyzed - if (isReturnNeeded && (isWeapon || isTool)) - { - return; - } - - MWBase::Environment::get().getWindowManager()->useItem(item); - MWWorld::ConstContainerStoreIterator rightHand = store.getSlot(MWWorld::InventoryStore::Slot_CarriedRight); - // change draw state only if the item is in player's right hand - if (rightHand != store.end() && item == *rightHand) - { - MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Weapon); - } - } - else if (type == Type_MagicItem) - { - MWWorld::Ptr item = *button->getUserData(); - - // retrieve ContainerStoreIterator to the item - MWWorld::ContainerStoreIterator it = store.begin(); - for (; it != store.end(); ++it) - { - if (*it == item) - { - break; - } - } - assert(it != store.end()); - - // equip, if it can be equipped - if (!item.getClass().getEquipmentSlots(item).first.empty()) - { - MWBase::Environment::get().getWindowManager()->useItem(item); - - // make sure that item was successfully equipped - if (!store.isEquipped(item)) - return; - } - - store.setSelectedEnchantItem(it); - MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Spell); - } else if (type == Type_HandToHand) { store.unequipSlot(MWWorld::InventoryStore::Slot_CarriedRight, player); diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index b5bc60b191..5e2305df8e 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -2,6 +2,7 @@ #define MWGUI_QUICKKEYS_H #include "../mwworld/ptr.hpp" +#include "../mwworld/containerstore.hpp" #include "windowbase.hpp" @@ -58,6 +59,8 @@ namespace MWGui MyGUI::EditBox* mInstructionLabel; MyGUI::Button* mOkButton; + MWWorld::ContainerStore mRefItemContainer; + std::vector mQuickKeyButtons; std::vector mAssigned; From 46c6abcf54f8e969e784089c0bd8ec99e9e58afa Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Mon, 25 Jun 2018 16:02:28 +1000 Subject: [PATCH 02/11] add string vectors for name/id in QuickKeysMenu for item lookups --- apps/openmw/mwgui/quickkeysmenu.cpp | 41 ++++++++++++++++------------- apps/openmw/mwgui/quickkeysmenu.hpp | 2 ++ 2 files changed, 25 insertions(+), 18 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 2271d25827..7d3e2cbc75 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -60,6 +60,9 @@ namespace MWGui mAssigned.push_back(Type_Unassigned); + mAssignedId.push_back(std::string("")); + mAssignedName.push_back(std::string("")); + unassign(button, i); } } @@ -131,6 +134,9 @@ namespace MWGui mRefItemContainer.remove(refItem.getCellRef().getRefId(), 1, MWMechanics::getPlayer()); } + mAssignedName[index] = ""; + mAssignedId[index] = ""; + key->clearUserStrings(); key->setItem(MWWorld::Ptr()); while (key->getChildCount()) // Destroy number label @@ -227,12 +233,14 @@ namespace MWGui MyGUI::Gui::getInstance().destroyWidget(button->getChildAt(0)); mAssigned[mSelectedIndex] = Type_Item; + mAssignedId[mSelectedIndex] = item.getCellRef().getRefId(); + mAssignedName[mSelectedIndex] = item.getClass().getName(item); - MWWorld::Ptr itemCopy = *mRefItemContainer.add(item, 1, MWMechanics::getPlayer()); + MWWorld::Ptr refItem = *mRefItemContainer.add(item, 1, MWMechanics::getPlayer()); - button->setItem(itemCopy, ItemWidget::Barter); + button->setItem(refItem, ItemWidget::Barter); button->setUserString ("ToolTipType", "ItemPtr"); - button->setUserData(itemCopy); + button->setUserData(item); if (mItemSelectionDialog) mItemSelectionDialog->setVisible(false); @@ -343,18 +351,26 @@ namespace MWGui if (type == Type_Item || type == Type_MagicItem) { - MWWorld::Ptr refItem = *button->getUserData(); - MWWorld::Ptr item = store.findReplacement(refItem.getCellRef().getRefId()); + MWWorld::Ptr item = *button->getUserData(); + + MWWorld::ContainerStoreIterator it = store.begin(); + for (; it != store.end(); ++it) + { + if (*it == item) + break; + } + if (it == store.end()) + item = NULL; // check the item is available and not broken if (!item || item.getRefData().getCount() < 1 || (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) { + item = store.findReplacement(mAssignedId[index-1]); if (!item || item.getRefData().getCount() < 1) { - // item not in plater inventory found MWBase::Environment::get().getWindowManager()->messageBox( - "#{sQuickMenu5} " + refItem.getClass().getName(refItem)); + "#{sQuickMenu5} " + mAssignedName[index-1]); return; } @@ -389,17 +405,6 @@ namespace MWGui } else if (type == Type_MagicItem) { - // retrieve ContainerStoreIterator to the item - MWWorld::ContainerStoreIterator it = store.begin(); - for (; it != store.end(); ++it) - { - if (*it == item) - { - break; - } - } - assert(it != store.end()); - // equip, if it can be equipped if (!item.getClass().getEquipmentSlots(item).first.empty()) { diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index 5e2305df8e..8df0ae2395 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -60,6 +60,8 @@ namespace MWGui MyGUI::Button* mOkButton; MWWorld::ContainerStore mRefItemContainer; + std::vector mAssignedId; + std::vector mAssignedName; std::vector mQuickKeyButtons; std::vector mAssigned; From 186ec8c50fa205ae731031934589091d3f96c3b0 Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Tue, 26 Jun 2018 13:35:04 +1000 Subject: [PATCH 03/11] rm ContainerStore/refItem --- apps/openmw/mwgui/quickkeysmenu.cpp | 11 +---------- apps/openmw/mwgui/quickkeysmenu.hpp | 6 ++---- 2 files changed, 3 insertions(+), 14 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 7d3e2cbc75..e19df2bbb5 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -127,13 +127,6 @@ namespace MWGui void QuickKeysMenu::unassign(ItemWidget* key, int index) { - // cleanup refrance ItemContainer - if( mAssigned[index] == Type_Item || mAssigned[index] == Type_MagicItem) - { - MWWorld::Ptr refItem = *key->getUserData(); - mRefItemContainer.remove(refItem.getCellRef().getRefId(), 1, MWMechanics::getPlayer()); - } - mAssignedName[index] = ""; mAssignedId[index] = ""; @@ -236,9 +229,7 @@ namespace MWGui mAssignedId[mSelectedIndex] = item.getCellRef().getRefId(); mAssignedName[mSelectedIndex] = item.getClass().getName(item); - MWWorld::Ptr refItem = *mRefItemContainer.add(item, 1, MWMechanics::getPlayer()); - - button->setItem(refItem, ItemWidget::Barter); + button->setItem(item, ItemWidget::Barter); button->setUserString ("ToolTipType", "ItemPtr"); button->setUserData(item); diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index 8df0ae2395..29506ab58d 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -59,12 +59,10 @@ namespace MWGui MyGUI::EditBox* mInstructionLabel; MyGUI::Button* mOkButton; - MWWorld::ContainerStore mRefItemContainer; - std::vector mAssignedId; - std::vector mAssignedName; - std::vector mQuickKeyButtons; std::vector mAssigned; + std::vector mAssignedId; + std::vector mAssignedName; QuickKeysMenuAssign* mAssignDialog; ItemSelectionDialog* mItemSelectionDialog; From 43c9fd4cec3e9c060ca524a048bf63ba8f0f1021 Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Tue, 26 Jun 2018 13:41:53 +1000 Subject: [PATCH 04/11] check MWWorld::Ptr != NULL for MWGui ItemPtr tooltips --- apps/openmw/mwgui/tooltips.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/apps/openmw/mwgui/tooltips.cpp b/apps/openmw/mwgui/tooltips.cpp index b2991a0344..20814aac50 100644 --- a/apps/openmw/mwgui/tooltips.cpp +++ b/apps/openmw/mwgui/tooltips.cpp @@ -191,6 +191,9 @@ namespace MWGui else if (type == "ItemPtr") { mFocusObject = *focus->getUserData(); + if (!mFocusObject) + return; + tooltipSize = getToolTipViaPtr(mFocusObject.getRefData().getCount(), false, checkOwned()); } else if (type == "ItemModelIndex") From 335e2c5897d73ea866807f427c5b362e5867c03a Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Thu, 28 Jun 2018 13:27:08 +1000 Subject: [PATCH 05/11] add keyData struct + general cleanup --- apps/openmw/mwgui/quickkeysmenu.cpp | 181 +++++++++++++--------------- apps/openmw/mwgui/quickkeysmenu.hpp | 20 +-- 2 files changed, 99 insertions(+), 102 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index e19df2bbb5..819decfc19 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -43,27 +43,21 @@ namespace MWGui getWidget(mInstructionLabel, "InstructionLabel"); mMainWidget->setSize(mMainWidget->getWidth(), - mMainWidget->getHeight() + (mInstructionLabel->getTextSize().height - mInstructionLabel->getHeight())); + mMainWidget->getHeight() + + (mInstructionLabel->getTextSize().height - mInstructionLabel->getHeight())); mOkButton->eventMouseButtonClick += MyGUI::newDelegate(this, &QuickKeysMenu::onOkButtonClicked); center(); + mKey = std::vector(10); for (int i = 0; i < 10; ++i) { - ItemWidget* button; - getWidget(button, "QuickKey" + MyGUI::utility::toString(i+1)); + mKey[i].index = i; + getWidget(mKey[i].button, "QuickKey" + MyGUI::utility::toString(i+1)); + mKey[i].button->eventMouseButtonClick += MyGUI::newDelegate(this, &QuickKeysMenu::onQuickKeyButtonClicked); - button->eventMouseButtonClick += MyGUI::newDelegate(this, &QuickKeysMenu::onQuickKeyButtonClicked); - - mQuickKeyButtons.push_back(button); - - mAssigned.push_back(Type_Unassigned); - - mAssignedId.push_back(std::string("")); - mAssignedName.push_back(std::string("")); - - unassign(button, i); + unassign(&mKey[i]); } } @@ -73,7 +67,7 @@ namespace MWGui for (int i=0; i<10; ++i) { - unassign(mQuickKeyButtons[i], i); + unassign(&mKey[i]); } } @@ -94,10 +88,7 @@ namespace MWGui // Check if quick keys are still valid for (int i=0; i<10; ++i) { - ItemWidget* button = mQuickKeyButtons[i]; - int type = mAssigned[i]; - - switch (type) + switch (mKey[i].type) { case Type_Unassigned: case Type_HandToHand: @@ -106,7 +97,7 @@ namespace MWGui case Type_Item: case Type_MagicItem: { - MWWorld::Ptr item = *button->getUserData(); + MWWorld::Ptr item = *mKey[i].button->getUserData(); // Make sure the item is available and is not broken if (item.getRefData().getCount() < 1 || (item.getClass().hasItemHealth(item) && @@ -116,51 +107,53 @@ namespace MWGui std::string id = item.getCellRef().getRefId(); item = store.findReplacement(id); - button->setUserData(MWWorld::Ptr(item)); + mKey[i].button->setUserData(MWWorld::Ptr(item)); break; } } } } - } - void QuickKeysMenu::unassign(ItemWidget* key, int index) + void QuickKeysMenu::unassign(struct keyData* key) { - mAssignedName[index] = ""; - mAssignedId[index] = ""; + key->button->clearUserStrings(); + key->button->setItem(MWWorld::Ptr()); - key->clearUserStrings(); - key->setItem(MWWorld::Ptr()); - while (key->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(key->getChildAt(0)); + while(key->button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(key->button->getChildAt(0)); - if (index == 9) + if (key->index == 9) { - mAssigned[index] = Type_HandToHand; + key->type = Type_HandToHand; - MyGUI::ImageBox* image = key->createWidget("ImageBox", + MyGUI::ImageBox* image = key->button->createWidget("ImageBox", MyGUI::IntCoord(14, 13, 32, 32), MyGUI::Align::Default); + image->setImageTexture("icons\\k\\stealth_handtohand.dds"); image->setNeedMouseFocus(false); } else { - mAssigned[index] = Type_Unassigned; + key->type = Type_Unassigned; + key->id = ""; + key->name = ""; - MyGUI::TextBox* textBox = key->createWidgetReal("SandText", MyGUI::FloatCoord(0,0,1,1), MyGUI::Align::Default); - textBox->setTextAlign (MyGUI::Align::Center); - textBox->setCaption (MyGUI::utility::toString(index+1)); - textBox->setNeedMouseFocus (false); + MyGUI::TextBox* textBox = key->button->createWidgetReal("SandText", + MyGUI::FloatCoord(0,0,1,1), MyGUI::Align::Default); + + textBox->setTextAlign(MyGUI::Align::Center); + textBox->setCaption(MyGUI::utility::toString(key->index + 1)); + textBox->setNeedMouseFocus(false); } } void QuickKeysMenu::onQuickKeyButtonClicked(MyGUI::Widget* sender) { int index = -1; - for (int i = 0; i < 10; ++i) + for(int i = 0; i < 10; ++i) { - if (sender == mQuickKeyButtons[i] || sender->getParent () == mQuickKeyButtons[i]) + if(sender == mKey[i].button || sender->getParent() == mKey[i].button) { index = i; break; @@ -170,9 +163,10 @@ namespace MWGui mSelectedIndex = index; // open assign dialog - if (!mAssignDialog) + if(!mAssignDialog) mAssignDialog = new QuickKeysMenuAssign(this); - mAssignDialog->setVisible (true); + + mAssignDialog->setVisible(true); } void QuickKeysMenu::onOkButtonClicked (MyGUI::Widget *sender) @@ -180,7 +174,6 @@ namespace MWGui MWBase::Environment::get().getWindowManager()->removeGuiMode(GM_QuickKeysMenu); } - void QuickKeysMenu::onItemButtonClicked(MyGUI::Widget* sender) { if (!mItemSelectionDialog ) @@ -198,42 +191,42 @@ namespace MWGui void QuickKeysMenu::onMagicButtonClicked(MyGUI::Widget* sender) { - if (!mMagicSelectionDialog ) + if(!mMagicSelectionDialog) { mMagicSelectionDialog = new MagicSelectionDialog(this); } mMagicSelectionDialog->setVisible(true); - mAssignDialog->setVisible (false); + mAssignDialog->setVisible(false); } void QuickKeysMenu::onUnassignButtonClicked(MyGUI::Widget* sender) { - unassign(mQuickKeyButtons[mSelectedIndex], mSelectedIndex); - mAssignDialog->setVisible (false); + unassign(&mKey[mSelectedIndex]); + mAssignDialog->setVisible(false); } void QuickKeysMenu::onCancelButtonClicked(MyGUI::Widget* sender) { - mAssignDialog->setVisible (false); + mAssignDialog->setVisible(false); } void QuickKeysMenu::onAssignItem(MWWorld::Ptr item) { - assert (mSelectedIndex >= 0); - ItemWidget* button = mQuickKeyButtons[mSelectedIndex]; - while (button->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(button->getChildAt(0)); + assert(mSelectedIndex >= 0); - mAssigned[mSelectedIndex] = Type_Item; - mAssignedId[mSelectedIndex] = item.getCellRef().getRefId(); - mAssignedName[mSelectedIndex] = item.getClass().getName(item); + while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(mKey[mSelectedIndex].button->getChildAt(0)); - button->setItem(item, ItemWidget::Barter); - button->setUserString ("ToolTipType", "ItemPtr"); - button->setUserData(item); + mKey[mSelectedIndex].type = Type_Item; + mKey[mSelectedIndex].id = item.getCellRef().getRefId(); + mKey[mSelectedIndex].name = item.getClass().getName(item); - if (mItemSelectionDialog) + mKey[mSelectedIndex].button->setItem(item, ItemWidget::Barter); + mKey[mSelectedIndex].button->setUserString("ToolTipType", "ItemPtr"); + mKey[mSelectedIndex].button->setUserData(item); + + if(mItemSelectionDialog) mItemSelectionDialog->setVisible(false); } @@ -242,37 +235,37 @@ namespace MWGui mItemSelectionDialog->setVisible(false); } - void QuickKeysMenu::onAssignMagicItem (MWWorld::Ptr item) + void QuickKeysMenu::onAssignMagicItem(MWWorld::Ptr item) { - assert (mSelectedIndex >= 0); - ItemWidget* button = mQuickKeyButtons[mSelectedIndex]; - while (button->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(button->getChildAt(0)); + assert(mSelectedIndex >= 0); - mAssigned[mSelectedIndex] = Type_MagicItem; + while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(mKey[mSelectedIndex].button->getChildAt(0)); - button->setFrame("textures\\menu_icon_select_magic_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); - button->setIcon(item); + mKey[mSelectedIndex].type = Type_MagicItem; - button->setUserString ("ToolTipType", "ItemPtr"); - button->setUserData(MWWorld::Ptr(item)); + mKey[mSelectedIndex].button->setFrame("textures\\menu_icon_select_magic_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); + mKey[mSelectedIndex].button->setIcon(item); - if (mMagicSelectionDialog) + mKey[mSelectedIndex].button->setUserString ("ToolTipType", "ItemPtr"); + mKey[mSelectedIndex].button->setUserData(MWWorld::Ptr(item)); + + if(mMagicSelectionDialog) mMagicSelectionDialog->setVisible(false); } - void QuickKeysMenu::onAssignMagic (const std::string& spellId) + void QuickKeysMenu::onAssignMagic(const std::string& spellId) { - assert (mSelectedIndex >= 0); - ItemWidget* button = mQuickKeyButtons[mSelectedIndex]; - while (button->getChildCount()) // Destroy number label + assert(mSelectedIndex >= 0); + ItemWidget* button = mKey[mSelectedIndex].button; + while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label MyGUI::Gui::getInstance().destroyWidget(button->getChildAt(0)); - mAssigned[mSelectedIndex] = Type_Magic; + mKey[mSelectedIndex].type = Type_Magic; - button->setItem(MWWorld::Ptr()); - button->setUserString ("ToolTipType", "Spell"); - button->setUserString ("Spell", spellId); + mKey[mSelectedIndex].button->setItem(MWWorld::Ptr()); + mKey[mSelectedIndex].button->setUserString("ToolTipType", "Spell"); + mKey[mSelectedIndex].button->setUserString("Spell", spellId); const MWWorld::ESMStore &esmStore = MWBase::Environment::get().getWorld()->getStore(); @@ -311,10 +304,9 @@ namespace MWGui void QuickKeysMenu::activateQuickKey(int index) { - assert (index-1 >= 0); - ItemWidget* button = mQuickKeyButtons[index-1]; - - QuickKeyType type = mAssigned[index-1]; + assert(index-1 >= 0); + ItemWidget* button = mKey[index-1].button; + QuickKeyType type = mKey[index-1].type; MWWorld::Ptr player = MWMechanics::getPlayer(); MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player); @@ -351,17 +343,17 @@ namespace MWGui break; } if (it == store.end()) - item = NULL; + item = nullptr; // check the item is available and not broken if (!item || item.getRefData().getCount() < 1 || (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) { - item = store.findReplacement(mAssignedId[index-1]); + item = store.findReplacement(mKey[index-1].id); if (!item || item.getRefData().getCount() < 1) { MWBase::Environment::get().getWindowManager()->messageBox( - "#{sQuickMenu5} " + mAssignedName[index-1]); + "#{sQuickMenu5} " + mKey[index-1].name); return; } @@ -490,9 +482,9 @@ namespace MWGui for (int i=0; i<10; ++i) { - ItemWidget* button = mQuickKeyButtons[i]; + ItemWidget* button = mKey[i].button; - int type = mAssigned[i]; + int type = mKey[i].type; ESM::QuickKeys::QuickKey key; key.mType = type; @@ -525,7 +517,7 @@ namespace MWGui void QuickKeysMenu::readRecord(ESM::ESMReader &reader, uint32_t type) { - if (type != ESM::REC_KEYS) + if(type != ESM::REC_KEYS) return; ESM::QuickKeys keys; @@ -535,20 +527,19 @@ namespace MWGui MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player); int i=0; - for (std::vector::const_iterator it = keys.mKeys.begin(); it != keys.mKeys.end(); ++it) + for(std::vector::const_iterator it = keys.mKeys.begin(); it != keys.mKeys.end(); ++it) { - if (i >= 10) + if(i >= 10) return; mSelectedIndex = i; int keyType = it->mType; std::string id = it->mId; - ItemWidget* button = mQuickKeyButtons[i]; switch (keyType) { case Type_Magic: - if (MWBase::Environment::get().getWorld()->getStore().get().search(id)) + if(MWBase::Environment::get().getWorld()->getStore().get().search(id)) onAssignMagic(id); break; case Type_Item: @@ -557,13 +548,13 @@ namespace MWGui // Find the item by id MWWorld::Ptr item = store.findReplacement(id); - if (item.isEmpty()) - unassign(button, i); + if(item.isEmpty()) + unassign(&mKey[i]); else { - if (keyType == Type_Item) + if(keyType == Type_Item) onAssignItem(item); - else if (keyType == Type_MagicItem) + else if(keyType == Type_MagicItem) onAssignMagicItem(item); } @@ -571,7 +562,7 @@ namespace MWGui } case Type_Unassigned: case Type_HandToHand: - unassign(button, i); + unassign(&mKey[i]); break; } diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index 29506ab58d..f11673f5fe 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -2,7 +2,6 @@ #define MWGUI_QUICKKEYS_H #include "../mwworld/ptr.hpp" -#include "../mwworld/containerstore.hpp" #include "windowbase.hpp" @@ -56,14 +55,21 @@ namespace MWGui private: + + struct keyData { + int index; + ItemWidget* button; + QuickKeysMenu::QuickKeyType type; + std::string id; + std::string name; + keyData(): index(-1), button(nullptr), type(Type_Unassigned), id(""), name("") {} + }; + + std::vector mKey; + MyGUI::EditBox* mInstructionLabel; MyGUI::Button* mOkButton; - std::vector mQuickKeyButtons; - std::vector mAssigned; - std::vector mAssignedId; - std::vector mAssignedName; - QuickKeysMenuAssign* mAssignDialog; ItemSelectionDialog* mItemSelectionDialog; MagicSelectionDialog* mMagicSelectionDialog; @@ -74,7 +80,7 @@ namespace MWGui void onQuickKeyButtonClicked(MyGUI::Widget* sender); void onOkButtonClicked(MyGUI::Widget* sender); - void unassign(ItemWidget* key, int index); + void unassign(struct keyData* key); }; class QuickKeysMenuAssign : public WindowModal From 80a3f0a0d40a7f39a8be6337119286a3d64d683a Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Thu, 28 Jun 2018 17:02:25 +1000 Subject: [PATCH 06/11] switch mSelectedIndex/mActivatedIndex int to mSelected/mActivated keyData pointers --- apps/openmw/mwgui/quickkeysmenu.cpp | 174 ++++++++++++++-------------- apps/openmw/mwgui/quickkeysmenu.hpp | 5 +- 2 files changed, 90 insertions(+), 89 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 819decfc19..b2bf9df0ed 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -33,11 +33,13 @@ namespace MWGui QuickKeysMenu::QuickKeysMenu() : WindowBase("openmw_quickkeys_menu.layout") + , mKey(std::vector(10)) + , mSelected(nullptr) + , mActivated(nullptr) , mAssignDialog(0) , mItemSelectionDialog(0) , mMagicSelectionDialog(0) - , mSelectedIndex(-1) - , mActivatedIndex(-1) + { getWidget(mOkButton, "OKButton"); getWidget(mInstructionLabel, "InstructionLabel"); @@ -49,8 +51,6 @@ namespace MWGui mOkButton->eventMouseButtonClick += MyGUI::newDelegate(this, &QuickKeysMenu::onOkButtonClicked); center(); - mKey = std::vector(10); - for (int i = 0; i < 10; ++i) { mKey[i].index = i; @@ -63,7 +63,7 @@ namespace MWGui void QuickKeysMenu::clear() { - mActivatedIndex = -1; + mActivated = nullptr; for (int i=0; i<10; ++i) { @@ -120,7 +120,7 @@ namespace MWGui key->button->clearUserStrings(); key->button->setItem(MWWorld::Ptr()); - while(key->button->getChildCount()) // Destroy number label + while (key->button->getChildCount()) // Destroy number label MyGUI::Gui::getInstance().destroyWidget(key->button->getChildAt(0)); if (key->index == 9) @@ -151,19 +151,19 @@ namespace MWGui void QuickKeysMenu::onQuickKeyButtonClicked(MyGUI::Widget* sender) { int index = -1; - for(int i = 0; i < 10; ++i) + for (int i = 0; i < 10; ++i) { - if(sender == mKey[i].button || sender->getParent() == mKey[i].button) + if (sender == mKey[i].button || sender->getParent() == mKey[i].button) { index = i; break; } } assert(index != -1); - mSelectedIndex = index; + mSelected = &mKey[index]; // open assign dialog - if(!mAssignDialog) + if (!mAssignDialog) mAssignDialog = new QuickKeysMenuAssign(this); mAssignDialog->setVisible(true); @@ -176,7 +176,7 @@ namespace MWGui void QuickKeysMenu::onItemButtonClicked(MyGUI::Widget* sender) { - if (!mItemSelectionDialog ) + if (!mItemSelectionDialog) { mItemSelectionDialog = new ItemSelectionDialog("#{sQuickMenu6}"); mItemSelectionDialog->eventItemSelected += MyGUI::newDelegate(this, &QuickKeysMenu::onAssignItem); @@ -186,12 +186,12 @@ namespace MWGui mItemSelectionDialog->openContainer(MWMechanics::getPlayer()); mItemSelectionDialog->setFilter(SortFilterItemModel::Filter_OnlyUsableItems); - mAssignDialog->setVisible (false); + mAssignDialog->setVisible(false); } void QuickKeysMenu::onMagicButtonClicked(MyGUI::Widget* sender) { - if(!mMagicSelectionDialog) + if (!mMagicSelectionDialog) { mMagicSelectionDialog = new MagicSelectionDialog(this); } @@ -202,7 +202,7 @@ namespace MWGui void QuickKeysMenu::onUnassignButtonClicked(MyGUI::Widget* sender) { - unassign(&mKey[mSelectedIndex]); + unassign(mSelected); mAssignDialog->setVisible(false); } @@ -213,20 +213,20 @@ namespace MWGui void QuickKeysMenu::onAssignItem(MWWorld::Ptr item) { - assert(mSelectedIndex >= 0); + assert(mSelected); - while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(mKey[mSelectedIndex].button->getChildAt(0)); + while (mSelected->button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(mSelected->button->getChildAt(0)); - mKey[mSelectedIndex].type = Type_Item; - mKey[mSelectedIndex].id = item.getCellRef().getRefId(); - mKey[mSelectedIndex].name = item.getClass().getName(item); + mSelected->type = Type_Item; + mSelected->id = item.getCellRef().getRefId(); + mSelected->name = item.getClass().getName(item); - mKey[mSelectedIndex].button->setItem(item, ItemWidget::Barter); - mKey[mSelectedIndex].button->setUserString("ToolTipType", "ItemPtr"); - mKey[mSelectedIndex].button->setUserData(item); + mSelected->button->setItem(item, ItemWidget::Barter); + mSelected->button->setUserString("ToolTipType", "ItemPtr"); + mSelected->button->setUserData(item); - if(mItemSelectionDialog) + if (mItemSelectionDialog) mItemSelectionDialog->setVisible(false); } @@ -237,38 +237,37 @@ namespace MWGui void QuickKeysMenu::onAssignMagicItem(MWWorld::Ptr item) { - assert(mSelectedIndex >= 0); + assert(mSelected); - while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(mKey[mSelectedIndex].button->getChildAt(0)); + while (mSelected->button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(mSelected->button->getChildAt(0)); - mKey[mSelectedIndex].type = Type_MagicItem; + mSelected->type = Type_MagicItem; - mKey[mSelectedIndex].button->setFrame("textures\\menu_icon_select_magic_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); - mKey[mSelectedIndex].button->setIcon(item); + mSelected->button->setFrame("textures\\menu_icon_select_magic_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); + mSelected->button->setIcon(item); - mKey[mSelectedIndex].button->setUserString ("ToolTipType", "ItemPtr"); - mKey[mSelectedIndex].button->setUserData(MWWorld::Ptr(item)); + mSelected->button->setUserString("ToolTipType", "ItemPtr"); + mSelected->button->setUserData(MWWorld::Ptr(item)); - if(mMagicSelectionDialog) + if (mMagicSelectionDialog) mMagicSelectionDialog->setVisible(false); } void QuickKeysMenu::onAssignMagic(const std::string& spellId) { - assert(mSelectedIndex >= 0); - ItemWidget* button = mKey[mSelectedIndex].button; - while(mKey[mSelectedIndex].button->getChildCount()) // Destroy number label - MyGUI::Gui::getInstance().destroyWidget(button->getChildAt(0)); + assert(mSelected); + while (mSelected->button->getChildCount()) // Destroy number label + MyGUI::Gui::getInstance().destroyWidget(mSelected->button->getChildAt(0)); - mKey[mSelectedIndex].type = Type_Magic; + mSelected->type = Type_Magic; + mSelected->id = spellId; - mKey[mSelectedIndex].button->setItem(MWWorld::Ptr()); - mKey[mSelectedIndex].button->setUserString("ToolTipType", "Spell"); - mKey[mSelectedIndex].button->setUserString("Spell", spellId); + mSelected->button->setItem(MWWorld::Ptr()); + mSelected->button->setUserString("ToolTipType", "Spell"); + mSelected->button->setUserString("Spell", spellId); - const MWWorld::ESMStore &esmStore = - MWBase::Environment::get().getWorld()->getStore(); + const MWWorld::ESMStore &esmStore = MWBase::Environment::get().getWorld()->getStore(); // use the icon of the first effect const ESM::Spell* spell = esmStore.get().find(spellId); @@ -281,14 +280,14 @@ namespace MWGui path.insert(slashPos+1, "b_"); path = MWBase::Environment::get().getWindowManager()->correctIconPath(path); - button->setFrame("textures\\menu_icon_select_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); - button->setIcon(path); + mSelected->button->setFrame("textures\\menu_icon_select_magic.dds", MyGUI::IntCoord(2, 2, 40, 40)); + mSelected->button->setIcon(path); if (mMagicSelectionDialog) mMagicSelectionDialog->setVisible(false); } - void QuickKeysMenu::onAssignMagicCancel () + void QuickKeysMenu::onAssignMagicCancel() { mMagicSelectionDialog->setVisible(false); } @@ -296,17 +295,16 @@ namespace MWGui void QuickKeysMenu::updateActivatedQuickKey() { // there is no delayed action, nothing to do. - if (mActivatedIndex < 0) + if (!mActivated) return; - activateQuickKey(mActivatedIndex); + activateQuickKey(mActivated->index); } void QuickKeysMenu::activateQuickKey(int index) { - assert(index-1 >= 0); - ItemWidget* button = mKey[index-1].button; - QuickKeyType type = mKey[index-1].type; + assert(index > 0); + struct keyData *key = &mKey[index-1]; MWWorld::Ptr player = MWMechanics::getPlayer(); MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player); @@ -319,22 +317,23 @@ namespace MWGui || playerStats.getHitRecovery(); bool isReturnNeeded = playerStats.isParalyzed() || playerStats.isDead(); - if (isReturnNeeded && type != Type_Item) + + if (isReturnNeeded && key->type != Type_Item) { return; } - - if (isDelayNeeded && type != Type_Item) + else if(isDelayNeeded && key->type != Type_Item) { - mActivatedIndex = index; + mActivated = key; return; } else - mActivatedIndex = -1; + mActivated = nullptr; - if (type == Type_Item || type == Type_MagicItem) + + if (key->type == Type_Item || key->type == Type_MagicItem) { - MWWorld::Ptr item = *button->getUserData(); + MWWorld::Ptr item = *key->button->getUserData(); MWWorld::ContainerStoreIterator it = store.begin(); for (; it != store.end(); ++it) @@ -347,19 +346,20 @@ namespace MWGui // check the item is available and not broken if (!item || item.getRefData().getCount() < 1 || - (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) + (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) { - item = store.findReplacement(mKey[index-1].id); + item = store.findReplacement(key->id); + if (!item || item.getRefData().getCount() < 1) { MWBase::Environment::get().getWindowManager()->messageBox( - "#{sQuickMenu5} " + mKey[index-1].name); + "#{sQuickMenu5} " + key->name); return; } } - if (type == Type_Item) + if (key->type == Type_Item) { bool isWeapon = item.getTypeName() == typeid(ESM::Weapon).name(); bool isTool = item.getTypeName() == typeid(ESM::Probe).name() || @@ -368,12 +368,11 @@ namespace MWGui // delay weapon switching if player is busy if (isDelayNeeded && (isWeapon || isTool)) { - mActivatedIndex = index; + mActivated = key; return; } - // disable weapon switching if player is dead or paralyzed - if (isReturnNeeded && (isWeapon || isTool)) + else if (isReturnNeeded && (isWeapon || isTool)) { return; } @@ -386,7 +385,7 @@ namespace MWGui MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Weapon); } } - else if (type == Type_MagicItem) + else if (key->type == Type_MagicItem) { // equip, if it can be equipped if (!item.getClass().getEquipmentSlots(item).first.empty()) @@ -402,25 +401,28 @@ namespace MWGui MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Spell); } } - else if (type == Type_Magic) + else if (key->type == Type_Magic) { - std::string spellId = button->getUserString("Spell"); + std::string spellId = key->id; // Make sure the player still has this spell MWMechanics::CreatureStats& stats = player.getClass().getCreatureStats(player); MWMechanics::Spells& spells = stats.getSpells(); + if (!spells.hasSpell(spellId)) { - const ESM::Spell* spell = MWBase::Environment::get().getWorld()->getStore().get().find(spellId); - MWBase::Environment::get().getWindowManager()->messageBox ( - "#{sQuickMenu5} " + spell->mName); + const ESM::Spell* spell = + MWBase::Environment::get().getWorld()->getStore().get().find(spellId); + MWBase::Environment::get().getWindowManager()->messageBox("#{sQuickMenu5} " + spell->mName); return; } + store.setSelectedEnchantItem(store.end()); - MWBase::Environment::get().getWindowManager()->setSelectedSpell(spellId, int(MWMechanics::getSpellSuccessChance(spellId, player))); + MWBase::Environment::get().getWindowManager() + ->setSelectedSpell(spellId, int(MWMechanics::getSpellSuccessChance(spellId, player))); MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Spell); } - else if (type == Type_HandToHand) + else if (key->type == Type_HandToHand) { store.unequipSlot(MWWorld::InventoryStore::Slot_CarriedRight, player); MWBase::Environment::get().getWorld()->getPlayer().setDrawState(MWMechanics::DrawState_Weapon); @@ -517,7 +519,7 @@ namespace MWGui void QuickKeysMenu::readRecord(ESM::ESMReader &reader, uint32_t type) { - if(type != ESM::REC_KEYS) + if (type != ESM::REC_KEYS) return; ESM::QuickKeys keys; @@ -527,34 +529,34 @@ namespace MWGui MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player); int i=0; - for(std::vector::const_iterator it = keys.mKeys.begin(); it != keys.mKeys.end(); ++it) + for (std::vector::const_iterator it = keys.mKeys.begin(); it != keys.mKeys.end(); ++it) { - if(i >= 10) + if (i >= 10) return; - mSelectedIndex = i; - int keyType = it->mType; - std::string id = it->mId; + mSelected = &mKey[i]; + mSelected->type = (QuickKeysMenu::QuickKeyType) it->mType; + mSelected->id = it->mId; - switch (keyType) + switch (mSelected->type) { case Type_Magic: - if(MWBase::Environment::get().getWorld()->getStore().get().search(id)) - onAssignMagic(id); + if (MWBase::Environment::get().getWorld()->getStore().get().search(mSelected->id)) + onAssignMagic(mSelected->id); break; case Type_Item: case Type_MagicItem: { // Find the item by id - MWWorld::Ptr item = store.findReplacement(id); + MWWorld::Ptr item = store.findReplacement(mSelected->id); - if(item.isEmpty()) + if (item.isEmpty()) unassign(&mKey[i]); else { - if(keyType == Type_Item) + if (mSelected->type == Type_Item) onAssignItem(item); - else if(keyType == Type_MagicItem) + else if (mSelected->type == Type_MagicItem) onAssignMagicItem(item); } diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index f11673f5fe..56394d6603 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -66,6 +66,8 @@ namespace MWGui }; std::vector mKey; + struct keyData* mSelected; + struct keyData* mActivated; MyGUI::EditBox* mInstructionLabel; MyGUI::Button* mOkButton; @@ -74,9 +76,6 @@ namespace MWGui ItemSelectionDialog* mItemSelectionDialog; MagicSelectionDialog* mMagicSelectionDialog; - int mSelectedIndex; - int mActivatedIndex; - void onQuickKeyButtonClicked(MyGUI::Widget* sender); void onOkButtonClicked(MyGUI::Widget* sender); From 24d5fb09da679e2f62737678ad21668b10fa49a9 Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Thu, 28 Jun 2018 22:55:02 +1000 Subject: [PATCH 07/11] fix crash on simultaneous key presses --- apps/openmw/mwgui/quickkeysmenu.cpp | 20 ++++++-------------- 1 file changed, 6 insertions(+), 14 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index b2bf9df0ed..4c5a7bf16c 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -303,7 +303,8 @@ namespace MWGui void QuickKeysMenu::activateQuickKey(int index) { - assert(index > 0); + assert(index >= 1 && index <= 9); + struct keyData *key = &mKey[index-1]; MWWorld::Ptr player = MWMechanics::getPlayer(); @@ -318,15 +319,12 @@ namespace MWGui bool isReturnNeeded = playerStats.isParalyzed() || playerStats.isDead(); - if (isReturnNeeded && key->type != Type_Item) - { + if (isReturnNeeded) return; - } - else if(isDelayNeeded && key->type != Type_Item) - { + + else if (isDelayNeeded) mActivated = key; - return; - } + else mActivated = nullptr; @@ -367,12 +365,6 @@ namespace MWGui // delay weapon switching if player is busy if (isDelayNeeded && (isWeapon || isTool)) - { - mActivated = key; - return; - } - // disable weapon switching if player is dead or paralyzed - else if (isReturnNeeded && (isWeapon || isTool)) { return; } From ed71656ea6efcbdaadadb08f4315f457d8544ee9 Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Fri, 29 Jun 2018 01:58:57 +1000 Subject: [PATCH 08/11] fix updateActivatedQuickKey() crash keyboard numbers don't start at zero... --- apps/openmw/mwgui/quickkeysmenu.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 4c5a7bf16c..2899dfb777 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -53,7 +53,7 @@ namespace MWGui for (int i = 0; i < 10; ++i) { - mKey[i].index = i; + mKey[i].index = i+1; getWidget(mKey[i].button, "QuickKey" + MyGUI::utility::toString(i+1)); mKey[i].button->eventMouseButtonClick += MyGUI::newDelegate(this, &QuickKeysMenu::onQuickKeyButtonClicked); @@ -143,7 +143,7 @@ namespace MWGui MyGUI::FloatCoord(0,0,1,1), MyGUI::Align::Default); textBox->setTextAlign(MyGUI::Align::Center); - textBox->setCaption(MyGUI::utility::toString(key->index + 1)); + textBox->setCaption(MyGUI::utility::toString(key->index)); textBox->setNeedMouseFocus(false); } } From 2722ca50fb2cddb5a8518205ec08ba2126dace57 Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Fri, 29 Jun 2018 23:32:05 +1000 Subject: [PATCH 09/11] fix QuickKeysMenu crash on reopening window after item drop + pickup [see: !11#note_85086570] --- apps/openmw/mwgui/quickkeysmenu.cpp | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 2899dfb777..47bc88c8bb 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -99,15 +99,16 @@ namespace MWGui { MWWorld::Ptr item = *mKey[i].button->getUserData(); // Make sure the item is available and is not broken - if (item.getRefData().getCount() < 1 || + if (!item || item.getRefData().getCount() < 1 || (item.getClass().hasItemHealth(item) && item.getClass().getItemHealth(item) <= 0)) { // Try searching for a compatible replacement - std::string id = item.getCellRef().getRefId(); + item = store.findReplacement(mKey[i].id); + + if (item) + mKey[i].button->setUserData(MWWorld::Ptr(item)); - item = store.findReplacement(id); - mKey[i].button->setUserData(MWWorld::Ptr(item)); break; } } From 596be205c1179fb363f04950d435406e522982ea Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Fri, 29 Jun 2018 23:43:51 +1000 Subject: [PATCH 10/11] cleanup unnecessary struct keywords... --- apps/openmw/mwgui/quickkeysmenu.cpp | 6 +++--- apps/openmw/mwgui/quickkeysmenu.hpp | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index 47bc88c8bb..4bfbd4dacd 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -33,7 +33,7 @@ namespace MWGui QuickKeysMenu::QuickKeysMenu() : WindowBase("openmw_quickkeys_menu.layout") - , mKey(std::vector(10)) + , mKey(std::vector(10)) , mSelected(nullptr) , mActivated(nullptr) , mAssignDialog(0) @@ -116,7 +116,7 @@ namespace MWGui } } - void QuickKeysMenu::unassign(struct keyData* key) + void QuickKeysMenu::unassign(keyData* key) { key->button->clearUserStrings(); key->button->setItem(MWWorld::Ptr()); @@ -306,7 +306,7 @@ namespace MWGui { assert(index >= 1 && index <= 9); - struct keyData *key = &mKey[index-1]; + keyData *key = &mKey[index-1]; MWWorld::Ptr player = MWMechanics::getPlayer(); MWWorld::InventoryStore& store = player.getClass().getInventoryStore(player); diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index 56394d6603..6d2ab8494a 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -65,7 +65,7 @@ namespace MWGui keyData(): index(-1), button(nullptr), type(Type_Unassigned), id(""), name("") {} }; - std::vector mKey; + std::vector mKey; struct keyData* mSelected; struct keyData* mActivated; From 09c9bd34c3e438ad2a47be6be098e5e75b46fb5b Mon Sep 17 00:00:00 2001 From: Finbar Crago Date: Sat, 30 Jun 2018 12:43:50 +1000 Subject: [PATCH 11/11] cleanup more unnecessary struct keywords... --- apps/openmw/mwgui/quickkeysmenu.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.hpp b/apps/openmw/mwgui/quickkeysmenu.hpp index 6d2ab8494a..431e847cbb 100644 --- a/apps/openmw/mwgui/quickkeysmenu.hpp +++ b/apps/openmw/mwgui/quickkeysmenu.hpp @@ -66,8 +66,8 @@ namespace MWGui }; std::vector mKey; - struct keyData* mSelected; - struct keyData* mActivated; + keyData* mSelected; + keyData* mActivated; MyGUI::EditBox* mInstructionLabel; MyGUI::Button* mOkButton; @@ -79,7 +79,7 @@ namespace MWGui void onQuickKeyButtonClicked(MyGUI::Widget* sender); void onOkButtonClicked(MyGUI::Widget* sender); - void unassign(struct keyData* key); + void unassign(keyData* key); }; class QuickKeysMenuAssign : public WindowModal