Core/Movement: FormationMovementGenerator
Port From (https://github.com/TrinityCore/TrinityCore/commit/84df2c57a385df4503fc1f8ff5dfdf445ea2e31f)
This commit is contained in:
@@ -27,25 +27,26 @@ namespace Framework.Constants
|
||||
|
||||
public enum MovementGeneratorType
|
||||
{
|
||||
Idle = 0, // IdleMovement
|
||||
Random = 1, // RandomMovement
|
||||
Waypoint = 2, // WaypointMovement
|
||||
Idle = 0, // IdleMovement
|
||||
Random = 1, // RandomMovement
|
||||
Waypoint = 2, // WaypointMovement
|
||||
|
||||
MaxDB = 3, // *** this and below motion types can't be set in DB.
|
||||
Confused = 4, // ConfusedMovementGenerator
|
||||
Chase = 5, // TargetedMovementGenerator
|
||||
Home = 6, // HomeMovementGenerator
|
||||
Flight = 7, // WaypointMovementGenerator
|
||||
Point = 8, // PointMovementGenerator
|
||||
Fleeing = 9, // FleeingMovementGenerator
|
||||
Distract = 10, // IdleMovementGenerator
|
||||
Assistance = 11, // PointMovementGenerator
|
||||
AssistanceDistract = 12, // IdleMovementGenerator
|
||||
TimedFleeing = 13, // FleeingMovementGenerator
|
||||
MaxDB = 3, // *** this and below motion types can't be set in DB.
|
||||
Confused = 4, // ConfusedMovementGenerator
|
||||
Chase = 5, // TargetedMovementGenerator
|
||||
Home = 6, // HomeMovementGenerator
|
||||
Flight = 7, // WaypointMovementGenerator
|
||||
Point = 8, // PointMovementGenerator
|
||||
Fleeing = 9, // FleeingMovementGenerator
|
||||
Distract = 10, // IdleMovementGenerator
|
||||
Assistance = 11, // PointMovementGenerator
|
||||
AssistanceDistract = 12, // IdleMovementGenerator
|
||||
TimedFleeing = 13, // FleeingMovementGenerator
|
||||
Follow = 14,
|
||||
Rotate = 15,
|
||||
Effect = 16,
|
||||
SplineChain = 17,
|
||||
SplineChain = 17, // SplineChainMovementGenerator
|
||||
Formation = 18, // FormationMovementGenerator
|
||||
Max
|
||||
}
|
||||
|
||||
|
||||
@@ -222,13 +222,16 @@ namespace Game.Entities
|
||||
m_Formed = !dismiss;
|
||||
}
|
||||
|
||||
public void LeaderMoveTo(float x, float y, float z)
|
||||
public void LeaderMoveTo(Position destination, uint id = 0, uint moveType = 0, bool orientation = false)
|
||||
{
|
||||
//! To do: This should probably get its own movement generator or use WaypointMovementGenerator.
|
||||
//! If the leader's path is known, member's path can be plotted as well using formation offsets.
|
||||
if (!m_leader)
|
||||
return;
|
||||
|
||||
float x = destination.GetPositionX();
|
||||
float y = destination.GetPositionY();
|
||||
float z = destination.GetPositionZ();
|
||||
float pathangle = (float)Math.Atan2(m_leader.GetPositionY() - y, m_leader.GetPositionX() - x);
|
||||
|
||||
foreach (var pair in m_members)
|
||||
@@ -254,12 +257,9 @@ namespace Game.Entities
|
||||
if (!member.IsFlying())
|
||||
member.UpdateGroundPositionZ(dx, dy, ref dz);
|
||||
|
||||
if (member.IsWithinDist(m_leader, dist + 5.0f))
|
||||
member.SetUnitMovementFlags(m_leader.GetUnitMovementFlags());
|
||||
else
|
||||
member.SetWalk(false);
|
||||
Position point = new Position(dx, dy, dz, destination.GetOrientation());
|
||||
|
||||
member.GetMotionMaster().MovePoint(0, dx, dy, dz);
|
||||
member.GetMotionMaster().MoveFormation(id, point, moveType, !member.IsWithinDist(m_leader, dist + 5.0f), orientation);
|
||||
member.SetHomePosition(dx, dy, dz, pathangle);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,160 @@
|
||||
/*
|
||||
* Copyright (C) 2012-2020 CypherCore <http://github.com/CypherCore>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
using Framework.Constants;
|
||||
using Game.Entities;
|
||||
|
||||
namespace Game.Movement
|
||||
{
|
||||
public class FormationMovementGenerator : MovementGeneratorMedium<Creature>
|
||||
{
|
||||
public FormationMovementGenerator(uint id, Position destination, uint moveType, bool run, bool orientation)
|
||||
{
|
||||
_movementId = id;
|
||||
_destination = destination;
|
||||
_moveType = moveType;
|
||||
_run = run;
|
||||
_orientation = orientation;
|
||||
}
|
||||
|
||||
public override void DoInitialize(Creature owner)
|
||||
{
|
||||
owner.AddUnitState(UnitState.Roaming);
|
||||
|
||||
if (owner.HasUnitState(UnitState.NotMove) || owner.IsMovementPreventedByCasting())
|
||||
{
|
||||
_interrupt = true;
|
||||
owner.StopMoving();
|
||||
return;
|
||||
}
|
||||
|
||||
owner.AddUnitState(UnitState.RoamingMove);
|
||||
|
||||
MoveSplineInit init = new MoveSplineInit(owner);
|
||||
init.MoveTo(_destination.GetPositionX(), _destination.GetPositionY(), _destination.GetPositionZ());
|
||||
if (_orientation)
|
||||
init.SetFacing(_destination.GetOrientation());
|
||||
|
||||
switch (_moveType)
|
||||
{
|
||||
case 2: // WAYPOINT_MOVE_TYPE_LAND
|
||||
init.SetAnimation(AnimType.ToGround);
|
||||
break;
|
||||
case 3: // WAYPOINT_MOVE_TYPE_TAKEOFF
|
||||
init.SetAnimation(AnimType.ToFly);
|
||||
break;
|
||||
case 1: // WAYPOINT_MOVE_TYPE_RUN
|
||||
init.SetWalk(false);
|
||||
break;
|
||||
case 0: // WAYPOINT_MOVE_TYPE_WALK
|
||||
init.SetWalk(true);
|
||||
break;
|
||||
}
|
||||
|
||||
if (_run)
|
||||
init.SetWalk(false);
|
||||
|
||||
init.Launch();
|
||||
}
|
||||
|
||||
public override void DoReset(Creature owner)
|
||||
{
|
||||
owner.StopMoving();
|
||||
DoInitialize(owner);
|
||||
}
|
||||
|
||||
public override bool DoUpdate(Creature owner, uint diff)
|
||||
{
|
||||
if (!owner)
|
||||
return false;
|
||||
|
||||
if (owner.HasUnitState(UnitState.NotMove) || owner.IsMovementPreventedByCasting())
|
||||
{
|
||||
_interrupt = true;
|
||||
owner.StopMoving();
|
||||
return true;
|
||||
}
|
||||
|
||||
if ((_interrupt && owner.MoveSpline.Finalized()) || (_recalculateSpeed && !owner.MoveSpline.Finalized()))
|
||||
{
|
||||
_recalculateSpeed = false;
|
||||
_interrupt = false;
|
||||
|
||||
owner.AddUnitState(UnitState.RoamingMove);
|
||||
|
||||
MoveSplineInit init = new MoveSplineInit(owner);
|
||||
init.MoveTo(_destination.GetPositionX(), _destination.GetPositionY(), _destination.GetPositionZ());
|
||||
if (_orientation)
|
||||
init.SetFacing(_destination.GetOrientation());
|
||||
|
||||
switch (_moveType)
|
||||
{
|
||||
case 2: // WAYPOINT_MOVE_TYPE_LAND
|
||||
init.SetAnimation(AnimType.ToGround);
|
||||
break;
|
||||
case 3: // WAYPOINT_MOVE_TYPE_TAKEOFF
|
||||
init.SetAnimation(AnimType.ToFly);
|
||||
break;
|
||||
case 1: // WAYPOINT_MOVE_TYPE_RUN
|
||||
init.SetWalk(false);
|
||||
break;
|
||||
case 0: // WAYPOINT_MOVE_TYPE_WALK
|
||||
init.SetWalk(true);
|
||||
break;
|
||||
}
|
||||
|
||||
if (_run)
|
||||
init.SetWalk(false);
|
||||
init.Launch();
|
||||
}
|
||||
|
||||
return !owner.MoveSpline.Finalized();
|
||||
}
|
||||
|
||||
public override void DoFinalize(Creature owner)
|
||||
{
|
||||
owner.ClearUnitState(UnitState.Roaming | UnitState.RoamingMove);
|
||||
|
||||
if (owner.MoveSpline.Finalized())
|
||||
MovementInform(owner);
|
||||
}
|
||||
|
||||
public override void UnitSpeedChanged()
|
||||
{
|
||||
_recalculateSpeed = true;
|
||||
}
|
||||
|
||||
public override MovementGeneratorType GetMovementGeneratorType()
|
||||
{
|
||||
return MovementGeneratorType.Formation;
|
||||
}
|
||||
|
||||
void MovementInform(Creature owner)
|
||||
{
|
||||
if (owner.GetAI() != null)
|
||||
owner.GetAI().MovementInform(MovementGeneratorType.Formation, _movementId);
|
||||
}
|
||||
|
||||
uint _movementId;
|
||||
Position _destination;
|
||||
uint _moveType;
|
||||
bool _run;
|
||||
bool _orientation;
|
||||
bool _recalculateSpeed;
|
||||
bool _interrupt;
|
||||
}
|
||||
}
|
||||
@@ -69,7 +69,7 @@ namespace Game.Movement
|
||||
Creature creature = owner.ToCreature();
|
||||
if (creature != null)
|
||||
if (creature.GetFormation() != null && creature.GetFormation().GetLeader() == creature)
|
||||
creature.GetFormation().LeaderMoveTo(_destination.GetPositionX(), _destination.GetPositionY(), _destination.GetPositionZ());
|
||||
creature.GetFormation().LeaderMoveTo(_destination, _movementId);
|
||||
}
|
||||
|
||||
public override void DoReset(T owner)
|
||||
@@ -110,7 +110,7 @@ namespace Game.Movement
|
||||
Creature creature = owner.ToCreature();
|
||||
if (creature != null)
|
||||
if (creature.GetFormation() != null && creature.GetFormation().GetLeader() == creature)
|
||||
creature.GetFormation().LeaderMoveTo(_destination.GetPositionX(), _destination.GetPositionY(), _destination.GetPositionZ());
|
||||
creature.GetFormation().LeaderMoveTo(_destination, _movementId);
|
||||
}
|
||||
|
||||
return !owner.MoveSpline.Finalized();
|
||||
|
||||
@@ -118,7 +118,7 @@ namespace Game.Movement
|
||||
|
||||
// Call for creature group update
|
||||
if (owner.GetFormation() != null && owner.GetFormation().GetLeader() == owner)
|
||||
owner.GetFormation().LeaderMoveTo(position.GetPositionX(), position.GetPositionY(), position.GetPositionZ());
|
||||
owner.GetFormation().LeaderMoveTo(position);
|
||||
}
|
||||
|
||||
public override MovementGeneratorType GetMovementGeneratorType()
|
||||
|
||||
@@ -187,7 +187,7 @@ namespace Game.Movement
|
||||
|
||||
creature.AddUnitState(UnitState.RoamingMove);
|
||||
|
||||
Position formationDest = new Position(node.x, node.y, node.z, 0.0f);
|
||||
Position formationDest = new Position(node.x, node.y, node.z, (node.orientation != 0 && node.delay != 0) ? node.orientation : 0.0f);
|
||||
MoveSplineInit init = new MoveSplineInit(creature);
|
||||
|
||||
//! If creature is on transport, we assume waypoints set in DB are already transport offsets
|
||||
@@ -196,7 +196,11 @@ namespace Game.Movement
|
||||
init.DisableTransportPathTransformations();
|
||||
ITransport trans = creature.GetDirectTransport();
|
||||
if (trans != null)
|
||||
trans.CalculatePassengerPosition(ref formationDest.posX, ref formationDest.posY, ref formationDest.posZ, ref formationDest.Orientation);
|
||||
{
|
||||
float orientation = formationDest.GetOrientation();
|
||||
trans.CalculatePassengerPosition(ref formationDest.posX, ref formationDest.posY, ref formationDest.posZ, ref orientation);
|
||||
formationDest.SetOrientation(orientation);
|
||||
}
|
||||
}
|
||||
|
||||
//! Do not use formationDest here, MoveTo requires transport offsets due to DisableTransportPathTransformations() call
|
||||
@@ -227,10 +231,7 @@ namespace Game.Movement
|
||||
|
||||
//Call for creature group update
|
||||
if (creature.GetFormation() != null && creature.GetFormation().GetLeader() == creature)
|
||||
{
|
||||
creature.SetWalk(node.moveType != WaypointMoveType.Run);
|
||||
creature.GetFormation().LeaderMoveTo(formationDest.posX, formationDest.posY, formationDest.posZ);
|
||||
}
|
||||
creature.GetFormation().LeaderMoveTo(formationDest, node.id, (uint)node.moveType, (node.orientation != 0 && node.delay != 0) ? true : false);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -607,6 +607,12 @@ namespace Game.Movement
|
||||
StartMovement(new RotateMovementGenerator(time, direction), MovementSlot.Active);
|
||||
}
|
||||
|
||||
public void MoveFormation(uint id, Position destination, uint moveType, bool forceRun = false, bool forceOrientation = false)
|
||||
{
|
||||
if (_owner.GetTypeId() == TypeId.Unit)
|
||||
StartMovement(new FormationMovementGenerator(id, destination, moveType, forceRun, forceOrientation), MovementSlot.Active);
|
||||
}
|
||||
|
||||
void Pop()
|
||||
{
|
||||
if (Empty())
|
||||
|
||||
Reference in New Issue
Block a user