diff --git a/apps/openmw/mwmechanics/actors.cpp b/apps/openmw/mwmechanics/actors.cpp index 7a2730e02..063b15e99 100644 --- a/apps/openmw/mwmechanics/actors.cpp +++ b/apps/openmw/mwmechanics/actors.cpp @@ -1413,7 +1413,12 @@ namespace MWMechanics MechanicsHelper::resetAttack(localAttack); localAttack->type = MechanicsHelper::isUsingRangedWeapon(player) ? mwmp::Attack::RANGED : mwmp::Attack::MELEE; localAttack->pressed = state; - localAttack->shouldSend = true; + + // Prepare this attack for sending as long as it's not a ranged attack that's being released, + // because we need to get the final attackStrength for that from WeaponAnimation to have the + // correct projectile speed + if (localAttack->type == mwmp::Attack::MELEE || state) + localAttack->shouldSend = true; } } } diff --git a/apps/openmw/mwrender/weaponanimation.cpp b/apps/openmw/mwrender/weaponanimation.cpp index 0b3d000f3..f3750389b 100644 --- a/apps/openmw/mwrender/weaponanimation.cpp +++ b/apps/openmw/mwrender/weaponanimation.cpp @@ -5,6 +5,16 @@ #include #include +/* + Start of tes3mp addition + + Include additional headers for multiplayer purposes +*/ +#include "../mwmp/MechanicsHelper.hpp" +/* + End of tes3mp addition +*/ + #include "../mwbase/world.hpp" #include "../mwbase/environment.hpp" #include "../mwbase/soundmanager.hpp" @@ -92,6 +102,33 @@ void WeaponAnimation::attachArrow(MWWorld::Ptr actor) void WeaponAnimation::releaseArrow(MWWorld::Ptr actor, float attackStrength) { + /* + Start of tes3mp addition + + If this is an attack by a LocalPlayer or LocalActor, record its attackStrength and + prepare an attack packet for sending + + If it's an attack by a DedicatedPlayer or DedicatedActor, apply the attackStrength + from their latest attack packet + */ + mwmp::Attack *localAttack = MechanicsHelper::getLocalAttack(actor); + + if (localAttack) + { + localAttack->attackStrength = attackStrength; + localAttack->shouldSend = true; + } + else + { + mwmp::Attack *dedicatedAttack = MechanicsHelper::getDedicatedAttack(actor); + + if (dedicatedAttack) + attackStrength = dedicatedAttack->attackStrength; + } + /* + End of tes3mp addition + */ + MWWorld::InventoryStore& inv = actor.getClass().getInventoryStore(actor); MWWorld::ContainerStoreIterator weapon = inv.getSlot(MWWorld::InventoryStore::Slot_CarriedRight); if (weapon == inv.end()) diff --git a/components/openmw-mp/Base/BaseStructs.hpp b/components/openmw-mp/Base/BaseStructs.hpp index d877d54e5..bbbdd51d1 100644 --- a/components/openmw-mp/Base/BaseStructs.hpp +++ b/components/openmw-mp/Base/BaseStructs.hpp @@ -81,6 +81,7 @@ namespace mwmp ESM::Position hitPosition; float damage; + float attackStrength; bool success; bool block; diff --git a/components/openmw-mp/Packets/Actor/PacketActorAttack.cpp b/components/openmw-mp/Packets/Actor/PacketActorAttack.cpp index ffb054cd1..d15ecfcbe 100644 --- a/components/openmw-mp/Packets/Actor/PacketActorAttack.cpp +++ b/components/openmw-mp/Packets/Actor/PacketActorAttack.cpp @@ -43,9 +43,13 @@ void PacketActorAttack::Actor(BaseActor &actor, bool send) RW(actor.attack.damage, send); RW(actor.attack.block, send); RW(actor.attack.knockdown, send); - RW(actor.attack.applyWeaponEnchantment, send); - RW(actor.attack.applyProjectileEnchantment, send); + + if (actor.attack.type == mwmp::Attack::RANGED) + { + RW(actor.attack.applyProjectileEnchantment, send); + RW(actor.attack.attackStrength, send); + } if (actor.attack.success || actor.attack.applyWeaponEnchantment || actor.attack.applyProjectileEnchantment) { diff --git a/components/openmw-mp/Packets/Player/PacketPlayerAttack.cpp b/components/openmw-mp/Packets/Player/PacketPlayerAttack.cpp index b28e5c0ff..70b1bd5a3 100644 --- a/components/openmw-mp/Packets/Player/PacketPlayerAttack.cpp +++ b/components/openmw-mp/Packets/Player/PacketPlayerAttack.cpp @@ -44,9 +44,13 @@ void PacketPlayerAttack::Packet(RakNet::BitStream *bs, bool send) RW(player->attack.damage, send); RW(player->attack.block, send); RW(player->attack.knockdown, send); - RW(player->attack.applyWeaponEnchantment, send); - RW(player->attack.applyProjectileEnchantment, send); + + if (player->attack.type == mwmp::Attack::RANGED) + { + RW(player->attack.applyProjectileEnchantment, send); + RW(player->attack.attackStrength, send); + } if (player->attack.success || player->attack.applyWeaponEnchantment || player->attack.applyProjectileEnchantment) {