cache AttackGarrisoned fire ports using IRulesetLoaded

This commit is contained in:
atlimit8
2015-09-26 10:41:53 -05:00
parent 079cff0a7a
commit dc54841bad
2 changed files with 35 additions and 34 deletions

View File

@@ -25,7 +25,7 @@ namespace OpenRA.Mods.Common.Traits
} }
[Desc("Cargo can fire their weapons out of fire ports.")] [Desc("Cargo can fire their weapons out of fire ports.")]
public class AttackGarrisonedInfo : AttackFollowInfo, Requires<CargoInfo> public class AttackGarrisonedInfo : AttackFollowInfo, IRulesetLoaded, Requires<CargoInfo>
{ {
[FieldLoader.Require] [FieldLoader.Require]
[Desc("Fire port offsets in local coordinates.")] [Desc("Fire port offsets in local coordinates.")]
@@ -39,16 +39,39 @@ namespace OpenRA.Mods.Common.Traits
[Desc("Fire port yaw cone angle.")] [Desc("Fire port yaw cone angle.")]
public readonly WAngle[] PortCones = null; public readonly WAngle[] PortCones = null;
public FirePort[] Ports { get; private set; }
[PaletteReference] public readonly string MuzzlePalette = "effect"; [PaletteReference] public readonly string MuzzlePalette = "effect";
public override object Create(ActorInitializer init) { return new AttackGarrisoned(init.Self, this); } public override object Create(ActorInitializer init) { return new AttackGarrisoned(init.Self, this); }
public void RulesetLoaded(Ruleset rules, ActorInfo ai)
{
if (PortOffsets.Length == 0)
throw new YamlException("PortOffsets must have at least one entry.");
if (PortYaws.Length != PortOffsets.Length)
throw new YamlException("PortYaws must define an angle for each port.");
if (PortCones.Length != PortOffsets.Length)
throw new YamlException("PortCones must define an angle for each port.");
Ports = new FirePort[PortOffsets.Length];
for (var i = 0; i < PortOffsets.Length; i++)
{
Ports[i] = new FirePort
{
Offset = PortOffsets[i],
Yaw = PortYaws[i],
Cone = PortCones[i],
};
}
}
} }
public class AttackGarrisoned : AttackFollow, INotifyPassengerEntered, INotifyPassengerExited, IRender public class AttackGarrisoned : AttackFollow, INotifyPassengerEntered, INotifyPassengerExited, IRender
{ {
public readonly FirePort[] Ports; public readonly new AttackGarrisonedInfo Info;
AttackGarrisonedInfo info;
Lazy<BodyOrientation> coords; Lazy<BodyOrientation> coords;
List<Armament> armaments; List<Armament> armaments;
List<AnimationWithOffset> muzzles; List<AnimationWithOffset> muzzles;
@@ -59,7 +82,7 @@ namespace OpenRA.Mods.Common.Traits
public AttackGarrisoned(Actor self, AttackGarrisonedInfo info) public AttackGarrisoned(Actor self, AttackGarrisonedInfo info)
: base(self, info) : base(self, info)
{ {
this.info = info; this.Info = info;
coords = Exts.Lazy(() => self.Trait<BodyOrientation>()); coords = Exts.Lazy(() => self.Trait<BodyOrientation>());
armaments = new List<Armament>(); armaments = new List<Armament>();
muzzles = new List<AnimationWithOffset>(); muzzles = new List<AnimationWithOffset>();
@@ -68,28 +91,6 @@ namespace OpenRA.Mods.Common.Traits
paxRender = new Dictionary<Actor, RenderSprites>(); paxRender = new Dictionary<Actor, RenderSprites>();
getArmaments = () => armaments; getArmaments = () => armaments;
if (info.PortOffsets.Length == 0)
throw new InvalidOperationException("PortOffsets must have at least one entry.");
if (info.PortYaws.Length != info.PortOffsets.Length)
throw new InvalidOperationException("PortYaws must define an angle for each port.");
if (info.PortCones.Length != info.PortOffsets.Length)
throw new InvalidOperationException("PortCones must define an angle for each port.");
var p = new List<FirePort>();
for (var i = 0; i < info.PortOffsets.Length; i++)
{
p.Add(new FirePort
{
Offset = info.PortOffsets[i],
Yaw = info.PortYaws[i],
Cone = info.PortCones[i],
});
}
Ports = p.ToArray();
} }
public void PassengerEntered(Actor self, Actor passenger) public void PassengerEntered(Actor self, Actor passenger)
@@ -99,7 +100,7 @@ namespace OpenRA.Mods.Common.Traits
paxRender.Add(passenger, passenger.Trait<RenderSprites>()); paxRender.Add(passenger, passenger.Trait<RenderSprites>());
armaments.AddRange( armaments.AddRange(
passenger.TraitsImplementing<Armament>() passenger.TraitsImplementing<Armament>()
.Where(a => info.Armaments.Contains(a.Info.Name))); .Where(a => Info.Armaments.Contains(a.Info.Name)));
} }
public void PassengerExited(Actor self, Actor passenger) public void PassengerExited(Actor self, Actor passenger)
@@ -114,14 +115,14 @@ namespace OpenRA.Mods.Common.Traits
{ {
// Pick a random port that faces the target // Pick a random port that faces the target
var bodyYaw = facing.Value != null ? WAngle.FromFacing(facing.Value.Facing) : WAngle.Zero; var bodyYaw = facing.Value != null ? WAngle.FromFacing(facing.Value.Facing) : WAngle.Zero;
var indices = Enumerable.Range(0, Ports.Length).Shuffle(self.World.SharedRandom); var indices = Enumerable.Range(0, Info.Ports.Length).Shuffle(self.World.SharedRandom);
foreach (var i in indices) foreach (var i in indices)
{ {
var yaw = bodyYaw + Ports[i].Yaw; var yaw = bodyYaw + Info.Ports[i].Yaw;
var leftTurn = (yaw - targetYaw).Angle; var leftTurn = (yaw - targetYaw).Angle;
var rightTurn = (targetYaw - yaw).Angle; var rightTurn = (targetYaw - yaw).Angle;
if (Math.Min(leftTurn, rightTurn) <= Ports[i].Cone.Angle) if (Math.Min(leftTurn, rightTurn) <= Info.Ports[i].Cone.Angle)
return Ports[i]; return Info.Ports[i];
} }
return null; return null;
@@ -178,7 +179,7 @@ namespace OpenRA.Mods.Common.Traits
public IEnumerable<IRenderable> Render(Actor self, WorldRenderer wr) public IEnumerable<IRenderable> Render(Actor self, WorldRenderer wr)
{ {
var pal = wr.Palette(info.MuzzlePalette); var pal = wr.Palette(Info.MuzzlePalette);
// Display muzzle flashes // Display muzzle flashes
foreach (var m in muzzles) foreach (var m in muzzles)

View File

@@ -60,7 +60,7 @@ namespace OpenRA.Mods.Common.Traits
if (garrison != null) if (garrison != null)
{ {
var bodyOrientation = coords.Value.QuantizeOrientation(self, self.Orientation); var bodyOrientation = coords.Value.QuantizeOrientation(self, self.Orientation);
foreach (var p in garrison.Ports) foreach (var p in garrison.Info.Ports)
{ {
var pos = self.CenterPosition + coords.Value.LocalToWorld(p.Offset.Rotate(bodyOrientation)); var pos = self.CenterPosition + coords.Value.LocalToWorld(p.Offset.Rotate(bodyOrientation));
var da = coords.Value.LocalToWorld(new WVec(224, 0, 0).Rotate(WRot.FromYaw(p.Yaw + p.Cone)).Rotate(bodyOrientation)); var da = coords.Value.LocalToWorld(new WVec(224, 0, 0).Rotate(WRot.FromYaw(p.Yaw + p.Cone)).Rotate(bodyOrientation));