From 5a9396fbcb9b236b814f244c35cf715b717c66ac Mon Sep 17 00:00:00 2001 From: sigonasr2 Date: Sun, 31 Dec 2023 18:05:41 -0600 Subject: [PATCH] Fix hover over label update bug inside character equip menu (thanks to a side effect of updating the item reference). Applied random stats to equip stats. Made sure that rings that are the same in both equip slots do not cause the stats difference display from showing any actual differences. Prevent accidental unequipping of rings already equipped (if you technically were to swap between them) --- Crawler/CharacterMenuWindow.cpp | 84 ++++++++++++++++++++------------- Crawler/EquipSlotButton.h | 7 ++- Crawler/MenuItemItemButton.h | 3 +- Crawler/MenuLabel.h | 8 ++-- Crawler/Player.cpp | 1 + Crawler/Version.h | 2 +- 6 files changed, 64 insertions(+), 41 deletions(-) diff --git a/Crawler/CharacterMenuWindow.cpp b/Crawler/CharacterMenuWindow.cpp index f48cb8d8..fc12f0a0 100644 --- a/Crawler/CharacterMenuWindow.cpp +++ b/Crawler/CharacterMenuWindow.cpp @@ -133,26 +133,37 @@ void Menu::InitializeCharacterMenuWindow(){ ScrollableWindowComponent*equipList=Component(data.component->parentMenu,"Equip List"); equipList->RemoveAllComponents(); for(int counter=0;const std::weak_ptrit:availableEquipment){ + const static auto OppositeRingSlotDoesNotMatchCurrentEquip=[](RowItemDisplay*comp){ + EquipSlot slot=EquipSlot(comp->I(Attribute::EQUIP_TYPE)); + std::weak_ptrotherItem; + if(slot==EquipSlot::RING1)otherItem=Inventory::GetEquip(EquipSlot::RING2); + else + if(slot==EquipSlot::RING2)otherItem=Inventory::GetEquip(EquipSlot::RING1); + return ISBLANK(otherItem)||(&*comp->GetItem().lock()!=&*otherItem.lock()); + }; + auto equip=equipList->ADD("Equip Item "+std::to_string(counter),RowItemDisplay)({{2,2+counter*29.f},{120-15,28}},it, [](MenuFuncData data){ RowItemDisplay*comp=DYNAMIC_CAST(data.component); if(comp!=nullptr){ - Inventory::EquipItem(comp->GetItem(),EquipSlot(comp->I(Attribute::EQUIP_TYPE))); - for(MenuComponent*button:((ScrollableWindowComponent*)data.parentComponent)->GetComponents()){ - RowItemDisplay*comp=DYNAMIC_CAST(button); - if(comp!=nullptr){ - comp->SetSelected(false); - }else{ - ERR("WARNING! Attempting to cast a button that isn't a RowItemDisplay!"); + if(OppositeRingSlotDoesNotMatchCurrentEquip(comp)){ //If we find that the opposite ring slot is equipped to us, this would be an item swap or the exact same ring, therefore no stat calculations apply. + Inventory::EquipItem(comp->GetItem(),EquipSlot(comp->I(Attribute::EQUIP_TYPE))); + for(MenuComponent*button:((ScrollableWindowComponent*)data.parentComponent)->GetComponents()){ + RowItemDisplay*comp=DYNAMIC_CAST(button); + if(comp!=nullptr){ + comp->SetSelected(false); + }else{ + ERR("WARNING! Attempting to cast a button that isn't a RowItemDisplay!"); + } } + comp->SetSelected(true); + for(int counter=0;const std::string&attribute:displayAttrs){ + StatLabel*statDisplayLabel=Component(CHARACTER_MENU,"Attribute "+std::string(ItemAttribute::Get(attribute).Name())+" Label"); + statDisplayLabel->SetStatChangeAmt(0); + } + MenuItemItemButton*equipButton=Component(CHARACTER_MENU,"Equip Slot "+slotNames[data.parentComponent->I(A::INDEXED_THEME)]); + equipButton->SetItem(comp->GetItem()); } - comp->SetSelected(true); - for(int counter=0;const std::string&attribute:displayAttrs){ - StatLabel*statDisplayLabel=Component(CHARACTER_MENU,"Attribute "+std::string(ItemAttribute::Get(attribute).Name())+" Label"); - statDisplayLabel->SetStatChangeAmt(0); - } - MenuItemItemButton*equipButton=Component(CHARACTER_MENU,"Equip Slot "+slotNames[data.parentComponent->I(A::INDEXED_THEME)]); - equipButton->SetItem(comp->GetItem()); }else{ ERR("WARNING! Attempting to cast a button that isn't a RowItemDisplay!"); } @@ -175,21 +186,23 @@ void Menu::InitializeCharacterMenuWindow(){ if(slot==EquipSlot::RING1)otherItem=Inventory::GetEquip(EquipSlot::RING2); else if(slot==EquipSlot::RING2)otherItem=Inventory::GetEquip(EquipSlot::RING1); - Inventory::EquipItem(buttonItem,slot); - for(int counter=0;const std::string&attribute:displayAttrs){ - StatLabel*statDisplayLabel=Component(CHARACTER_MENU,"Attribute "+std::string(ItemAttribute::Get(attribute).Name())+" Label"); - int statChangeAmt=game->GetPlayer()->GetStat(attribute)-statsBeforeEquip[counter]; - statDisplayLabel->SetStatChangeAmt(statChangeAmt); - counter++; - } - Inventory::UnequipItem(slot); - if(!ISBLANK(equippedItem)){ - Inventory::EquipItem(equippedItem,slot); - } - if(!ISBLANK(otherItem)){ - if(slot==EquipSlot::RING1)Inventory::EquipItem(otherItem,EquipSlot::RING2); - else - if(slot==EquipSlot::RING2)Inventory::EquipItem(otherItem,EquipSlot::RING1); + if(OppositeRingSlotDoesNotMatchCurrentEquip(button)){ //If we find that the opposite ring slot is equipped to us, this would be an item swap or the exact same ring, therefore no stat calculations apply. + Inventory::EquipItem(buttonItem,slot); + for(int counter=0;const std::string&attribute:displayAttrs){ + StatLabel*statDisplayLabel=Component(CHARACTER_MENU,"Attribute "+std::string(ItemAttribute::Get(attribute).Name())+" Label"); + int statChangeAmt=game->GetPlayer()->GetStat(attribute)-statsBeforeEquip[counter]; + statDisplayLabel->SetStatChangeAmt(statChangeAmt); + counter++; + } + Inventory::UnequipItem(slot); + if(!ISBLANK(equippedItem)){ + Inventory::EquipItem(equippedItem,slot); + } + if(!ISBLANK(otherItem)){ + if(slot==EquipSlot::RING1)Inventory::EquipItem(otherItem,EquipSlot::RING2); + else + if(slot==EquipSlot::RING2)Inventory::EquipItem(otherItem,EquipSlot::RING1); + } } }else{ ERR("WARNING! Attempting to cast a button that isn't a RowItemDisplay!"); @@ -226,12 +239,17 @@ void Menu::InitializeCharacterMenuWindow(){ equipmentWindowOpened=true; return true; },[](MenuFuncData data){//On Mouse Hover - if(Component(data.component->parentMenu,"Item Equip Description")->GetLabel()!=""){ + EquipSlot slot=DYNAMIC_CAST(data.component)->GetSlot(); + const std::weak_ptrequip=Inventory::GetEquip(slot); + if(!ISBLANK(equip)){ Component(data.component->parentMenu,"Character Rotating Display")->Enable(false); } return true; },[](MenuFuncData data){//On Mouse Out - if(Component(data.component->parentMenu,"Item Equip Description")->GetLabel()!=""&&!equipmentWindowOpened){ + if(!equipmentWindowOpened){ + Component(data.component->parentMenu,"Item Equip Description")->SetLabel(""); + Component(data.component->parentMenu,"Item Equip Name")->Enable(false); + Component(data.component->parentMenu,"Item Equip Description")->Enable(false); Component(data.component->parentMenu,"Character Rotating Display")->Enable(true); } return true; @@ -258,9 +276,9 @@ void Menu::InitializeCharacterMenuWindow(){ characterMenuWindow->ADD("Back button",MenuComponent)({{windowSize.x/2-64,windowSize.y},{128,12}},"Back",[](MenuFuncData data){Menu::stack.pop_back();return true;})END; - auto itemNameDisplay=characterMenuWindow->ADD("Item Name",MenuLabel)({{0,28},{120,12}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW)END; + auto itemNameDisplay=characterMenuWindow->ADD("Item Name",MenuLabel)({{0,28},{120,12}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW|ComponentAttr::FIT_TO_LABEL)END; auto itemDescriptionDisplay=characterMenuWindow->ADD("Item Description",MenuLabel)({{0,40},{120,windowSize.y-49}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW)END; - auto itemEquipNameDisplay=characterMenuWindow->ADD("Item Equip Name",MenuLabel)({{123,28},{120,12}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW)END; + auto itemEquipNameDisplay=characterMenuWindow->ADD("Item Equip Name",MenuLabel)({{123,28},{120,12}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW|ComponentAttr::FIT_TO_LABEL)END; auto itemEquipDescriptionDisplay=characterMenuWindow->ADD("Item Equip Description",MenuLabel)({{123,40},{120,windowSize.y-49}},"",1,ComponentAttr::BACKGROUND|ComponentAttr::LEFT_ALIGN|ComponentAttr::OUTLINE|ComponentAttr::SHADOW)END; itemNameDisplay->Enable(false); diff --git a/Crawler/EquipSlotButton.h b/Crawler/EquipSlotButton.h index c65d8563..ac1031c3 100644 --- a/Crawler/EquipSlotButton.h +++ b/Crawler/EquipSlotButton.h @@ -53,10 +53,13 @@ public: const std::weak_ptrequip=Inventory::GetEquip(slot); if(!ISBLANK(equip)){ icon=const_cast(equip.lock()->Decal()); - SetItem(equip); + itemRef=equip; }else{ icon=nullptr; - SetItem(Item::BLANK); + itemRef=Item::BLANK; } } + inline const EquipSlot GetSlot()const{ + return slot; + } }; \ No newline at end of file diff --git a/Crawler/MenuItemItemButton.h b/Crawler/MenuItemItemButton.h index f0d1c8eb..773c2b5f 100644 --- a/Crawler/MenuItemItemButton.h +++ b/Crawler/MenuItemItemButton.h @@ -49,12 +49,13 @@ INCLUDE_ITEM_DATA class MenuItemItemButton:public MenuIconButton{ private: - std::weak_ptritemRef; std::string itemNameLabelName; std::string itemDescriptionLabelName; bool hideQty=false; CompactText compact=COMPACT; bool hideDetails=false; +protected: + std::weak_ptritemRef; public: inline MenuItemItemButton(geom2d::rectrect,const std::weak_ptritemRef,MenuType menuDest,MenuFunc onClick,std::string itemNameLabelName,std::string itemDescriptionLabelName,IconButtonAttr attributes=IconButtonAttr::SELECTABLE) :MenuIconButton(rect,!ISBLANK(itemRef)?const_cast(itemRef.lock()->Decal()):nullptr,menuDest,onClick,attributes),itemRef(itemRef),itemNameLabelName(itemNameLabelName),itemDescriptionLabelName(itemDescriptionLabelName){ diff --git a/Crawler/MenuLabel.h b/Crawler/MenuLabel.h index 6b121f46..58ce4739 100644 --- a/Crawler/MenuLabel.h +++ b/Crawler/MenuLabel.h @@ -82,14 +82,14 @@ protected: vf2d(game->GetWrappedTextSize(label,rect.size.x,adjustedScale)); if(fitToLabel){ - float sizeRatio=((labelTextSize*adjustedScale).x)/(rect.size.x-2); - if(sizeRatio>1){ - adjustedScale.x/=sizeRatio; - } labelTextSize= proportional? vf2d(game->GetTextSizeProp(label)*adjustedScale): vf2d(game->GetTextSize(label)*adjustedScale); + float sizeRatio=((labelTextSize*adjustedScale).x)/(rect.size.x-2); + if(sizeRatio>1){ + adjustedScale.x/=sizeRatio; + } } vf2d drawPos=rect.middle()-vf2d{labelTextSize}/2; //Assume centered. diff --git a/Crawler/Player.cpp b/Crawler/Player.cpp index aaac87fe..9560b51a 100644 --- a/Crawler/Player.cpp +++ b/Crawler/Player.cpp @@ -932,6 +932,7 @@ void EntityStats::RecalculateEquipStats(){ if(ISBLANK(equip))continue; for(auto&[key,size]:ItemAttribute::attributes){ equipStats.A(key)+=equip.lock()->GetStats().A_Read(key); + equipStats.A(key)+=equip.lock()->RandomStats().A_Read(key); } } diff --git a/Crawler/Version.h b/Crawler/Version.h index 781decd3..9296d761 100644 --- a/Crawler/Version.h +++ b/Crawler/Version.h @@ -39,7 +39,7 @@ All rights reserved. #define VERSION_MAJOR 0 #define VERSION_MINOR 2 #define VERSION_PATCH 1 -#define VERSION_BUILD 5143 +#define VERSION_BUILD 5161 #define stringify(a) stringify_(a) #define stringify_(a) #a