Files
firestorm/Gameleap/mw4/Content/ABLScripts/GenericScripts/Generic_PatrolAlly.abl
T
Cyd 2b8ca921cb Initial full mirror of c:\VWE (source + assets + toolchain + outputs) via Git LFS
Complete disaster-recovery snapshot: engine/game source, game data assets,
VC6 toolchain + DX SDKs, build outputs, deployed game, and _UNUSED archive.
Large binaries in Git LFS; text preserved byte-for-byte (core.autocrlf=false,
no eol attributes). See RECOVERY.md for the one-clone rebuild procedure.
2026-06-24 21:28:16 -05:00

220 lines
6.5 KiB
Plaintext

//------------------------------------------------------------------
// NOTE: The fsm name below MUST be changed in order for the
// script to be considered a unique entity!
fsm Generic_PatrolAlly : integer;
//------------------------------------------------------------------
// Generic_PatrolAlly:
// Follow a path. Move to attack anything that comes within range,
// and return to the path when done.
// Whenever we get within a certain range of a target unit,
// we follow that unit, and continue to attack any enemies.
//------------------------------------------------------------------
//------------------------------------------------------------------
// Constants
//------------------------------------------------------------------
const
#include_ <content\ABLScripts\mwconst.abi>
//------------------------------------------------------------------
// Types
//------------------------------------------------------------------
type
#include_ <content\ABLScripts\mwtype.abi>
//------------------------------------------------------------------
// Variables
//------------------------------------------------------------------
var
static integer attackRange1; // At what range do I start shooting?
static integer withdrawRange1; // At what range do I withdraw from combat completely?
static integer path; // What path do I follow?
static integer moveType; // How I move along the path
static integer speed; // The speed at which I move along the path
static ObjectID whoToJoin; // Who do I want to join?
static integer joinRange; // At what range do I join my leader?
static integer followXOffset; // My follow X offset
static integer followYOffset; // My follow Y offset
static integer attackRange2; // At what range do I start shooting (after joining)?
static integer withdrawRange2; // At what range do I stop shooting (after joining)?
static integer piloting; // Piloting skill
static integer gunnery; // Gunnery skill/chance to hit
static real minDelay; // Minimum amount of time I will wait between shots once a weapon is reloaded
static real maxDelay; // Maximum amount of time I will wait between shots once a weapon is reloaded
static integer eliteLevel; // Elite level. This helps determine tactics, defensive manuevers, opportunity fire
// and other things. It indicates a general level of combat experience.
static integer attackThrottle; // My attack throttle
static integer findTypes; // What kind of enemies to look for
static integer isShotRadius; // How far away from me will I detect an enemy shot?
static integer attackSound; // The attack sound I play when I first attack
static integer deathSound; // The sound I play when I die
static integer mood; // My default mood.
static integer takeOffDistance; // My take-off distance if I'm an airplane (ignored if not an airplane)
//------------------------------------------------------------------
// Init: my initialization function
//------------------------------------------------------------------
function Init;
code
// script-specific variables
attackRange1 = 500;
withdrawRange1 = attackRange1 * 3 / 2;
path = -1;
moveType = move_circle;
speed = 600;
whoToJoin = NO_UNIT;
joinRange = 500;
followXOffset = 0;
followYOffset = 50;
attackRange2 = attackRange1;
withdrawRange2 = attackRange2 * 3 / 2;
takeOffDistance = 150;
// driver settings
piloting = 50;
gunnery = 30;
minDelay = 1.5;
maxDelay = 3.0;
eliteLevel = 30;
attackThrottle = 80;
isShotRadius = 120;
attackSound = -1; // no sound
deathSound = -1; // no sound
mood = NEUTRAL_START;
findTypes = FT_DEFAULT;
endfunction;
//------------------------------------------------------------------
// StartState: my initial state
//------------------------------------------------------------------
state StartState;
code
SetFiringDelay (ME,minDelay,maxDelay);
SetIgnoreFriendlyFire (ME,true);
SetIsShotRadius (ME,isShotRadius);
SetEntropyMood (ME,mood);
SetCurMood (ME,mood);
SetSkillLevel (ME,piloting,gunnery,eliteLevel);
SetAttackThrottle (ME,attackThrottle);
if (orderTakeOff(takeOffDistance) == true) then
trans FollowPathState;
endif;
endstate;
//------------------------------------------------------------------
// FollowPathState: wait for something to shoot
//------------------------------------------------------------------
state FollowPathState;
code
if (IsWithin(ME,whoToJoin,joinRange)) then
trans FollowState;
endif;
if (FindEnemy(attackRange1,findTypes)) then
trans Attack1State;
endif;
if (path <> -1) then
OrderMoveResumePatrol(path,speed,moveType,true,false);
else
OrderMoveLookOut;
endif;
endstate;
//------------------------------------------------------------------
// Attack1State: look for something to shoot
//------------------------------------------------------------------
state Attack1State;
code
if (LeaveAttackState(withdrawRange1)) then
OrderStopAttacking;
SetTarget(ME,NO_UNIT);
trans FollowPathState;
endif;
if (IsWithin(ME,whoToJoin,joinRange)) then
trans Attack2State;
endif;
OrderAttack(true);
endstate;
//------------------------------------------------------------------
// FollowState: follow the chosen unit
//------------------------------------------------------------------
state FollowState;
code
if (FindEnemy(attackRange2,findTypes)) then
trans Attack2State;
endif;
OrderMoveFollow(whoToJoin,followXOffset,followYOffset);
endstate;
//------------------------------------------------------------------
// Attack2State: look for something to shoot
//------------------------------------------------------------------
state Attack2State;
code
if (LeaveAttackState(withdrawRange2)) then
OrderStopAttacking;
SetTarget(ME,NO_UNIT);
trans FollowState;
endif;
OrderAttack(true);
endstate;
//------------------------------------------------------------------
// DeadState: OK, I kicked the bucket.
//------------------------------------------------------------------
state DeadState;
code
if (deathSound <> -1) then
PlaySoundOnce(deathSound);
endif;
orderDie;
endstate;
endfsm.