From f142f8f8d064eb167e094e722cb6b5f5829a6325 Mon Sep 17 00:00:00 2001 From: NotAdam Date: Sat, 9 Feb 2019 20:49:22 +1100 Subject: [PATCH] add 99.99% accurate (probably) mp calculation --- src/world/Action/Action.cpp | 83 +++++++++++++++++++++++++++++++++++++ src/world/Action/Action.h | 3 ++ 2 files changed, 86 insertions(+) diff --git a/src/world/Action/Action.cpp b/src/world/Action/Action.cpp index d7ac7e18..1ce77f9e 100644 --- a/src/world/Action/Action.cpp +++ b/src/world/Action/Action.cpp @@ -34,6 +34,9 @@ Sapphire::Action::Action::Action( Entity::CharaPtr caster, uint32_t actionId, m_costType = static_cast< Common::ActionCostType >( action->costType ); m_cost = action->cost; + + if( caster->isPlayer() && isCastedAction() ) + calculateMPCost(); } uint32_t Sapphire::Action::Action::getId() const @@ -41,6 +44,86 @@ uint32_t Sapphire::Action::Action::getId() const return m_id; } +void Sapphire::Action::Action::calculateMPCost() +{ + auto level = m_pSource->getLevel(); + + // each level range is 1-10, 11-20, 21-30, ... therefore: + // level 50 should be in the 4th group, not the 5th + // dividing by 10 on the border will break this unless we subtract 1 + auto levelGroup = std::max< uint8_t >( level - 1, 1 ) / 10; + + float cost = m_cost; + + // thanks to andrew for helping me figure this shit out, should be pretty accurate + switch( levelGroup ) + { + // level 1-10 + case 0: + { + // r^2 = 0.9999 + cost = 0.0952f * level + 0.9467f; + break; + } + + // level 11-20 + case 1: + { + // r^2 = 1 + cost = 0.19f * level; + break; + } + + // level 21-30 + case 2: + { + // r^2 = 1 + cost = 0.38f * level - 3.8f; + break; + } + + // level 31-40 + case 3: + { + // r^2 = 1 + cost = 0.6652f * level - 12.358f; + break; + } + + // level 41-50 + case 4: + { + // r^2 = 1 + cost = 1.2352f * level - 35.159f; + break; + } + + // level 51-60 + case 5: + { + // r^2 = 1 + cost = 0.0654f * std::exp( 0.1201f * level ); + break; + } + + // level 61-70 + case 6: + { + // r^2 = 0.9998 + cost = 0.2313f * ( level * level ) - 26.98f * level + 875.21f; + break; + } + } + + // m_cost is the base cost, cost is the multiplier for the current player level + m_cost = static_cast< uint16_t >( std::round( cost * m_cost ) ); +} + +void Sapphire::Action::Action::subtractCostFromCaster() +{ + +} + void Sapphire::Action::Action::setPos( Sapphire::Common::FFXIVARR_POSITION3 pos ) { m_pos = pos; diff --git a/src/world/Action/Action.h b/src/world/Action/Action.h index 79c5581c..2c3e9a3e 100644 --- a/src/world/Action/Action.h +++ b/src/world/Action/Action.h @@ -74,6 +74,9 @@ namespace Sapphire::Action protected: + void calculateMPCost(); + void subtractCostFromCaster(); + /*! * @brief Some actions are capable of both healing and dealing damage. This identifies them. */