aboutsummaryrefslogtreecommitdiff
path: root/src/server/game/Movement/MotionMaster.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/server/game/Movement/MotionMaster.cpp')
-rw-r--r--src/server/game/Movement/MotionMaster.cpp98
1 files changed, 36 insertions, 62 deletions
diff --git a/src/server/game/Movement/MotionMaster.cpp b/src/server/game/Movement/MotionMaster.cpp
index 202663cf1cc..af61fd0a27f 100644
--- a/src/server/game/Movement/MotionMaster.cpp
+++ b/src/server/game/Movement/MotionMaster.cpp
@@ -29,6 +29,7 @@
#include "PathGenerator.h"
#include "Player.h"
#include "ScriptSystem.h"
+#include "Types.h"
#include <boost/container/static_vector.hpp>
#include <algorithm>
#include <iterator>
@@ -858,52 +859,43 @@ void MotionMaster::MoveKnockbackFrom(Position const& origin, float speedXY, floa
Add(movement);
}
-void MotionMaster::MoveJump(Position const& pos, float speedXY, float speedZ, uint32 id /*= EVENT_JUMP*/, MovementFacingTarget const& facing /*= {}*/,
- bool orientationFixed /*= false*/, JumpArrivalCastArgs const* arrivalCast /*= nullptr*/, Movement::SpellEffectExtraData const* spellEffectExtraData /*= nullptr*/,
+void MotionMaster::MoveJump(uint32 id, Position const& pos, std::variant<std::monostate, float, Milliseconds> speedOrTime /*= {}*/,
+ Optional<float> minHeight /*= {}*/, Optional<float> maxHeight /*= {}*/,
+ MovementFacingTarget const& facing /*= {}*/, bool orientationFixed, bool unlimitedSpeed /*= false*/, Optional<float> speedMultiplier /*= {}*/,
+ JumpArrivalCastArgs const* arrivalCast /*= nullptr*/, Movement::SpellEffectExtraData const* spellEffectExtraData /*= nullptr*/,
Optional<Scripting::v2::ActionResultSetter<MovementStopReason>>&& scriptResult /*= {}*/)
{
TC_LOG_DEBUG("movement.motionmaster", "MotionMaster::MoveJump: '{}', jumps to point Id: {} ({})", _owner->GetGUID(), id, pos.ToString());
- if (speedXY < 0.01f)
- {
- if (scriptResult)
- scriptResult->SetResult(MovementStopReason::Interrupted);
- return;
- }
- float moveTimeHalf = speedZ / Movement::gravity;
- float max_height = -Movement::computeFallElevation(moveTimeHalf, false, -speedZ);
+ float dist = _owner->GetExactDist(pos);
- std::function<void(Movement::MoveSplineInit&)> initializer = [=, effect = (spellEffectExtraData ? Optional<Movement::SpellEffectExtraData>(*spellEffectExtraData) : Optional<Movement::SpellEffectExtraData>())](Movement::MoveSplineInit& init)
+ float speedXY = std::visit([owner = _owner, speedMultiplier = speedMultiplier.value_or(1.0f), dist]<typename T>(T speedOrTime) noexcept -> float
{
- init.MoveTo(pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), false);
- init.SetParabolic(max_height, 0);
- init.SetVelocity(speedXY);
- std::visit(Movement::MoveSplineInitFacingVisitor(init), facing);
- init.SetJumpOrientationFixed(orientationFixed);
- if (effect)
- init.SetSpellEffectExtraData(*effect);
- };
+ if constexpr (std::is_same_v<T, std::monostate>)
+ {
+ float baseSpeed = owner->IsControlledByPlayer() ? playerBaseMoveSpeed[MOVE_RUN] : baseMoveSpeed[MOVE_RUN];
+ if (Creature* creature = owner->ToCreature())
+ baseSpeed *= creature->GetCreatureTemplate()->speed_run;
- uint32 arrivalSpellId = 0;
- ObjectGuid arrivalSpellTargetGuid;
- if (arrivalCast)
- {
- arrivalSpellId = arrivalCast->SpellId;
- arrivalSpellTargetGuid = arrivalCast->Target;
- }
+ return baseSpeed * 3.0f * speedMultiplier;
+ }
+ else if constexpr (std::is_same_v<T, float>)
+ {
+ return speedOrTime;
+ }
+ else if constexpr (std::is_same_v<T, Milliseconds>)
+ {
+ return dist / duration_cast<FloatSeconds>(speedOrTime).count();
+ }
+ else
+ {
+ static_assert(Trinity::dependant_false_v<T>, "Unhandled type");
+ }
+ }, speedOrTime);
- GenericMovementGenerator* movement = new GenericMovementGenerator(std::move(initializer), EFFECT_MOTION_TYPE, id,
- { .ArrivalSpellId = arrivalSpellId, .ArrivalSpellTarget = arrivalSpellTargetGuid, .ScriptResult = std::move(scriptResult) });
- movement->Priority = MOTION_PRIORITY_HIGHEST;
- movement->BaseUnitState = UNIT_STATE_JUMPING;
- Add(movement);
-}
+ if (!unlimitedSpeed)
+ speedXY = std::min(speedXY, 50.0f);
-void MotionMaster::MoveJumpWithGravity(Position const& pos, float speedXY, float gravity, uint32 id/* = EVENT_JUMP*/, MovementFacingTarget const& facing/* = {}*/,
- bool orientationFixed /*= false*/, JumpArrivalCastArgs const* arrivalCast /*= nullptr*/, Movement::SpellEffectExtraData const* spellEffectExtraData /*= nullptr*/,
- Optional<Scripting::v2::ActionResultSetter<MovementStopReason>>&& scriptResult /*= {}*/)
-{
- TC_LOG_DEBUG("movement.motionmaster", "MotionMaster::MoveJumpWithGravity: '{}', jumps to point Id: {} ({})", _owner->GetGUID(), id, pos.ToString());
if (speedXY < 0.01f)
{
if (scriptResult)
@@ -911,15 +903,19 @@ void MotionMaster::MoveJumpWithGravity(Position const& pos, float speedXY, float
return;
}
+ float duration = dist / speedXY;
+ float durationSqr = duration * duration;
+ float height = std::clamp(Movement::gravity * durationSqr / 8, minHeight.value_or(0.5f), maxHeight.value_or(1000.0f));
+
std::function<void(Movement::MoveSplineInit&)> initializer = [=, effect = (spellEffectExtraData ? Optional<Movement::SpellEffectExtraData>(*spellEffectExtraData) : Optional<Movement::SpellEffectExtraData>())](Movement::MoveSplineInit& init)
{
init.MoveTo(pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), false);
- init.SetParabolicVerticalAcceleration(gravity, 0);
- init.SetUncompressed();
+ init.SetParabolic(height, 0);
init.SetVelocity(speedXY);
- init.SetUnlimitedSpeed();
std::visit(Movement::MoveSplineInitFacingVisitor(init), facing);
init.SetJumpOrientationFixed(orientationFixed);
+ if (unlimitedSpeed)
+ init.SetUnlimitedSpeed();
if (effect)
init.SetSpellEffectExtraData(*effect);
};
@@ -936,7 +932,6 @@ void MotionMaster::MoveJumpWithGravity(Position const& pos, float speedXY, float
{ .ArrivalSpellId = arrivalSpellId, .ArrivalSpellTarget = arrivalSpellTargetGuid, .ScriptResult = std::move(scriptResult) });
movement->Priority = MOTION_PRIORITY_HIGHEST;
movement->BaseUnitState = UNIT_STATE_JUMPING;
- movement->AddFlag(MOVEMENTGENERATOR_FLAG_PERSIST_ON_DEATH);
Add(movement);
}
@@ -1201,27 +1196,6 @@ void MotionMaster::LaunchMoveSpline(std::function<void(Movement::MoveSplineInit&
Add(movement);
}
-void MotionMaster::CalculateJumpSpeeds(float dist, UnitMoveType moveType, float speedMultiplier, float minHeight, float maxHeight, float& speedXY, float& speedZ) const
-{
- float baseSpeed = _owner->IsControlledByPlayer() ? playerBaseMoveSpeed[moveType] : baseMoveSpeed[moveType];
- if (Creature* creature = _owner->ToCreature())
- baseSpeed *= creature->GetCreatureTemplate()->speed_run;
-
- speedXY = std::min(baseSpeed * 3.0f * speedMultiplier, std::max(28.0f, _owner->GetSpeed(moveType) * 4.0f));
-
- float duration = dist / speedXY;
- float durationSqr = duration * duration;
- float height;
- if (durationSqr < minHeight * 8 / Movement::gravity)
- height = minHeight;
- else if (durationSqr > maxHeight * 8 / Movement::gravity)
- height = maxHeight;
- else
- height = Movement::gravity * durationSqr / 8;
-
- speedZ = std::sqrt(2 * Movement::gravity * height);
-}
-
/******************** Private methods ********************/
void MotionMaster::ResolveDelayedActions()