From 7fd36875649c39a6a04142ed3cdc7406ada6a06e Mon Sep 17 00:00:00 2001 From: Deukhoofd Date: Sat, 25 Apr 2020 20:09:20 +0200 Subject: [PATCH] Cleanup of ExecutingAttack, removing TargetData, and reducing the number of allocations needed. --- CInterface/Battling/ExecutingAttack.cpp | 13 ++------ src/Battling/Flow/TurnHandler.cpp | 17 +++++----- src/Battling/Flow/TurnHandler.hpp | 3 +- src/Battling/Models/ExecutingAttack.hpp | 41 +++++++++++-------------- 4 files changed, 29 insertions(+), 45 deletions(-) diff --git a/CInterface/Battling/ExecutingAttack.cpp b/CInterface/Battling/ExecutingAttack.cpp index c8875fa..213fac1 100644 --- a/CInterface/Battling/ExecutingAttack.cpp +++ b/CInterface/Battling/ExecutingAttack.cpp @@ -11,9 +11,9 @@ export uint8_t CreatureLib_ExecutingAttack_Construct(ExecutingAttack*& out, Crea export void CreatureLib_ExecutingAttack_Destruct(ExecutingAttack* p) { delete p; } -export uint8_t CreatureLib_ExecutingAttack_GetAttackDataForTarget(ExecutingAttack::TargetData*& out, ExecutingAttack* p, - Creature* target) { - Try(out = &p->GetAttackDataForTarget(target);) +export uint8_t CreatureLib_ExecutingAttack_GetHitData(ExecutingAttack::HitData*& out, ExecutingAttack* p, + Creature* target, uint8_t hit) { + Try(out = &p->GetHitData(target, hit);) } export bool CreatureLib_ExecutingAttack_IsCreatureTarget(ExecutingAttack* p, Creature* target) { @@ -23,13 +23,6 @@ export bool CreatureLib_ExecutingAttack_IsCreatureTarget(ExecutingAttack* p, Cre export Creature* CreatureLib_ExecutingAttack_GetUser(ExecutingAttack* p) { return p->GetUser(); } export LearnedAttack* CreatureLib_ExecutingAttack_GetAttack(ExecutingAttack* p) { return p->GetAttack(); } -export uint8_t CreatureLib_TargetData_GetHit(ExecutingAttack::HitData*& out, ExecutingAttack::TargetData* p, - uint8_t hit) { - Try(out = &p->GetHit(hit);) -} -export uint8_t CreatureLib_TargetData_GetNumberOfHits(ExecutingAttack::TargetData* p) { return p->GetNumberOfHits(); } -export bool CreatureLib_TargetData_IsHit(ExecutingAttack::TargetData* p) { return p->IsHit(); } - #define HITDATA_GET_FUNC(name, returnType) \ export returnType CreatureLib_HitData##_##name(const ExecutingAttack::HitData* p) { return p->name(); } diff --git a/src/Battling/Flow/TurnHandler.cpp b/src/Battling/Flow/TurnHandler.cpp index 13faceb..701ea88 100644 --- a/src/Battling/Flow/TurnHandler.cpp +++ b/src/Battling/Flow/TurnHandler.cpp @@ -90,16 +90,15 @@ void TurnHandler::ExecuteAttackChoice(AttackTurnChoice* choice) { } HOOK(OnBeforeAttack, attack, attack); - for (auto& kv : attack->GetTargets()) { - HandleAttackForTarget(attack, kv.first, kv.second); + for (auto& t : attack->GetTargets()) { + HandleAttackForTarget(attack, t); } // TODO: We currently delete this, but we probably want to store this in a log, so scripts can look it up. delete attack; } -void TurnHandler::HandleAttackForTarget(ExecutingAttack* attack, Creature* target, - ExecutingAttack::TargetData& targetData) { +void TurnHandler::HandleAttackForTarget(ExecutingAttack* attack, Creature* target) { auto user = attack->GetUser(); AssertNotNull(user) AssertNotNull(target) @@ -121,26 +120,24 @@ void TurnHandler::HandleAttackForTarget(ExecutingAttack* attack, Creature* targe return; } - if (!targetData.IsHit()) { + auto numberOfHits = attack->GetNumberOfHits(); + if (numberOfHits == 0) { HOOK(OnAttackMiss, targetSource, attack, target); return; } - auto numHits = targetData.GetNumberOfHits(); - if (numHits == 0) - return; auto attackData = attack->GetAttack()->GetAttack(); auto library = user->GetBattle()->GetLibrary(); AssertNotNull(library) auto dmgLibrary = library->GetDamageLibrary(); - for (uint8_t hitIndex = 0; hitIndex < numHits; hitIndex++) { + for (uint8_t hitIndex = 0; hitIndex < numberOfHits; hitIndex++) { if (user->IsFainted()) { break; } if (target->IsFainted()) { break; } - auto& hit = targetData.GetHit(hitIndex); + auto& hit = attack->GetHitData(target, hitIndex); auto hitType = hit.GetType(); HOOK(ChangeAttackType, targetSource, attack, target, hitIndex, &hitType); auto effectiveness = library->GetTypeLibrary()->GetEffectiveness(hitType, target->GetTypes()); diff --git a/src/Battling/Flow/TurnHandler.hpp b/src/Battling/Flow/TurnHandler.hpp index 64afaa9..f6d0959 100644 --- a/src/Battling/Flow/TurnHandler.hpp +++ b/src/Battling/Flow/TurnHandler.hpp @@ -14,8 +14,7 @@ namespace CreatureLib::Battling { static void ExecuteChoice(BaseTurnChoice* choice); static void ExecuteAttackChoice(AttackTurnChoice* choice); - static void HandleAttackForTarget(ExecutingAttack* attack, Creature* target, - ExecutingAttack::TargetData& targetData); + static void HandleAttackForTarget(ExecutingAttack* attack, Creature* target); static void ExecuteSwitchChoice(SwitchTurnChoice* choice); static void ExecuteFleeChoice(FleeTurnChoice* choice); diff --git a/src/Battling/Models/ExecutingAttack.hpp b/src/Battling/Models/ExecutingAttack.hpp index 836e4ba..f00b709 100644 --- a/src/Battling/Models/ExecutingAttack.hpp +++ b/src/Battling/Models/ExecutingAttack.hpp @@ -37,24 +37,10 @@ namespace CreatureLib::Battling { inline void SetType(uint8_t value) noexcept { _type = value; } }; - class TargetData { - bool _isHit = true; - List _hits; - - public: - explicit TargetData(uint8_t numberOfHits) : _hits(numberOfHits) { _hits.Resize(numberOfHits, HitData()); } - TargetData() = default; - TargetData& operator=(const TargetData&) = delete; - - HitData& GetHit(uint8_t index) { return _hits[index]; } - - uint8_t GetNumberOfHits() const noexcept { return _hits.Count(); } - - bool IsHit() const noexcept { return _isHit; } - }; - private: - Dictionary _targets; + List _targets; + uint8_t _numberHits; + List _hits; Creature* _user; LearnedAttack* _attack; Script* _script; @@ -62,21 +48,30 @@ namespace CreatureLib::Battling { public: ExecutingAttack(const List& targets, uint8_t numberHits, Creature* user, LearnedAttack* attack, Script* script) - : _targets(targets.Count()), _user(user), _attack(attack), _script(script) { + : _targets(targets.Count()), _numberHits(numberHits), _hits(targets.Count() * numberHits), _user(user), + _attack(attack), _script(script) { AssertNotNull(user) AssertNotNull(attack) for (auto target : targets) { - _targets.Insert(target, TargetData(numberHits)); + _targets.Append(target); + _hits.Resize(numberHits); } } virtual ~ExecutingAttack() noexcept { delete _script; }; - TargetData& GetAttackDataForTarget(Creature* creature) { return _targets[creature]; } + HitData& GetHitData(Creature* creature, uint8_t hit) { + for (size_t i = 0; i < _targets.Count(); i++) { + if (_targets[i] == creature) { + return _hits[i * _numberHits + hit]; + } + } + throw CreatureException("Invalid target requested."); + } - bool IsCreatureTarget(Creature* creature) noexcept { return _targets.Has(creature); } - - Dictionary& GetTargets() noexcept { return _targets; } + bool IsCreatureTarget(Creature* creature) noexcept { return _targets.IndexOf(creature) != -1; } + const List& GetTargets() noexcept { return _targets; } + uint8_t GetNumberOfHits() const noexcept { return _numberHits; } Creature* GetUser() noexcept { return _user; }