diff --git a/src/world/Actor/Chara.cpp b/src/world/Actor/Chara.cpp index d9df2d97..ebe2581f 100644 --- a/src/world/Actor/Chara.cpp +++ b/src/world/Actor/Chara.cpp @@ -15,6 +15,7 @@ #include "Network/PacketWrappers/ActorControlTargetPacket.h" #include "Network/PacketWrappers/UpdateHpMpTpPacket.h" #include "Network/PacketWrappers/EffectPacket1.h" +#include "Network/PacketWrappers/HudParamPacket.h" #include "StatusEffect/StatusEffect.h" #include "Action/Action.h" @@ -616,7 +617,10 @@ void Sapphire::Entity::Chara::removeStatusEffect( uint8_t effectSlotId ) m_statusEffectMap.erase( effectSlotId ); - sendStatusEffectUpdate(); + if( isPlayer() ) + server().queueForPlayers( getInRangePlayerIds( isPlayer() ), makeHudParam( *getAsPlayer() ) ); + else if( isBattleNpc() ) + server().queueForPlayers( getInRangePlayerIds( isPlayer() ), makeHudParam( *getAsBNpc() ) ); } std::map< uint8_t, Sapphire::StatusEffect::StatusEffectPtr > Sapphire::Entity::Chara::getStatusEffectMap() const diff --git a/src/world/Network/PacketWrappers/HudParamPacket.h b/src/world/Network/PacketWrappers/HudParamPacket.h index 98e7d523..664023dd 100644 --- a/src/world/Network/PacketWrappers/HudParamPacket.h +++ b/src/world/Network/PacketWrappers/HudParamPacket.h @@ -3,6 +3,8 @@ #include #include #include +#include +#include #include "Forwards.h" namespace Sapphire::Network::Packets::WorldPackets::Server @@ -19,6 +21,11 @@ namespace Sapphire::Network::Packets::WorldPackets::Server initialize( player ); }; + HudParamPacket( Entity::BNpc& bnpc ) : ZoneChannelPacket< FFXIVIpcHudParam >( bnpc.getId(), bnpc.getId() ) + { + initialize( bnpc ); + }; + private: void initialize( Entity::Player& player ) { @@ -32,19 +39,58 @@ namespace Sapphire::Network::Packets::WorldPackets::Server m_data.HpMax = player.getMaxHp(); m_data.MpMax = player.getMaxMp(); + for( int i = 0; i < 30; ++i ) + m_data.effect[ i ] = { 0, 0, 0.0f, 0 }; + auto statusMap = player.getStatusEffectMap(); int i = 0; for( const auto& [ key, val ] : statusMap ) { + auto timeLeft = static_cast< int32_t >( val->getDuration() - ( Common::Util::getTimeMs() - val->getStartTimeMs() ) ); m_data.effect[ i ].Id = val->getId(); m_data.effect[ i ].Source = val->getSrcActorId(); m_data.effect[ i ].SystemParam = val->getParam(); - m_data.effect[ i ].Time = ( val->getDuration() - ( Common::Util::getTimeMs() - val->getStartTimeMs() ) ) / 1000.f; + if( timeLeft <= 0 ) + m_data.effect[ i ].Time = 0.f; + else + m_data.effect[ i ].Time = timeLeft / 1000.f; i++; } - }; + } + void initialize( Entity::BNpc& bnpc ) + { + m_data.ClassJob = static_cast< uint8_t >( bnpc.getClass() ); + m_data.Lv = bnpc.getLevel(); + m_data.OrgLv = bnpc.getLevel(); + m_data.LvSync = 0; + m_data.Hp = bnpc.getHp(); + m_data.Mp = bnpc.getMp(); + m_data.Tp = bnpc.getTp(); + m_data.HpMax = bnpc.getMaxHp(); + m_data.MpMax = bnpc.getMaxMp(); + + for( int i = 0; i < 30; ++i ) + m_data.effect[ i ] = { 0, 0, 0.0f, 0 }; + + auto statusMap = bnpc.getStatusEffectMap(); + + int i = 0; + for( const auto& [ key, val ] : statusMap ) + { + auto timeLeft = static_cast< int32_t >( val->getDuration() - ( Common::Util::getTimeMs() - val->getStartTimeMs() ) ); + m_data.effect[ i ].Id = val->getId(); + m_data.effect[ i ].Source = val->getSrcActorId(); + m_data.effect[ i ].SystemParam = val->getParam(); + if( timeLeft <= 0 ) + m_data.effect[ i ].Time = 0.f; + else + m_data.effect[ i ].Time = timeLeft / 1000.f; + + i++; + } + } }; template< typename... Args > std::shared_ptr< HudParamPacket > makeHudParam( Args... args )