Spawn aircraft landed and occupying land or at cruise altitude

This commit is contained in:
Gustas
2024-06-03 19:14:25 +03:00
committed by Matthias Mailänder
parent 734afd8bcf
commit 7b01204eed
3 changed files with 81 additions and 21 deletions

View File

@@ -286,6 +286,7 @@ namespace OpenRA.Mods.Common.Traits
public bool RequireForceMove;
readonly int creationActivityDelay;
readonly bool creationByMap;
readonly CPos[] creationRallyPoint;
bool notify = true;
@@ -312,12 +313,13 @@ namespace OpenRA.Mods.Common.Traits
self = init.Self;
var locationInit = init.GetOrDefault<LocationInit>();
if (locationInit != null)
SetPosition(self, locationInit.Value);
var centerPositionInit = init.GetOrDefault<CenterPositionInit>();
if (centerPositionInit != null)
SetPosition(self, centerPositionInit.Value);
if (locationInit != null || centerPositionInit != null)
{
var pos = centerPositionInit?.Value ?? self.World.Map.CenterOfCell(locationInit.Value);
creationByMap = init.Contains<SpawnedByMapInit>();
SetPosition(self, pos);
}
Facing = init.GetValue<FacingInit, WAngle>(Info.InitialFacing);
creationActivityDelay = init.GetValue<CreationActivityDelayInit, int>(0);
@@ -1220,8 +1222,8 @@ namespace OpenRA.Mods.Common.Traits
Activity ICreationActivity.GetCreationActivity()
{
if (creationRallyPoint != null || creationActivityDelay > 0)
return new AssociateWithAirfieldActivity(self, creationActivityDelay, creationRallyPoint);
if (creationRallyPoint != null || creationActivityDelay > 0 || creationByMap)
return new AssociateWithAirfieldActivity(this, creationActivityDelay, creationRallyPoint, creationByMap);
return null;
}
@@ -1231,28 +1233,70 @@ namespace OpenRA.Mods.Common.Traits
readonly Aircraft aircraft;
readonly int delay;
readonly CPos[] rallyPoint;
readonly bool creationByMap;
public AssociateWithAirfieldActivity(Actor self, int delay, CPos[] rallyPoint)
public AssociateWithAirfieldActivity(Aircraft self, int delay, CPos[] rallyPoint, bool creationByMap)
{
aircraft = self.Trait<Aircraft>();
aircraft = self;
this.delay = delay;
this.rallyPoint = rallyPoint;
this.creationByMap = creationByMap;
}
protected override void OnFirstRun(Actor self)
{
var cpos = self.Location;
var pos = self.CenterPosition;
bool TryDock()
{
var host = aircraft.GetActorBelow();
if (host != null)
{
// Center the actor on the resupplier.
var exit = host.NearestExitOrDefault(pos);
pos = host.CenterPosition;
pos = new WPos(pos.X, pos.Y, pos.Z - self.World.Map.DistanceAboveTerrain(pos).Length);
if (exit != null)
{
pos += exit.Info.SpawnOffset;
if (exit.Info.Facing != null)
aircraft.Facing = exit.Info.Facing.Value;
}
aircraft.AddInfluence(cpos);
aircraft.SetPosition(self, pos);
aircraft.MakeReservation(host);
// Freshly created aircraft shouldn't block the exit, so we allow them to yield their reservation.
aircraft.AllowYieldingReservation();
return true;
}
return false;
}
if (creationByMap)
{
if (TryDock())
return;
pos = new WPos(pos.X, pos.Y, pos.Z - self.World.Map.DistanceAboveTerrain(pos).Length);
if (!aircraft.Info.TakeOffOnCreation && aircraft.CanLand(cpos))
{
aircraft.AddInfluence(cpos);
aircraft.SetPosition(self, pos);
}
else
aircraft.SetPosition(self, new WPos(pos.X, pos.Y, pos.Z + aircraft.Info.CruiseAltitude.Length));
}
else
{
TryDock();
if (delay > 0)
QueueChild(new Wait(delay));
}
}
public override bool Tick(Actor self)
{
@@ -1260,16 +1304,29 @@ namespace OpenRA.Mods.Common.Traits
return true;
if (rallyPoint != null && rallyPoint.Length > 0)
{
foreach (var cell in rallyPoint)
QueueChild(new AttackMoveActivity(self, () => aircraft.MoveTo(cell, 1, evaluateNearestMovableCell: true, targetLineColor: Color.OrangeRed)));
}
else if (self.World.Map.DistanceAboveTerrain(aircraft.CenterPosition).Length <= aircraft.LandAltitude.Length)
QueueChild(new TakeOff(self));
if (!creationByMap)
aircraft.UnReserve();
return true;
}
public override IEnumerable<Target> GetTargets(Actor self)
{
if (ChildActivity != null)
return ChildActivity.GetTargets(self);
return Target.None;
}
public override IEnumerable<TargetLineNode> TargetLineNodes(Actor self)
{
if (ChildActivity != null)
foreach (var n in ChildActivity.TargetLineNodes(self))
yield return n;
}
}
public class AircraftMoveOrderTargeter : IOrderTargeter

View File

@@ -94,6 +94,7 @@ namespace OpenRA.Mods.Common.Traits
new OwnerInit(p),
new SkipMakeAnimsInit(),
new FacingInit(facing),
new SpawnedByMapInit(),
});
}
@@ -123,6 +124,7 @@ namespace OpenRA.Mods.Common.Traits
new LocationInit(validCell),
new SubCellInit(subCell),
new FacingInit(facing),
new SpawnedByMapInit(),
});
}
}

View File

@@ -18,6 +18,7 @@ carryall.reinforce:
LandableTerrainTypes: Sand, Rock, Transition, Spice, SpiceSand, Dune, Concrete
Repulsable: False
AirborneCondition: airborne
CanForceLand: false
CanSlide: True
VTOL: true
IdleTurnSpeed: 4