Added ProximityCaptor and filtering of possible captors for KOTH

This commit is contained in:
geckosoft
2010-11-22 11:49:45 +01:00
committed by Chris Forbes
parent de26b63fd2
commit 0f17fa34a8
8 changed files with 152 additions and 14 deletions

View File

@@ -106,6 +106,7 @@
<Compile Include="UnitStances\UnitStanceHoldFire.cs" /> <Compile Include="UnitStances\UnitStanceHoldFire.cs" />
<Compile Include="UnitStances\UnitStanceReturnFire.cs" /> <Compile Include="UnitStances\UnitStanceReturnFire.cs" />
<Compile Include="UnitStances\UnitStanceHoldGround.cs" /> <Compile Include="UnitStances\UnitStanceHoldGround.cs" />
<Compile Include="ProximityCaptor.cs" />
<Compile Include="Valued.cs" /> <Compile Include="Valued.cs" />
<Compile Include="Combat.cs" /> <Compile Include="Combat.cs" />
<Compile Include="Player\SurrenderOnDisconnect.cs" /> <Compile Include="Player\SurrenderOnDisconnect.cs" />

View File

@@ -0,0 +1,48 @@
#region Copyright & License Information
/*
* Copyright 2007-2010 The OpenRA Developers (see AUTHORS)
* This file is part of OpenRA, which is free software. It is made
* available to you under the terms of the GNU General Public License
* as published by the Free Software Foundation. For more information,
* see LICENSE.
*/
#endregion
using System.Linq;
using OpenRA.Traits;
namespace OpenRA.Mods.RA
{
public class ProximityCaptorInfo : ITraitInfo
{
public readonly string[] Types = {};
public object Create(ActorInitializer init) { return new ProximityCaptor(this); }
}
public class ProximityCaptor
{
public readonly ProximityCaptorInfo Info;
public string[] Types;
[Sync]
public int Hash { get { return string.Join(",", Types).GetHashCode(); } }
public ProximityCaptor(ProximityCaptorInfo info)
{
Info = info;
Types = info.Types.Select(t => t.ToLowerInvariant()).OrderBy(t => t).ToArray();
}
public bool HasAny(string[] typesList)
{
return typesList.Select(t => t.ToLowerInvariant()).Any(flag => Types.Contains(flag));
}
public bool HasAll(string[] typesList)
{
return typesList.Select(t => t.ToLowerInvariant()).All(flag => Types.Contains(flag));
}
}
}

View File

@@ -9,6 +9,7 @@ namespace OpenRA.Mods.RA
public readonly bool Permanent = false; public readonly bool Permanent = false;
public readonly int Range = 5; public readonly int Range = 5;
public readonly bool MustBeClear = false; public readonly bool MustBeClear = false;
public readonly string[] CaptorTypes = {"Vehicle", "Tank", "Infantry"};
public object Create(ActorInitializer init) { return new ProximityCapturable(init.self, this); } public object Create(ActorInitializer init) { return new ProximityCapturable(init.self, this); }
} }
@@ -35,6 +36,13 @@ namespace OpenRA.Mods.RA
[Sync] [Sync]
public bool MustBeClear = false; public bool MustBeClear = false;
public string[] CaptorTypes = {};
[Sync]
public int ActorTypesHash
{
get { return string.Join(",", CaptorTypes).GetHashCode(); }
}
public Actor Self; public Actor Self;
public ProximityCapturable(Actor self, ProximityCapturableInfo info) public ProximityCapturable(Actor self, ProximityCapturableInfo info)
@@ -45,6 +53,7 @@ namespace OpenRA.Mods.RA
MustBeClear = info.MustBeClear; MustBeClear = info.MustBeClear;
Self = self; Self = self;
OriginalOwner = self.Owner; OriginalOwner = self.Owner;
CaptorTypes = info.CaptorTypes;
} }
public void Tick(Actor self) public void Tick(Actor self)
@@ -55,11 +64,11 @@ namespace OpenRA.Mods.RA
if (!Captured) if (!Captured)
{ {
var captor = GetInRange(self, OriginalOwner, Range); var captor = GetInRange(self, OriginalOwner, Range, CaptorTypes);
if (captor != null) if (captor != null)
{ {
if (MustBeClear && !IsClear(self, captor.Owner, Range, OriginalOwner)) return; if (MustBeClear && !IsClear(self, captor.Owner, Range, OriginalOwner, CaptorTypes)) return;
ChangeOwnership(self, captor, OriginalOwner); ChangeOwnership(self, captor, OriginalOwner);
} }
@@ -68,7 +77,7 @@ namespace OpenRA.Mods.RA
} }
// if the area must be clear, and there is more than 1 player nearby => return ownership to default // if the area must be clear, and there is more than 1 player nearby => return ownership to default
if (MustBeClear && !IsClear(self, Owner, Range, OriginalOwner)) if (MustBeClear && !IsClear(self, Owner, Range, OriginalOwner, CaptorTypes))
{ {
// Revert Ownership // Revert Ownership
ChangeOwnership(self, Owner, OriginalOwner); ChangeOwnership(self, Owner, OriginalOwner);
@@ -76,10 +85,10 @@ namespace OpenRA.Mods.RA
} }
// See if the 'temporary' owner still is in range // See if the 'temporary' owner still is in range
if (!IsStillInRange(self, self.Owner, Range)) if (!IsStillInRange(self, self.Owner, Range, CaptorTypes))
{ {
// no.. So find a new one // no.. So find a new one
var captor = GetInRange(self, OriginalOwner, Range); var captor = GetInRange(self, OriginalOwner, Range, CaptorTypes);
if (captor != null) // got one if (captor != null) // got one
{ {
@@ -140,26 +149,29 @@ namespace OpenRA.Mods.RA
b.Stances[a] == Stance.Ally; b.Stances[a] == Stance.Ally;
} }
public static bool IsClear(Actor self, Player currentOwner, int range, Player originalOwner) public static bool IsClear(Actor self, Player currentOwner, int range, Player originalOwner, string[] actorTypes)
{ {
var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range); var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range);
return unitsInRange.Where(a => !a.Destroyed && a.IsInWorld && a != self && !a.Owner.NonCombatant && a.Owner != originalOwner) return unitsInRange.Where(a => !a.Destroyed && a.IsInWorld && a != self && !a.Owner.NonCombatant && a.Owner != originalOwner)
.Where(a => a.Owner != currentOwner).All(a => AreMutualAllies(a.Owner, currentOwner)); .Where(a => a.Owner != currentOwner)
.Where(a => actorTypes.Length == 0 || (a.HasTrait<ProximityCaptor>() && a.Trait<ProximityCaptor>().HasAny(actorTypes)))
.All(a => AreMutualAllies(a.Owner, currentOwner));
} }
// TODO exclude other NeutralActor that arent permanent // TODO exclude other NeutralActor that arent permanent
public static bool IsStillInRange(Actor self, Player currentOwner, int range) public static bool IsStillInRange(Actor self, Player currentOwner, int range, string[] actorTypes)
{ {
var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range); var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range);
return unitsInRange return unitsInRange
.Where(a => a.Owner == currentOwner && !a.Destroyed && a.IsInWorld && a != self) .Where(a => a.Owner == currentOwner && !a.Destroyed && a.IsInWorld && a != self)
.Where(a => actorTypes.Length == 0 || (a.HasTrait<ProximityCaptor>() && a.Trait<ProximityCaptor>().HasAny(actorTypes)))
.Any(); .Any();
} }
// TODO exclude other NeutralActor that arent permanent // TODO exclude other NeutralActor that arent permanent
public static Actor GetInRange(Actor self, Player originalOwner, int range) public static Actor GetInRange(Actor self, Player originalOwner, int range, string[] actorTypes)
{ {
var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range); var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range);
@@ -167,11 +179,12 @@ namespace OpenRA.Mods.RA
.Where(a => a.Owner != originalOwner && !a.Destroyed && a.IsInWorld && a != self) .Where(a => a.Owner != originalOwner && !a.Destroyed && a.IsInWorld && a != self)
.Where(a => !a.Owner.PlayerRef.OwnsWorld) .Where(a => !a.Owner.PlayerRef.OwnsWorld)
.Where(a => !a.Owner.PlayerRef.NonCombatant) .Where(a => !a.Owner.PlayerRef.NonCombatant)
.Where(a => actorTypes.Length == 0 || (a.HasTrait<ProximityCaptor>() && a.Trait<ProximityCaptor>().HasAny(actorTypes)))
.OrderBy(a => (a.CenterLocation - self.CenterLocation).LengthSquared) .OrderBy(a => (a.CenterLocation - self.CenterLocation).LengthSquared)
.FirstOrDefault(); .FirstOrDefault();
} }
public static int CountPlayersNear(Actor self, Player ignoreMe, int range) public static int CountPlayersNear(Actor self, Player ignoreMe, int range, string[] actorTypes)
{ {
var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range); var unitsInRange = self.World.FindUnitsInCircle(self.CenterLocation, Game.CellSize * range);
@@ -179,6 +192,7 @@ namespace OpenRA.Mods.RA
.Where(a => a.Owner != ignoreMe && !a.Destroyed && a.IsInWorld && a != self) .Where(a => a.Owner != ignoreMe && !a.Destroyed && a.IsInWorld && a != self)
.Where(a => !a.Owner.PlayerRef.OwnsWorld) .Where(a => !a.Owner.PlayerRef.OwnsWorld)
.Where(a => !a.Owner.PlayerRef.NonCombatant) .Where(a => !a.Owner.PlayerRef.NonCombatant)
.Where(a =>actorTypes.Length == 0 || ( a.HasTrait<ProximityCaptor>() && a.Trait<ProximityCaptor>().HasAny(actorTypes)))
.Select(a => a.Owner) .Select(a => a.Owner)
.Distinct() .Distinct()
.Count(); .Count();

View File

@@ -28,6 +28,8 @@
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
AttackMove: AttackMove:
ProximityCaptor:
Types:Vehicle
^Tank: ^Tank:
AppearsOnRadar: AppearsOnRadar:
@@ -59,6 +61,8 @@
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
AttackMove: AttackMove:
ProximityCaptor:
Types:Tank
^Helicopter: ^Helicopter:
AppearsOnRadar: AppearsOnRadar:
@@ -79,6 +83,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
ProximityCaptor:
Types:Helicopter
^Infantry: ^Infantry:
AppearsOnRadar: AppearsOnRadar:
@@ -118,6 +124,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
ProximityCaptor:
Types:Infantry
^CivInfantry: ^CivInfantry:
Inherits: ^Infantry Inherits: ^Infantry
@@ -141,6 +149,8 @@
# ActorLostNotification: # ActorLostNotification:
# Notification: civdead1.aud # Notification: civdead1.aud
# NotifyAll: true # NotifyAll: true
ProximityCaptor:
Types:CivilianInfantry
^Plane: ^Plane:
AppearsOnRadar: AppearsOnRadar:
@@ -155,6 +165,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
ProximityCaptor:
Types:Plane
^Ship: ^Ship:
AppearsOnRadar: AppearsOnRadar:
@@ -173,6 +185,8 @@
ActorLostNotification: ActorLostNotification:
Notification: unitlost.aud Notification: unitlost.aud
AttackMove: AttackMove:
ProximityCaptor:
Types:Ship
^Building: ^Building:
AppearsOnRadar: AppearsOnRadar:
@@ -211,6 +225,8 @@
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
ShakeOnDeath: ShakeOnDeath:
ProximityCaptor:
Types:Building
^CivBuilding: ^CivBuilding:
Inherits: ^Building Inherits: ^Building
@@ -226,6 +242,8 @@
# -FrozenUnderFog: # -FrozenUnderFog:
Tooltip: Tooltip:
Name: Civilian Building Name: Civilian Building
ProximityCaptor:
Types:CivilianBuilding
^CivField: ^CivField:
Inherits: ^CivBuilding Inherits: ^CivBuilding
@@ -237,6 +255,9 @@
RenderBuilding: RenderBuilding:
OverrideTileset: DESERT OverrideTileset: DESERT
OverrideImage: v23 OverrideImage: v23
-ProximityCaptor:
ProximityCaptor:
Types:CivilianField
^Wall: ^Wall:
AppearsOnRadar: AppearsOnRadar:
@@ -263,6 +284,8 @@
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
AutoTargetIgnore: AutoTargetIgnore:
ProximityCaptor:
Types:Wall
^Tree: ^Tree:
Tooltip: Tooltip:
@@ -277,6 +300,8 @@
Terrain: Tree Terrain: Tree
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
ProximityCaptor:
Types:Tree
^Rock: ^Rock:
Tooltip: Tooltip:
@@ -291,6 +316,8 @@
Terrain: Tree Terrain: Tree
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
ProximityCaptor:
Types:Rock
^Husk: ^Husk:
Health: Health:
@@ -303,6 +330,8 @@
HiddenUnderFog: HiddenUnderFog:
AppearsOnRadar: AppearsOnRadar:
Burns: Burns:
ProximityCaptor:
Types:Husk
^Bridge: ^Bridge:
Tooltip: Tooltip:
@@ -318,3 +347,5 @@
Building: Building:
Footprint: ______ ______ ______ ______ Footprint: ______ ______ ______ ______
Dimensions: 6,4 Dimensions: 6,4
ProximityCaptor:
Types:Bridge

View File

@@ -191,3 +191,5 @@ CRATE:
Unit: mcv Unit: mcv
RenderUnit: RenderUnit:
BelowUnits: BelowUnits:
ProximityCaptor:
Types:Crate

View File

@@ -25,7 +25,9 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlst1.aud Notification: unitlst1.aud
ProximityCaptor:
Types:Vehicle
^Tank: ^Tank:
AppearsOnRadar: AppearsOnRadar:
Mobile: Mobile:
@@ -53,6 +55,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlst1.aud Notification: unitlst1.aud
ProximityCaptor:
Types:Tank
^Infantry: ^Infantry:
AppearsOnRadar: AppearsOnRadar:
@@ -87,6 +91,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: unitlst1.aud Notification: unitlst1.aud
ProximityCaptor:
Types:Infantry
^Ship: ^Ship:
AppearsOnRadar: AppearsOnRadar:
@@ -107,6 +113,8 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: navylst1.aud Notification: navylst1.aud
ProximityCaptor:
Types:Ship
^Plane: ^Plane:
AppearsOnRadar: AppearsOnRadar:
@@ -122,10 +130,13 @@
DrawLineToTarget: DrawLineToTarget:
ActorLostNotification: ActorLostNotification:
Notification: aunitl1.aud Notification: aunitl1.aud
<<<<<<< HEAD
DebugAircraftFacing: DebugAircraftFacing:
DebugAircraftSubPxX: DebugAircraftSubPxX:
DebugAircraftSubPxY: DebugAircraftSubPxY:
DebugAircraftAltitude: DebugAircraftAltitude:
ProximityCaptor:
Types:Plane
^Building: ^Building:
AppearsOnRadar: AppearsOnRadar:
@@ -151,6 +162,8 @@
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
ShakeOnDeath: ShakeOnDeath:
ProximityCaptor:
Types:Building
^Wall: ^Wall:
AppearsOnRadar: AppearsOnRadar:
@@ -179,6 +192,8 @@
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
AutoTargetIgnore: AutoTargetIgnore:
ProximityCaptor:
Types:Wall
^CivBuilding: ^CivBuilding:
Inherits: ^Building Inherits: ^Building
@@ -189,12 +204,17 @@
Type: Wood Type: Wood
Tooltip: Tooltip:
Name: Civilian Building Name: Civilian Building
ProximityCaptor:
Types:CivilianBuilding
^CivField: ^CivField:
Inherits: ^CivBuilding Inherits: ^CivBuilding
-Selectable: -Selectable:
Tooltip: Tooltip:
Name: Field Name: Field
-ProximityCaptor:
ProximityCaptor:
Types:CivilianField
^Tree: ^Tree:
Tooltip: Tooltip:
@@ -209,6 +229,8 @@
Terrain: Tree Terrain: Tree
EditorAppearance: EditorAppearance:
RelativeToTopLeft: yes RelativeToTopLeft: yes
ProximityCaptor:
Types:Tree
^Husk: ^Husk:
Health: Health:
@@ -221,6 +243,8 @@
HiddenUnderFog: HiddenUnderFog:
AppearsOnRadar: AppearsOnRadar:
Burns: Burns:
ProximityCaptor:
Types:Husk
^Bridge: ^Bridge:
Tooltip: Tooltip:
@@ -233,3 +257,5 @@
Dimensions: 4,2 Dimensions: 4,2
Health: Health:
HP: 1000 HP: 1000
ProximityCaptor:
Types:Bridge

View File

@@ -281,6 +281,9 @@ C1:
Range: 2 Range: 2
AttackFrontal: AttackFrontal:
PrimaryWeapon: Pistol PrimaryWeapon: Pistol
-ProximityCaptor:
ProximityCaptor:
Types:CivilianInfantry
C2: C2:
Inherits: ^Infantry Inherits: ^Infantry
@@ -299,6 +302,9 @@ C2:
Range: 2 Range: 2
AttackFrontal: AttackFrontal:
PrimaryWeapon: Pistol PrimaryWeapon: Pistol
-ProximityCaptor:
ProximityCaptor:
Types:CivilianInfantry
SHOK: SHOK:
Inherits: ^Infantry Inherits: ^Infantry

View File

@@ -208,6 +208,8 @@ MINP:
InvisibleToOthers: InvisibleToOthers:
Tooltip: Tooltip:
Name: Anti-Personnel Mine Name: Anti-Personnel Mine
ProximityCaptor:
Types:Mine
MINV: MINV:
Mine: Mine:
@@ -221,6 +223,8 @@ MINV:
InvisibleToOthers: InvisibleToOthers:
Tooltip: Tooltip:
Name: Anti-Tank Mine Name: Anti-Tank Mine
ProximityCaptor:
Types:Mine
CRATE: CRATE:
Tooltip: Tooltip:
@@ -279,13 +283,17 @@ CRATE:
Unit: 4tnk Unit: 4tnk
RenderUnit: RenderUnit:
BelowUnits: BelowUnits:
ProximityCaptor:
Types:Crate
CAMERA: CAMERA:
Aircraft: Aircraft:
Health: Health:
HP:1000 HP:1000
RevealsShroud: RevealsShroud:
Range: 10 Range: 10
ProximityCaptor:
Types:Camera
FLARE: FLARE:
Aircraft: Aircraft:
@@ -298,6 +306,8 @@ FLARE:
HiddenUnderFog: HiddenUnderFog:
Tooltip: Tooltip:
Name: Flare Name: Flare
ProximityCaptor:
Types: Flare
powerproxy.parabombs: powerproxy.parabombs:
AirstrikePower: AirstrikePower:
@@ -318,4 +328,4 @@ powerproxy.sonarpulse:
AllowMultiple: yes AllowMultiple: yes
OneShot: yes OneShot: yes
EndChargeSound: pulse1.aud EndChargeSound: pulse1.aud
SelectTargetSound: slcttgt1.aud SelectTargetSound: slcttgt1.aud