From c84beee30a2002c324b604208435eb8addb7350e Mon Sep 17 00:00:00 2001 From: NotAdam Date: Sat, 21 Jul 2018 23:32:10 +1000 Subject: [PATCH] replace old inline generation of effects packet with a wrapper --- src/common/Common.h | 7 ++ .../Network/PacketDef/Zone/ServerZoneDef.h | 15 ++--- .../sapphire_zone/Action/ActionMount.cpp | 21 +++--- .../sapphire_zone/Action/ActionTeleport.cpp | 17 ++--- .../sapphire_zone/Action/EventItemAction.cpp | 11 ++-- src/servers/sapphire_zone/Actor/Chara.cpp | 61 ++++++++--------- src/servers/sapphire_zone/Actor/Player.cpp | 54 +++++++-------- .../Network/PacketWrappers/EffectPacket.h | 65 +++++++++++++++++++ 8 files changed, 146 insertions(+), 105 deletions(-) create mode 100644 src/servers/sapphire_zone/Network/PacketWrappers/EffectPacket.h diff --git a/src/common/Common.h b/src/common/Common.h index 7a72418b..39fbc393 100644 --- a/src/common/Common.h +++ b/src/common/Common.h @@ -423,6 +423,13 @@ namespace Common { CritDirectHitDamage = 3 }; + enum ActionEffectDisplayType : uint8_t + { + HideActionName = 0, + ShowActionName = 1, + ShowItemName = 2, + }; + enum class ActionCollisionType : uint8_t { None, diff --git a/src/common/Network/PacketDef/Zone/ServerZoneDef.h b/src/common/Network/PacketDef/Zone/ServerZoneDef.h index 2bc4e0ce..3787e1c2 100644 --- a/src/common/Network/PacketDef/Zone/ServerZoneDef.h +++ b/src/common/Network/PacketDef/Zone/ServerZoneDef.h @@ -299,7 +299,7 @@ struct FFXIVIpcUpdateHpMpTp : FFXIVIpcBasePacket * Structural representation of the packet sent by the server * for battle actions */ -struct effectEntry +struct EffectEntry { Common::ActionEffectType effectType; Common::ActionHitSeverityType hitSeverity; @@ -322,24 +322,19 @@ struct FFXIVIpcEffect : FFXIVIpcBasePacket uint16_t hiddenAnimation; // if 0, always shows animation, otherwise hides it. counts up by 1 for each animation skipped on a caster - int16_t rotation; + uint16_t rotation; uint16_t actionAnimationId; // the animation that is played by the casting character uint8_t unknown1E; // can be 0,1,2 - maybe other values? - doesn't do anything? - /* effectDisplayType - * 0 = only show damage/heal amount - * 1 = show damage/heal amount + name - * 2 = show damage/heal amount + name but name is from item.exd, name id is actionId - */ - uint8_t effectDisplayType; + Common::ActionEffectDisplayType effectDisplayType; uint8_t unknown20; // is read by handler, runs code which gets the LODWORD of animationLockTime (wtf?) - uint8_t numEffects; // ignores effects if 0, otherwise parses all of them + uint8_t effectCount; // ignores effects if 0, otherwise parses all of them uint32_t padding_22[2]; - effectEntry effects[8]; + EffectEntry effects[8]; uint16_t padding_6A[3]; diff --git a/src/servers/sapphire_zone/Action/ActionMount.cpp b/src/servers/sapphire_zone/Action/ActionMount.cpp index 912e0c84..2b1ec0da 100644 --- a/src/servers/sapphire_zone/Action/ActionMount.cpp +++ b/src/servers/sapphire_zone/Action/ActionMount.cpp @@ -3,6 +3,7 @@ #include #include #include +#include #include "Network/PacketWrappers/ActorControlPacket142.h" #include "Network/PacketWrappers/ActorControlPacket143.h" @@ -73,19 +74,15 @@ void Core::Action::ActionMount::onFinish() pPlayer->unsetStateFlag( PlayerStateFlag::Casting ); - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), pPlayer->getId(), 4 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( pPlayer->getRot() ) ); - effectPacket->data().animationTargetId = pPlayer->getId(); - effectPacket->data().actionAnimationId = m_id; - // Affects displaying action name next to number in floating text - //effectPacket->data().unknown_62 = 13; - effectPacket->data().actionAnimationId = 4; - effectPacket->data().numEffects = 1; - effectPacket->data().rotation = Math::Util::floatToUInt16Rot( pPlayer->getRot() ); - //effectPacket->data().effectTarget = INVALID_GAME_OBJECT_ID; - effectPacket->data().effects[0].effectType = ActionEffectType::Mount; - effectPacket->data().effects[0].hitSeverity = ActionHitSeverityType::CritDamage; - effectPacket->data().effects[0].value = m_id; + Server::EffectEntry effectEntry{}; + effectEntry.effectType = ActionEffectType::Mount; + effectEntry.hitSeverity = ActionHitSeverityType::CritDamage; + effectEntry.value = m_id; + + effectPacket->addEffect( effectEntry ); pPlayer->sendToInRangeSet( effectPacket, true ); diff --git a/src/servers/sapphire_zone/Action/ActionTeleport.cpp b/src/servers/sapphire_zone/Action/ActionTeleport.cpp index 81a204c4..257bc27d 100644 --- a/src/servers/sapphire_zone/Action/ActionTeleport.cpp +++ b/src/servers/sapphire_zone/Action/ActionTeleport.cpp @@ -2,6 +2,8 @@ #include #include #include +#include +#include #include "Network/PacketWrappers/ActorControlPacket142.h" #include "Network/PacketWrappers/ActorControlPacket143.h" @@ -84,19 +86,12 @@ void Core::Action::ActionTeleport::onFinish() pPlayer->setZoningType( ZoneingType::Teleport ); - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); - effectPacket->data().animationTargetId = pPlayer->getId(); - effectPacket->data().actionAnimationId = 5; - //effectPacket.data().unknown_3 = 1; - effectPacket->data().actionAnimationId = 5; - effectPacket->data().numEffects = 1; - effectPacket->data().rotation = static_cast< uint16_t >( 0x8000 * ( ( pPlayer->getRot() + 3.1415926 ) ) / 3.1415926 ); - effectPacket->data().effectTargetId = pPlayer->getId(); + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), pPlayer->getId(), 5 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( pPlayer->getRot() ) ); + + pPlayer->sendToInRangeSet( effectPacket, true ); - pPlayer->teleport( m_targetAetheryte ); - - } void Core::Action::ActionTeleport::onInterrupt() diff --git a/src/servers/sapphire_zone/Action/EventItemAction.cpp b/src/servers/sapphire_zone/Action/EventItemAction.cpp index 8fa6323d..f1ac74e3 100644 --- a/src/servers/sapphire_zone/Action/EventItemAction.cpp +++ b/src/servers/sapphire_zone/Action/EventItemAction.cpp @@ -7,6 +7,7 @@ #include "Network/PacketWrappers/ActorControlPacket142.h" #include "Network/PacketWrappers/ActorControlPacket143.h" +#include "Network/PacketWrappers/EffectPacket.h" #include "Actor/Player.h" @@ -69,13 +70,9 @@ void Core::Action::EventItemAction::onFinish() try { - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( m_pSource->getId() ); - effectPacket->data().animationTargetId = static_cast< uint32_t >( m_additional ); - effectPacket->data().actionAnimationId = 1; - effectPacket->data().actionId = m_id; - effectPacket->data().numEffects = 1; - effectPacket->data().rotation = Math::Util::floatToUInt16Rot( m_pSource->getRot() ); - effectPacket->data().effectTargetId = static_cast< uint32_t >( m_additional ); + auto effectPacket = boost::make_shared< Server::EffectPacket >( m_pSource->getId(), m_additional, m_id ); + effectPacket->setAnimationId( 1 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( m_pSource->getRot() ) ); m_pSource->getAsPlayer()->unsetStateFlag( Common::PlayerStateFlag::Casting ); m_pSource->sendToInRangeSet( effectPacket, true ); diff --git a/src/servers/sapphire_zone/Actor/Chara.cpp b/src/servers/sapphire_zone/Actor/Chara.cpp index a2e6be7d..b0b22153 100644 --- a/src/servers/sapphire_zone/Actor/Chara.cpp +++ b/src/servers/sapphire_zone/Actor/Chara.cpp @@ -4,6 +4,7 @@ #include #include #include +#include #include "Forwards.h" #include "Action/Action.h" @@ -399,21 +400,20 @@ void Core::Entity::Chara::autoAttack( CharaPtr pTarget ) uint16_t damage = static_cast< uint16_t >( 10 + rand() % 12 ); uint32_t variation = static_cast< uint32_t >( 0 + rand() % 4 ); - auto ipcEffect = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); - ipcEffect->data().animationTargetId = pTarget->getId(); - ipcEffect->data().actionAnimationId = 0x366; - ipcEffect->data().actionId = 0x366; - ipcEffect->data().numEffects = 1; - ipcEffect->data().rotation = Math::Util::floatToUInt16Rot( getRot() ); - ipcEffect->data().effectTargetId = pTarget->getId(); - ipcEffect->data().effects[0].value = damage; - ipcEffect->data().effects[0].effectType = ActionEffectType::Damage; - ipcEffect->data().effects[0].hitSeverity = static_cast< ActionHitSeverityType >( variation ); + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), pTarget->getId(), 0x336 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( getRot() ) ); - sendToInRangeSet( ipcEffect ); + Server::EffectEntry effectEntry{ }; + effectEntry.value = damage; + effectEntry.effectType = ActionEffectType::Damage; + effectEntry.hitSeverity = static_cast< ActionHitSeverityType >( variation ); + + effectPacket->addEffect( effectEntry ); + + sendToInRangeSet( effectPacket ); if( isPlayer() ) - getAsPlayer()->queuePacket( ipcEffect ); + getAsPlayer()->queuePacket( effectPacket ); pTarget->takeDamage( damage ); } @@ -440,16 +440,8 @@ void Core::Entity::Chara::handleScriptSkill( uint32_t type, uint16_t actionId, u // Todo: Effect packet generator. 90% of this is basically setting params and it's basically unreadable. // Prepare packet. This is seemingly common for all packets in the action handler. - - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); - effectPacket->data().animationTargetId = target.getId(); - effectPacket->data().actionAnimationId = actionId; - //effectPacket->data().unknown_62 = 1; // Affects displaying action name next to number in floating text - //effectPacket->data().globalEffectCounter = 1; // This seems to have an effect on the "double-cast finish" animation - effectPacket->data().actionId = actionId; - effectPacket->data().numEffects = 1; - effectPacket->data().rotation = Math::Util::floatToUInt16Rot( getRot() ); - effectPacket->data().effectTargetId = target.getId(); + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), target.getId(), actionId ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( getRot() ) ); // Todo: for each actor, calculate how much damage the calculated value should deal to them - 2-step damage calc. we only have 1-step switch( type ) @@ -457,10 +449,12 @@ void Core::Entity::Chara::handleScriptSkill( uint32_t type, uint16_t actionId, u case ActionEffectType::Damage: { - effectPacket->data().effects[0].value = static_cast< uint16_t >( param1 ); - effectPacket->data().effects[0].effectType = ActionEffectType::Damage; - effectPacket->data().effects[0].hitSeverity = ActionHitSeverityType::NormalDamage; - //effectPacket->data().effects[0].unknown_3 = 7; + Server::EffectEntry effectEntry{}; + effectEntry.value = static_cast< uint16_t >( param1 ); + effectEntry.effectType = ActionEffectType::Damage; + effectEntry.hitSeverity = ActionHitSeverityType::NormalDamage; + + effectPacket->addEffect( effectEntry ); if( actionInfoPtr->castType == 1 && actionInfoPtr->effectRange != 0 || actionInfoPtr->castType != 1 ) { @@ -484,8 +478,7 @@ void Core::Entity::Chara::handleScriptSkill( uint32_t type, uint16_t actionId, u for( const auto& pHitActor : actorsCollided ) { - effectPacket->data().animationTargetId = pHitActor->getId(); - effectPacket->data().effectTargetId = pHitActor->getId(); + effectPacket->setTargetActor( pHitActor->getId() ); // todo: send to range of what? ourselves? when mob script hits this is going to be lacking sendToInRangeSet( effectPacket, true ); @@ -515,9 +508,12 @@ void Core::Entity::Chara::handleScriptSkill( uint32_t type, uint16_t actionId, u { uint32_t calculatedHeal = Math::CalcBattle::calculateHealValue( getAsPlayer(), static_cast< uint32_t >( param1 ) ); - effectPacket->data().effects[0].value = calculatedHeal; - effectPacket->data().effects[0].effectType = ActionEffectType::Heal; - effectPacket->data().effects[0].hitSeverity = ActionHitSeverityType::NormalHeal; + Server::EffectEntry effectEntry{}; + effectEntry.value = calculatedHeal; + effectEntry.effectType = ActionEffectType::Heal; + effectEntry.hitSeverity = ActionHitSeverityType::NormalHeal; + + effectPacket->addEffect( effectEntry ); if( actionInfoPtr->castType == 1 && actionInfoPtr->effectRange != 0 || actionInfoPtr->castType != 1 ) { @@ -537,8 +533,7 @@ void Core::Entity::Chara::handleScriptSkill( uint32_t type, uint16_t actionId, u for( auto pHitActor : actorsCollided ) { - effectPacket->data().animationTargetId = target.getId(); - effectPacket->data().effectTargetId = pHitActor->getId(); + effectPacket->setTargetActor( pHitActor->getId() ); sendToInRangeSet( effectPacket, true ); pHitActor->getAsChara()->heal( calculatedHeal ); diff --git a/src/servers/sapphire_zone/Actor/Player.cpp b/src/servers/sapphire_zone/Actor/Player.cpp index 80356f77..0d1dccb3 100644 --- a/src/servers/sapphire_zone/Actor/Player.cpp +++ b/src/servers/sapphire_zone/Actor/Player.cpp @@ -7,6 +7,7 @@ #include #include #include +#include #include "Session.h" #include "Player.h" @@ -1418,46 +1419,35 @@ void Core::Entity::Player::autoAttack( CharaPtr pTarget ) if( getClass() == ClassJob::Machinist || getClass() == ClassJob::Bard || getClass() == ClassJob::Archer ) { - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); - effectPacket->data().animationTargetId = pTarget->getId(); - effectPacket->data().actionAnimationId = 8; - // effectPacket.data().unknown_2 = variation; - effectPacket->data().numEffects = 1; - //effectPacket->data().unknown_61 = 1; - //effectPacket->data().unknown_62 = 1; - effectPacket->data().actionId = 8; - effectPacket->data().rotation = Math::Util::floatToUInt16Rot( getRot() ); - effectPacket->data().effectTargetId = pTarget->getId(); - //effectPacket->data().effectTarget = pTarget->getId(); - effectPacket->data().effects[0].value = damage; - effectPacket->data().effects[0].effectType = Common::ActionEffectType::Damage; - effectPacket->data().effects[0].hitSeverity = Common::ActionHitSeverityType::NormalDamage; - //effectPacket->data().effects[0].unknown_3 = 7; + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), pTarget->getId(), 8 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( getRot() ) ); - sendToInRangeSet(effectPacket, true); + Server::EffectEntry entry; + entry.value = damage; + entry.effectType = Common::ActionEffectType::Damage; + entry.hitSeverity = Common::ActionHitSeverityType::NormalDamage; + + effectPacket->addEffect( entry ); + + sendToInRangeSet( effectPacket, true ); } else { + auto effectPacket = boost::make_shared< Server::EffectPacket >( getId(), pTarget->getId(), 7 ); + effectPacket->setRotation( Math::Util::floatToUInt16Rot( getRot() ) ); - auto effectPacket = makeZonePacket< Server::FFXIVIpcEffect >( getId() ); - effectPacket->data().animationTargetId = pTarget->getId(); - effectPacket->data().actionAnimationId = 7; - // effectPacket.data().unknown_2 = variation; - effectPacket->data().numEffects = 1; - //effectPacket->data().unknown_61 = 1; - //effectPacket->data().unknown_62 = 1; - effectPacket->data().actionId = 7; - effectPacket->data().rotation = Math::Util::floatToUInt16Rot( getRot() ); - effectPacket->data().effectTargetId = pTarget->getId(); - effectPacket->data().effects[0].value = damage; - effectPacket->data().effects[0].effectType = Common::ActionEffectType::Damage; - effectPacket->data().effects[0].hitSeverity = Common::ActionHitSeverityType::NormalDamage; - //effectPacket->data().effects[0].unknown_3 = 71; + Server::EffectEntry entry; + entry.value = damage; + entry.effectType = Common::ActionEffectType::Damage; + entry.hitSeverity = Common::ActionHitSeverityType::NormalDamage; + + effectPacket->addEffect( entry ); + + sendToInRangeSet( effectPacket, true ); - sendToInRangeSet(effectPacket, true); } - pTarget->takeDamage(damage); + pTarget->takeDamage( damage ); } diff --git a/src/servers/sapphire_zone/Network/PacketWrappers/EffectPacket.h b/src/servers/sapphire_zone/Network/PacketWrappers/EffectPacket.h new file mode 100644 index 00000000..afafdffc --- /dev/null +++ b/src/servers/sapphire_zone/Network/PacketWrappers/EffectPacket.h @@ -0,0 +1,65 @@ +#ifndef SAPPHIRE_EFFECTPACKET_H +#define SAPPHIRE_EFFECTPACKET_H + +#include +#include +#include "Forwards.h" + +namespace Core { +namespace Network { +namespace Packets { +namespace Server { + +class EffectPacket : + public ZoneChannelPacket< FFXIVIpcEffect > +{ +public: + EffectPacket( uint64_t sourceId, uint32_t targetId, uint32_t actionId ) : + ZoneChannelPacket< FFXIVIpcEffect >( sourceId, targetId ) + { + m_data.actionId = actionId; + m_data.actionAnimationId = static_cast< uint16_t >( actionId ); + + m_data.animationTargetId = targetId; + m_data.effectTargetId = targetId; + + m_data.effectDisplayType = Common::ActionEffectDisplayType::ShowActionName; + } + + void addEffect( const Server::EffectEntry& effect ) + { + assert( m_data.effectCount <= 8 ); + + std::memcpy( &m_data.effects[m_data.effectCount++], &effect, sizeof( Server::EffectEntry ) ); + } + + void setAnimationId( const uint16_t animationId ) + { + m_data.actionAnimationId = animationId; + } + + void setEffectFlags( const uint32_t effectFlags ) + { + m_data.effectFlags = effectFlags; + } + + void setRotation( const uint16_t rotation ) + { + m_data.rotation = rotation; + } + + void setTargetActor( const uint32_t targetId ) + { + m_data.animationTargetId = targetId; + m_data.effectTargetId = targetId; + + FFXIVPacketBase::setTargetActor( targetId ); + } +}; + +} +} +} +} + +#endif //SAPPHIRE_EFFECTPACKET_H