Add plumbing for customizable vertical ProximityTrigger range

And check DistanceAboveTerrain instead of just vertical distance to upgrade
source.
This is necessary to avoid situations where an actor is technically on the right
vertical distance above/below ground, but not upgraded because it is located on a lower/higher terrain level than the upgrade source.
This commit is contained in:
reaperrr
2016-01-28 23:13:29 +01:00
parent b254d5fa88
commit b0e90989a6
4 changed files with 20 additions and 15 deletions

View File

@@ -98,22 +98,26 @@ namespace OpenRA.Traits
WPos position; WPos position;
WDist range; WDist range;
WDist vRange;
IEnumerable<Actor> currentActors = Enumerable.Empty<Actor>(); IEnumerable<Actor> currentActors = Enumerable.Empty<Actor>();
public ProximityTrigger(WPos pos, WDist range, Action<Actor> onActorEntered, Action<Actor> onActorExited) public ProximityTrigger(WPos pos, WDist range, WDist vRange, Action<Actor> onActorEntered, Action<Actor> onActorExited)
{ {
this.onActorEntered = onActorEntered; this.onActorEntered = onActorEntered;
this.onActorExited = onActorExited; this.onActorExited = onActorExited;
Update(pos, range); Update(pos, range, vRange);
} }
public void Update(WPos newPos, WDist newRange) public void Update(WPos newPos, WDist newRange, WDist newVRange)
{ {
position = newPos; position = newPos;
range = newRange; range = newRange;
vRange = newVRange;
var offset = new WVec(newRange, newRange, newVRange);
var offset = new WVec(newRange, newRange, WDist.Zero);
TopLeft = newPos - offset; TopLeft = newPos - offset;
BottomRight = newPos + offset; BottomRight = newPos + offset;
@@ -128,7 +132,8 @@ namespace OpenRA.Traits
var oldActors = currentActors; var oldActors = currentActors;
var delta = new WVec(range, range, WDist.Zero); var delta = new WVec(range, range, WDist.Zero);
currentActors = am.ActorsInBox(position - delta, position + delta) currentActors = am.ActorsInBox(position - delta, position + delta)
.Where(a => (a.CenterPosition - position).HorizontalLengthSquared < range.LengthSquared) .Where(a => (a.CenterPosition - position).HorizontalLengthSquared < range.LengthSquared
&& (vRange.Length == 0 || (a.World.Map.DistanceAboveTerrain(a.CenterPosition).LengthSquared <= vRange.LengthSquared)))
.ToList(); .ToList();
var entered = currentActors.Except(oldActors); var entered = currentActors.Except(oldActors);
@@ -439,10 +444,10 @@ namespace OpenRA.Traits
} }
} }
public int AddProximityTrigger(WPos pos, WDist range, Action<Actor> onEntry, Action<Actor> onExit) public int AddProximityTrigger(WPos pos, WDist range, WDist vRange, Action<Actor> onEntry, Action<Actor> onExit)
{ {
var id = nextTriggerId++; var id = nextTriggerId++;
var t = new ProximityTrigger(pos, range, onEntry, onExit); var t = new ProximityTrigger(pos, range, vRange, onEntry, onExit);
proximityTriggers.Add(id, t); proximityTriggers.Add(id, t);
foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight)) foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight))
@@ -463,7 +468,7 @@ namespace OpenRA.Traits
t.Dispose(); t.Dispose();
} }
public void UpdateProximityTrigger(int id, WPos newPos, WDist newRange) public void UpdateProximityTrigger(int id, WPos newPos, WDist newRange, WDist newVRange)
{ {
ProximityTrigger t; ProximityTrigger t;
if (!proximityTriggers.TryGetValue(id, out t)) if (!proximityTriggers.TryGetValue(id, out t))
@@ -472,7 +477,7 @@ namespace OpenRA.Traits
foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight)) foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight))
bin.ProximityTriggers.Remove(t); bin.ProximityTriggers.Remove(t);
t.Update(newPos, newRange); t.Update(newPos, newRange, newVRange);
foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight)) foreach (var bin in BinsInBox(t.TopLeft, t.BottomRight))
bin.ProximityTriggers.Add(t); bin.ProximityTriggers.Add(t);

View File

@@ -373,7 +373,7 @@ namespace OpenRA.Mods.Common.Scripting
} }
}; };
triggerId = Context.World.ActorMap.AddProximityTrigger(pos, range, invokeEntry, null); triggerId = Context.World.ActorMap.AddProximityTrigger(pos, range, WDist.Zero, invokeEntry, null);
return triggerId; return triggerId;
} }
@@ -400,7 +400,7 @@ namespace OpenRA.Mods.Common.Scripting
} }
}; };
triggerId = Context.World.ActorMap.AddProximityTrigger(pos, range, null, invokeExit); triggerId = Context.World.ActorMap.AddProximityTrigger(pos, range, WDist.Zero, null, invokeExit);
return triggerId; return triggerId;
} }

View File

@@ -67,7 +67,7 @@ namespace OpenRA.Mods.Common.Traits
return; return;
// TODO: Eventually support CellTriggers as well // TODO: Eventually support CellTriggers as well
proximityTrigger = self.World.ActorMap.AddProximityTrigger(self.CenterPosition, Info.Range, ActorEntered, ActorLeft); proximityTrigger = self.World.ActorMap.AddProximityTrigger(self.CenterPosition, Info.Range, WDist.Zero, ActorEntered, ActorLeft);
} }
void INotifyRemovedFromWorld.RemovedFromWorld(Actor self) void INotifyRemovedFromWorld.RemovedFromWorld(Actor self)
@@ -84,7 +84,7 @@ namespace OpenRA.Mods.Common.Traits
if (!self.IsInWorld || self.CenterPosition == prevPosition) if (!self.IsInWorld || self.CenterPosition == prevPosition)
return; return;
self.World.ActorMap.UpdateProximityTrigger(proximityTrigger, self.CenterPosition, Info.Range); self.World.ActorMap.UpdateProximityTrigger(proximityTrigger, self.CenterPosition, Info.Range, WDist.Zero);
prevPosition = self.CenterPosition; prevPosition = self.CenterPosition;
} }

View File

@@ -57,7 +57,7 @@ namespace OpenRA.Mods.Common.Traits
public void AddedToWorld(Actor self) public void AddedToWorld(Actor self)
{ {
cachedPosition = self.CenterPosition; cachedPosition = self.CenterPosition;
proximityTrigger = self.World.ActorMap.AddProximityTrigger(cachedPosition, cachedRange, ActorEntered, ActorExited); proximityTrigger = self.World.ActorMap.AddProximityTrigger(cachedPosition, cachedRange, WDist.Zero, ActorEntered, ActorExited);
} }
public void RemovedFromWorld(Actor self) public void RemovedFromWorld(Actor self)
@@ -80,7 +80,7 @@ namespace OpenRA.Mods.Common.Traits
{ {
cachedPosition = self.CenterPosition; cachedPosition = self.CenterPosition;
cachedRange = desiredRange; cachedRange = desiredRange;
self.World.ActorMap.UpdateProximityTrigger(proximityTrigger, cachedPosition, cachedRange); self.World.ActorMap.UpdateProximityTrigger(proximityTrigger, cachedPosition, cachedRange, WDist.Zero);
} }
} }