From 771eb65b924c301ac52f77f5bde8da387036bf3c Mon Sep 17 00:00:00 2001 From: David Markowitz Date: Tue, 25 Jul 2023 21:29:06 -0700 Subject: [PATCH] two tables done --- dDatabase/Tables/CDSkillBehaviorTable.cpp | 12 ++----- dDatabase/Tables/CDSkillBehaviorTable.h | 4 +-- dDatabase/Tables/CDTable.h | 1 + dDatabase/Tables/CDVendorComponentTable.cpp | 36 +++---------------- dDatabase/Tables/CDVendorComponentTable.h | 7 ++-- dDatabase/Tables/CDZoneTableTable.h | 2 -- dGame/Entity.cpp | 6 ++-- dGame/dBehaviors/OverTimeBehavior.cpp | 3 +- dGame/dComponents/BuffComponent.cpp | 7 +++- dGame/dComponents/InventoryComponent.cpp | 8 +++-- dGame/dComponents/SkillComponent.cpp | 7 +++- dGame/dComponents/VendorComponent.cpp | 12 +++---- dGame/dGameMessages/GameMessageHandler.cpp | 9 +++-- dGame/dInventory/ItemSet.cpp | 10 +++--- .../02_server/Map/General/QbEnemyStunner.cpp | 5 +-- .../FireFirstSkillonStartup.cpp | 5 +-- 16 files changed, 60 insertions(+), 74 deletions(-) diff --git a/dDatabase/Tables/CDSkillBehaviorTable.cpp b/dDatabase/Tables/CDSkillBehaviorTable.cpp index 8ffbb5ce..201aa0d7 100644 --- a/dDatabase/Tables/CDSkillBehaviorTable.cpp +++ b/dDatabase/Tables/CDSkillBehaviorTable.cpp @@ -1,8 +1,6 @@ #include "CDSkillBehaviorTable.h" void CDSkillBehaviorTable::LoadValuesFromDatabase() { - m_empty = CDSkillBehavior(); - // First, get the size of the table unsigned int size = 0; auto tableSize = CDClientDatabase::ExecuteQuery("SELECT COUNT(*) FROM SkillBehavior"); @@ -49,12 +47,8 @@ void CDSkillBehaviorTable::LoadValuesFromDatabase() { tableData.finalize(); } -const CDSkillBehavior& CDSkillBehaviorTable::GetSkillByID(unsigned int skillID) { - std::map::iterator it = this->entries.find(skillID); - if (it != this->entries.end()) { - return it->second; - } - - return m_empty; +const std::optional CDSkillBehaviorTable::GetSkillByID(unsigned int skillID) { + auto it = this->entries.find(skillID); + return it != this->entries.end() ? std::make_optional(it->second) : std::nullopt; } diff --git a/dDatabase/Tables/CDSkillBehaviorTable.h b/dDatabase/Tables/CDSkillBehaviorTable.h index 5b1081cd..e6d06fc3 100644 --- a/dDatabase/Tables/CDSkillBehaviorTable.h +++ b/dDatabase/Tables/CDSkillBehaviorTable.h @@ -28,12 +28,10 @@ struct CDSkillBehavior { class CDSkillBehaviorTable : public CDTable { private: std::map entries; - CDSkillBehavior m_empty; - public: void LoadValuesFromDatabase(); // Gets an entry by skillID - const CDSkillBehavior& GetSkillByID(unsigned int skillID); + const std::optional GetSkillByID(unsigned int skillID); }; diff --git a/dDatabase/Tables/CDTable.h b/dDatabase/Tables/CDTable.h index e4c11fb9..a7929035 100644 --- a/dDatabase/Tables/CDTable.h +++ b/dDatabase/Tables/CDTable.h @@ -5,6 +5,7 @@ #include "DluAssert.h" #include +#include #include #include #include diff --git a/dDatabase/Tables/CDVendorComponentTable.cpp b/dDatabase/Tables/CDVendorComponentTable.cpp index d01fdea2..5d170725 100644 --- a/dDatabase/Tables/CDVendorComponentTable.cpp +++ b/dDatabase/Tables/CDVendorComponentTable.cpp @@ -1,50 +1,24 @@ #include "CDVendorComponentTable.h" void CDVendorComponentTable::LoadValuesFromDatabase() { - - // First, get the size of the table - unsigned int size = 0; - auto tableSize = CDClientDatabase::ExecuteQuery("SELECT COUNT(*) FROM VendorComponent"); - while (!tableSize.eof()) { - size = tableSize.getIntField(0, 0); - - tableSize.nextRow(); - } - - tableSize.finalize(); - - // Reserve the size - this->entries.reserve(size); - // Now get the data auto tableData = CDClientDatabase::ExecuteQuery("SELECT * FROM VendorComponent"); while (!tableData.eof()) { CDVendorComponent entry; - entry.id = tableData.getIntField("id", -1); + uint32_t id = tableData.getIntField("id", -1); entry.buyScalar = tableData.getFloatField("buyScalar", -1.0f); entry.sellScalar = tableData.getFloatField("sellScalar", -1.0f); entry.refreshTimeSeconds = tableData.getFloatField("refreshTimeSeconds", -1.0f); entry.LootMatrixIndex = tableData.getIntField("LootMatrixIndex", -1); - this->entries.push_back(entry); + this->entries.insert_or_assign(id, entry); tableData.nextRow(); } tableData.finalize(); } -//! Queries the table with a custom "where" clause -std::vector CDVendorComponentTable::Query(std::function predicate) { - - std::vector data = cpplinq::from(this->entries) - >> cpplinq::where(predicate) - >> cpplinq::to_vector(); - - return data; +const std::optional CDVendorComponentTable::Query(uint32_t id) { + const auto& iter = entries.find(id); + return iter != entries.end() ? std::make_optional(iter->second) : std::nullopt; } - -//! Gets all the entries in the table -const std::vector& CDVendorComponentTable::GetEntries() const { - return this->entries; -} - diff --git a/dDatabase/Tables/CDVendorComponentTable.h b/dDatabase/Tables/CDVendorComponentTable.h index 29854d49..43d05168 100644 --- a/dDatabase/Tables/CDVendorComponentTable.h +++ b/dDatabase/Tables/CDVendorComponentTable.h @@ -4,7 +4,6 @@ #include "CDTable.h" struct CDVendorComponent { - unsigned int id; //!< The Component ID float buyScalar; //!< Buy Scalar (what does that mean?) float sellScalar; //!< Sell Scalar (what does that mean?) float refreshTimeSeconds; //!< The refresh time @@ -13,13 +12,11 @@ struct CDVendorComponent { class CDVendorComponentTable : public CDTable { private: - std::vector entries; + std::map entries; public: void LoadValuesFromDatabase(); // Queries the table with a custom "where" clause - std::vector Query(std::function predicate); - - const std::vector& GetEntries(void) const; + const std::optional Query(uint32_t id); }; diff --git a/dDatabase/Tables/CDZoneTableTable.h b/dDatabase/Tables/CDZoneTableTable.h index 789024ad..1f676632 100644 --- a/dDatabase/Tables/CDZoneTableTable.h +++ b/dDatabase/Tables/CDZoneTableTable.h @@ -2,8 +2,6 @@ #include "CDTable.h" -#include - struct CDZoneTable { unsigned int zoneID; //!< The Zone ID of the object unsigned int locStatus; //!< The Locale Status(?) diff --git a/dGame/Entity.cpp b/dGame/Entity.cpp index 78ba959a..72803f24 100644 --- a/dGame/Entity.cpp +++ b/dGame/Entity.cpp @@ -1628,9 +1628,9 @@ void Entity::PickupItem(const LWOOBJID& objectID) { std::vector skills = skillsTable->Query([=](CDObjectSkills entry) {return (entry.objectTemplate == p.second.lot); }); for (CDObjectSkills skill : skills) { CDSkillBehaviorTable* skillBehTable = CDClientManager::Instance().GetTable(); - CDSkillBehavior behaviorData = skillBehTable->GetSkillByID(skill.skillID); - - SkillComponent::HandleUnmanaged(behaviorData.behaviorID, GetObjectID()); + auto behaviorData = skillBehTable->GetSkillByID(skill.skillID); + if (!behaviorData) continue; + SkillComponent::HandleUnmanaged(behaviorData->behaviorID, GetObjectID()); auto* missionComponent = GetComponent(); diff --git a/dGame/dBehaviors/OverTimeBehavior.cpp b/dGame/dBehaviors/OverTimeBehavior.cpp index 49077f0f..3122a276 100644 --- a/dGame/dBehaviors/OverTimeBehavior.cpp +++ b/dGame/dBehaviors/OverTimeBehavior.cpp @@ -42,7 +42,8 @@ void OverTimeBehavior::Load() { // Since m_Action is a skillID and not a behavior, get is correlated behaviorID. CDSkillBehaviorTable* skillTable = CDClientManager::Instance().GetTable(); - m_ActionBehaviorId = skillTable->GetSkillByID(m_Action).behaviorID; + auto skillData = skillTable->GetSkillByID(m_Action); + if (skillData) m_ActionBehaviorId = skillData->behaviorID; m_Delay = GetFloat("delay"); m_NumIntervals = GetInt("num_intervals"); diff --git a/dGame/dComponents/BuffComponent.cpp b/dGame/dComponents/BuffComponent.cpp index 68b5182c..c500e833 100644 --- a/dGame/dComponents/BuffComponent.cpp +++ b/dGame/dComponents/BuffComponent.cpp @@ -104,7 +104,12 @@ void BuffComponent::ApplyBuff(const int32_t id, const float duration, const LWOO if (parameter.name == "overtime") { auto* behaviorTemplateTable = CDClientManager::Instance().GetTable(); - behaviorID = behaviorTemplateTable->GetSkillByID(parameter.values[0]).behaviorID; + auto skillInfo = behaviorTemplateTable->GetSkillByID(parameter.values[0]); + if (skillInfo) { + behaviorID = skillInfo->behaviorID; + } else { + Game::logger->Log("BuffComponent", "Failed to find skill info for skill ID %d!", parameter.values[0]); + } stacks = static_cast(parameter.values[1]); tick = parameter.values[2]; const auto unknown2 = parameter.values[3]; // Always 0 diff --git a/dGame/dComponents/InventoryComponent.cpp b/dGame/dComponents/InventoryComponent.cpp index 66b47e52..236e1715 100644 --- a/dGame/dComponents/InventoryComponent.cpp +++ b/dGame/dComponents/InventoryComponent.cpp @@ -1341,8 +1341,12 @@ std::vector InventoryComponent::FindBuffs(Item* item, bool castOnEquip for (const auto& result : results) { if (result.castOnType == 1) { const auto entry = behaviors->GetSkillByID(result.skillID); + if (!entry) { + Game::logger->Log("InventoryComponent", "Buff %i not in database!", result.skillID); - if (entry.skillID == 0) { + continue; + } + if (entry->skillID == 0) { Game::logger->Log("InventoryComponent", "Failed to find buff behavior for skill (%i)!", result.skillID); continue; @@ -1353,7 +1357,7 @@ std::vector InventoryComponent::FindBuffs(Item* item, bool castOnEquip } // If item is not a proxy, add its buff to the added buffs. - if (item->GetParent() == LWOOBJID_EMPTY) buffs.push_back(static_cast(entry.behaviorID)); + if (item->GetParent() == LWOOBJID_EMPTY) buffs.push_back(static_cast(entry->behaviorID)); } } diff --git a/dGame/dComponents/SkillComponent.cpp b/dGame/dComponents/SkillComponent.cpp index 5c1d221a..eb02725c 100644 --- a/dGame/dComponents/SkillComponent.cpp +++ b/dGame/dComponents/SkillComponent.cpp @@ -235,7 +235,12 @@ bool SkillComponent::CastSkill(const uint32_t skillId, LWOOBJID target, const LW // if it's not in the cache look it up and cache it if (pair == m_skillBehaviorCache.end()) { auto skillTable = CDClientManager::Instance().GetTable(); - behaviorId = skillTable->GetSkillByID(skillId).behaviorID; + auto skill = skillTable->GetSkillByID(skillId); + if (!skill) { + Game::logger->LogDebug("SkillComponent", "Tried to cast skill %i but found no skill", skillId); + return false; + } + behaviorId = skill->behaviorID; m_skillBehaviorCache.insert_or_assign(skillId, behaviorId); } else { behaviorId = pair->second; diff --git a/dGame/dComponents/VendorComponent.cpp b/dGame/dComponents/VendorComponent.cpp index e89cc926..94960b0d 100644 --- a/dGame/dComponents/VendorComponent.cpp +++ b/dGame/dComponents/VendorComponent.cpp @@ -127,12 +127,12 @@ void VendorComponent::SetupConstants() { int componentID = compRegistryTable->GetByIDAndType(m_Parent->GetLOT(), eReplicaComponentType::VENDOR); auto* vendorComponentTable = CDClientManager::Instance().GetTable(); - std::vector vendorComps = vendorComponentTable->Query([=](CDVendorComponent entry) { return (entry.id == componentID); }); - if (vendorComps.empty()) return; - m_BuyScalar = vendorComps[0].buyScalar; - m_SellScalar = vendorComps[0].sellScalar; - m_RefreshTimeSeconds = vendorComps[0].refreshTimeSeconds; - m_LootMatrixID = vendorComps[0].LootMatrixIndex; + auto vendorCompData = vendorComponentTable->Query(componentID); + if (!vendorCompData) return; + m_BuyScalar = vendorCompData->buyScalar; + m_SellScalar = vendorCompData->sellScalar; + m_RefreshTimeSeconds = vendorCompData->refreshTimeSeconds; + m_LootMatrixID = vendorCompData->LootMatrixIndex; } bool VendorComponent::SellsItem(const LOT item) const { diff --git a/dGame/dGameMessages/GameMessageHandler.cpp b/dGame/dGameMessages/GameMessageHandler.cpp index 83005b6f..b290bd68 100644 --- a/dGame/dGameMessages/GameMessageHandler.cpp +++ b/dGame/dGameMessages/GameMessageHandler.cpp @@ -288,7 +288,12 @@ void GameMessageHandler::HandleMessage(RakNet::BitStream* inStream, const System } CDSkillBehaviorTable* skillTable = CDClientManager::Instance().GetTable(); - unsigned int behaviorId = skillTable->GetSkillByID(startSkill.skillID).behaviorID; + auto skill = skillTable->GetSkillByID(startSkill.skillID); + if (!skill) { + Game::logger->Log("GameMessageHandler", "Failed to find skill %d in the skill table!", startSkill.skillID); + return; + } + unsigned int behaviorId = skill->behaviorID; bool success = false; @@ -301,7 +306,7 @@ void GameMessageHandler::HandleMessage(RakNet::BitStream* inStream, const System if (success && entity->GetCharacter()) { DestroyableComponent* destComp = entity->GetComponent(); - destComp->SetImagination(destComp->GetImagination() - skillTable->GetSkillByID(startSkill.skillID).imaginationcost); + destComp->SetImagination(destComp->GetImagination() - skill->imaginationcost); } delete bs; diff --git a/dGame/dInventory/ItemSet.cpp b/dGame/dInventory/ItemSet.cpp index a8e58739..9cac290b 100644 --- a/dGame/dInventory/ItemSet.cpp +++ b/dGame/dInventory/ItemSet.cpp @@ -131,11 +131,12 @@ void ItemSet::OnEquip(const LOT lot) { for (const auto skill : skillSet) { auto* skillTable = CDClientManager::Instance().GetTable(); - const auto behaviorId = skillTable->GetSkillByID(skill).behaviorID; + auto skillData = skillTable->GetSkillByID(skill); + if (!skillData) continue; missionComponent->Progress(eMissionTaskType::USE_SKILL, skill); - skillComponent->HandleUnmanaged(behaviorId, m_InventoryComponent->GetParent()->GetObjectID()); + skillComponent->HandleUnmanaged(skillData->behaviorID, m_InventoryComponent->GetParent()->GetObjectID()); } } @@ -163,9 +164,10 @@ void ItemSet::OnUnEquip(const LOT lot) { for (const auto skill : skillSet) { auto* skillTable = CDClientManager::Instance().GetTable(); - const auto behaviorId = skillTable->GetSkillByID(skill).behaviorID; + auto skillData = skillTable->GetSkillByID(skill); + if (!skillData) continue; - skillComponent->HandleUnCast(behaviorId, m_InventoryComponent->GetParent()->GetObjectID()); + skillComponent->HandleUnCast(skillData->behaviorID, m_InventoryComponent->GetParent()->GetObjectID()); } } diff --git a/dScripts/02_server/Map/General/QbEnemyStunner.cpp b/dScripts/02_server/Map/General/QbEnemyStunner.cpp index 441d743c..2b8967fb 100644 --- a/dScripts/02_server/Map/General/QbEnemyStunner.cpp +++ b/dScripts/02_server/Map/General/QbEnemyStunner.cpp @@ -23,9 +23,10 @@ void QbEnemyStunner::OnRebuildComplete(Entity* self, Entity* target) { // For each skill, cast it with the associated behavior ID. for (auto skill : skills) { CDSkillBehaviorTable* skillBehaviorTable = CDClientManager::Instance().GetTable(); - CDSkillBehavior behaviorData = skillBehaviorTable->GetSkillByID(skill.skillID); + auto behaviorData = skillBehaviorTable->GetSkillByID(skill.skillID); + if (!behaviorData) continue; - skillBehaviorMap.insert(std::make_pair(skill.skillID, behaviorData.behaviorID)); + skillBehaviorMap.insert(std::make_pair(skill.skillID, behaviorData->behaviorID)); } // If there are no skills found, insert a default skill to use. diff --git a/dScripts/EquipmentScripts/FireFirstSkillonStartup.cpp b/dScripts/EquipmentScripts/FireFirstSkillonStartup.cpp index 389f3621..1624a9e2 100644 --- a/dScripts/EquipmentScripts/FireFirstSkillonStartup.cpp +++ b/dScripts/EquipmentScripts/FireFirstSkillonStartup.cpp @@ -17,10 +17,11 @@ void FireFirstSkillonStartup::OnStartup(Entity* self) { // For each skill, cast it with the associated behavior ID. for (auto skill : skills) { CDSkillBehaviorTable* skillBehaviorTable = CDClientManager::Instance().GetTable(); - CDSkillBehavior behaviorData = skillBehaviorTable->GetSkillByID(skill.skillID); + auto behaviorData = skillBehaviorTable->GetSkillByID(skill.skillID); + if (!behaviorData) continue; // Should parent entity be null, make the originator self. const auto target = self->GetParentEntity() ? self->GetParentEntity()->GetObjectID() : self->GetObjectID(); - skillComponent->CalculateBehavior(skill.skillID, behaviorData.behaviorID, LWOOBJID_EMPTY, false, false, target); + skillComponent->CalculateBehavior(skill.skillID, behaviorData->behaviorID, LWOOBJID_EMPTY, false, false, target); } }