From 6170ff825589f9e09f63bafd70dc7dbed148aefb Mon Sep 17 00:00:00 2001 From: Ragora Date: Sun, 17 Mar 2013 23:06:58 -0400 Subject: [PATCH] Other changes --- scripts/ai.cs | 11 +- scripts/chatCommands.cs | 1 + scripts/data/messagedata.cs | 84 -- scripts/message.cs | 74 - scripts/modscripts/ai/zombie.cs | 1664 +++++++++++++++++++++ scripts/modscripts/chatcommands/admin.cs | 12 +- scripts/modscripts/chatcommands/zombie.cs | 2 +- scripts/pack.cs | 3 + scripts/packs/ZSpawnpack.cs | 1661 -------------------- scripts/power.cs | 2 + scripts/server.cs | 40 +- scripts/vehicles/vehicle_shrike.cs | 6 +- scripts/weapTurretCode.cs | 5 +- 13 files changed, 1716 insertions(+), 1849 deletions(-) create mode 100644 scripts/modscripts/ai/zombie.cs diff --git a/scripts/ai.cs b/scripts/ai.cs index 84d5830..e1a56d7 100644 --- a/scripts/ai.cs +++ b/scripts/ai.cs @@ -363,17 +363,20 @@ function SimObject::AIMissionInit(%this) function ItemData::AIMissionInit(%data, %object) { - $AIItemSet.add(%object); + if (isObject($AIItemSet)) + $AIItemSet.add(%object); } function AIThrowObject(%object) { - $AIItemSet.add(%object); + if (isObject($AIItemSet)) + $AIItemSet.add(%object); } function AIGrenadeThrown(%object) { - $AIGrenadeSet.add(%object); + if (isObject($AIItemSet)) + $AIGrenadeSet.add(%object); } function AIDeployObject(%client, %object) @@ -905,4 +908,4 @@ function AIProcessVehicle(%client) function AIPilotVehicle(%client) { //this is not very well supported, but someone will find a use for this function... -} \ No newline at end of file +} diff --git a/scripts/chatCommands.cs b/scripts/chatCommands.cs index 825f25b..45ced43 100644 --- a/scripts/chatCommands.cs +++ b/scripts/chatCommands.cs @@ -444,6 +444,7 @@ function ccBf(%sender,%args) if (!isObject(%sender.player)) { // No player object? Bitch, you can't use this command. MessageClient(%sender, "Msg", "\c2You you have a player object in order to buy your inventory. ~wfx/misc/misc.error.wav"); + return; } if (%sender.BasicTimer > 0) diff --git a/scripts/data/messagedata.cs b/scripts/data/messagedata.cs index 4916026..14f6076 100644 --- a/scripts/data/messagedata.cs +++ b/scripts/data/messagedata.cs @@ -1,90 +1,6 @@ //============================================================================== // ACCM Message Database - By Blnukem. -//------------------------------------------------------------------------------ -// This is the message database for Sentinels and other miscellaneous functions -// The following will be addressed in each message cluster on what can or cannot -// be used in those messages. -// -// This was made for the pleasure of ACCM users to customize Sentinel responses -// and a few other messages. -//------------------------------------------------------------------------------ -// %1 = Sentinel's Name. -// %2 = Sender's Name. -// %3 = Sender/Target's Gender. (He/She) -// %4 = Sender/Target's Present Tense Gender. (Him/Her) -// %5 = Sender/Target's Possesive Gender. (His/Her) -// %6 = Target's Name. (Only if there is a target defined) //============================================================================== -// No Target Client for this cluster exists: - -$SentinelDenyFollowCount = 5; -$SentinelDenyFollow[0] = '\c2%1 ::\c0 %2, I am already occupied with a task, I cannot follow you.'; -$SentinelDenyFollow[1] = '\c2%1 ::\c0 I\'m already engaged in a task, %2.'; -$SentinelDenyFollow[2] = '\c2%1 ::\c0 I am occupied at the moment, %2. Sorry, but I cannot follow you.'; -$SentinelDenyFollow[3] = '\c2%1 ::\c0 %2, I\'m busy doing something. I cannot follow you.'; -$SentinelDenyFollow[4] = '\c2%1 ::\c0 I\'m already doing something, %2.'; - -//------------------------------------------------------------------------------ -// Sender and Target Clients for this cluster exist: - -$SentinelDenyAttackCount = 5; -$SentinelDenyAttack[0] = '\c2%1 ::\c0 I\'m already doing something, %2'; -$SentinelDenyAttack[1] = '\c2%1 ::\c0 %2, I\'m busy doing something. I cannot engage %6.'; -$SentinelDenyAttack[2] = '\c2%1 ::\c0 I am occupied at the moment, %2. Sorry, but I cannot do what you ask.'; -$SentinelDenyAttack[3] = '\c2%1 ::\c0 %2, I am already occupied with a task, I cannot attack %6.'; -$SentinelDenyAttack[4] = '\c2%1 ::\c0 I\'m already engaged in a task, %2.'; - -//------------------------------------------------------------------------------ -// Sender and Target Clients for this cluster exist: - -$SentinelAcceptAttackCount = 4; -$SentinelAcceptAttack[0] = '\c2%1 ::\c0 I\'m now engaging %6.'; -$SentinelAcceptAttack[1] = '\c2%1 ::\c0 Command confirmed, I will now hunt down %6.'; -$SentinelAcceptAttack[2] = '\c2%1 ::\c0 Attack protocol engaged, I will now hunt down %6.'; -$SentinelAcceptAttack[3] = '\c2%1 ::\c0 Command confirmed %2, I will now attack %6.'; - -//------------------------------------------------------------------------------ -// Sender and Target Clients for this cluster exist: - -$SentinelAttackAlreadyDeadTargetCount = 1; -$SentinelAttackAlreadyDeadTarget[0] = '\c2%1 ::\c0 %6 is already dead.'; - -//------------------------------------------------------------------------------ -// Sender and Target Clients for this cluster exist: - -$SentinelTargetTooFarCount = 1; -$SentinelTargetTooFar[0] = '\c2%1 ::\c0 Command declined. %6 is out of range.'; - -//------------------------------------------------------------------------------ -// No Target Client for this cluster exists: - -$SentinelAttackSenderCount = 1; -$SentinelAttackSender[0] = '\c2%1 ::\c0 Command declined %2, I cannot kill the person giving me an order.'; - -//------------------------------------------------------------------------------ -// No Target Client for this cluster exists: - -$SentinelAttackSenderNotAdminCount = 1; -$SentinelAttackSenderNotAdmin[0] = '\c2%1 ::\c0 %2, you must be an admin to set an attack order.'; - -//------------------------------------------------------------------------------ -// No Sender Client for this cluster exists: - -$SentinelAnnoyedCount = 3; -$SentinelAnnoyed[0] = '\c2%1 ::\c0 %2, now you will learn not to fly around sentinels.'; -$SentinelAnnoyed[1] = '\c2%1 ::\c0 Target Designated. %2, you were warned not to fly around Sentinels.'; -$SentinelAnnoyed[2] = '\c2%1 ::\c0 %2, you need to learn to not fly around Sentinels.'; - -//------------------------------------------------------------------------------ -// No Sender Client for this cluster exists: - -$SentinelWarnCount = 4; -$SentinelWarn[0] = '\c2%1 ::\c0 Please stop flying around me, %2.'; -$SentinelWarn[1] = '\c2%1 ::\c0 Quit flying around me %2.'; -$SentinelWarn[2] = '\c2%1 ::\c0 Do not fly around me, %2.'; -$SentinelWarn[3] = '\c2%1 ::\c0 %2, if you do not stop flying around me, you will be killed.'; - -//------------------------------------------------------------------------------ $ACCMTipCount = 10; $ACCMTip[0] = "Random Tip:\nRemember, type /help for a list of useful commands."; diff --git a/scripts/message.cs b/scripts/message.cs index 5a16c71..a10e50a 100644 --- a/scripts/message.cs +++ b/scripts/message.cs @@ -406,80 +406,6 @@ function chatMessageAll( %sender, %msgString, %a1, %a2, %a3, %a4, %a5, %a6, %a7, return; } - -//============================================================================== -// Interactive Sentinel AI. By Blnukem. -//============================================================================== -// Sentinel Interaction: - - if ($Host::SentinelProtection $= 1 && MonitorGroup.GetCount() == 1 && strstr(%a2, "Follow me") != -1 || strstr(%a2, "follow me") != -1 - || strstr(%a2, "Come") != -1 || strstr(%a2, "come") != -1) - { - Call("ccFollow", %sender); - } - - if ($Host::SentinelProtection $= 1 && MonitorGroup.GetCount() == 1 && strstr(%a2, "Stop") != -1 || strstr(%a2, "stop") != -1 - || strstr(%a2, "Don't follow") != -1 || strstr(%a2, "Dont follow") != -1 || strstr(%a2, "don't follow") != -1 || strstr(%a2, "dont follow") != -1) - { - Call("ccStop", %sender); - } - - if ($Host::SentinelProtection == 1 && MonitorGroup.GetCount() == 1 && strstr(%a2, "Kill") == 0) - { - %rest = getsubstr(%a2, 1, 255); - %target = plnametocid(getword(%rest, 0)); - %message = getsubstr(%rest, strlen(getword(%rest, 0)) + 1, 255); - ccAttack(%sender, %message); - } - -//------------------------------------------------------------------------------ -// Monitor Interaction: - - %sentinelcount = SentinelGroup.GetCount(); - %zombiecount = ZombieGroup.GetCount(); - if ($Host::SentinelProtection !$= 1 || MonitorGroup.GetCount() != 1) - { - } - - if ($Host::SentinelProtection $= 1 && MonitorGroup.GetCount() $= 1 && strstr(%a2, "spawn a sentinel") != -1 || strstr(%a2, "Spawn a sentinel") != -1 - || strstr(%a2, "Spawn a Sentinel") != -1 || strstr(%a2, "spawn another sentinel") != -1 || strstr(%a2, "Spawn another sentinel") != -1 || strstr(%a2, "Spawn another Sentinel") != -1) - { - Call("ccCreateSentinel", %sender); - } - - if ($Host::SentinelProtection $= 1 && MonitorGroup.GetCount() == 1 && strstr(%a2, "How many sentinels") != -1 || strstr(%a2, "how many sentinels") != -1 || - strstr(%a2, "Display sentinel count") != -1 || strstr(%a2, "display sentinel count") != -1) - { - if (SentinelGroup.GetCount() == 0) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 There are no Sentinel units currently deployed."); - } else if (SentinelGroup.GetCount() == 1) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 There is 1 Sentinel unit currently deployed."); - } else if (SentinelGroup.GetCount() >= 1) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 There are "@%sentinelcount@" Sentinel units currently deployed."); - } - } else if ($Host::SentinelProtection $= 1 && MonitorGroup.GetCount() == 1 && strstr(%a2, "How many zombies") != -1 || strstr(%a2, "how many zombies") != -1 || - strstr(%a2, "Display zombie count") != -1 || strstr(%a2, "display zombie count") != -1) - { - if (ZombieGroup.GetCount() == 0) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 No zombies have been detected by the Sentinel Network."); - } else if (ZombieGroup.GetCount() == 1) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 There is 1 zombie currently detected by the Sentinel Network."); - } else if (ZombieGroup.GetCount() >= 1) - { - Schedule(1, 0, MessageAll, "Msg", "\c2Monitor ::\c0 There are "@%zombiecount@" zombies detected by the Sentinel Network."); - } - } - -//============================================================================== -// End of Interactive Sentinel AI. -//============================================================================== - - if ( ( %msgString $= "" ) || spamAlert( %sender ) ) return; diff --git a/scripts/modscripts/ai/zombie.cs b/scripts/modscripts/ai/zombie.cs new file mode 100644 index 0000000..858aa6e --- /dev/null +++ b/scripts/modscripts/ai/zombie.cs @@ -0,0 +1,1664 @@ +//---------------------------------------------- +// zombie.cs +// Zombie AI Code +//============================================== +function ZcreateLoop(%obj) +{ + if(isObject(%obj)) + { + if(%obj.timedout == 0){ + if((%obj.numZ <= 2 || %obj.numZ $= "") && (ZombieGroup.getCount() < $Host::MaxZombies || $Host::MaxZombies == -1)){ + ZPCreateZombie(%obj); + if(%obj.numZ $= "") + %obj.numZ = 0; + %obj.numZ++; + %obj.timedout = 1; + schedule(10000, %obj, "TimedInF", %obj); + } + } + %obj.ZCLoop = schedule(2000, 0, "ZcreateLoop", %obj); + } +} + +function TimedInF(%obj){ + %obj.timedout = 0; +} + +//this is for when a ZSpawn spawns a zombie +function ZPCreateZombie(%obj){ + %Cpos = vectorAdd(%obj.getposition() ,%obj.getUpvector()); + if(%obj.Ztype $= ""){ + %obj.ZType = 1; + } + if(%obj.ZType == 1){ + %Zombie = new player(){ + Datablock = "ZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Zombie"); + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); + } + else if(%obj.ZType == 2){ + %Zombie = new player(){ + Datablock = "FZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Ravenger Zombie"); + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); + } + else if(%obj.ZType == 3){ + %Zombie = new player(){ + Datablock = "LordZombieArmor"; + }; + applyskin(%zombie,'ZLord',"Zombie Lord"); + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),2.4),"0 0 -2.4"),%obj.getposition()); + %Zombie.mountImage(ZHead, 3); + %Zombie.mountImage(ZBack, 4); + %Zombie.mountImage(ZDummyslotImg, 5); + %Zombie.mountImage(ZDummyslotImg2, 6); + %zombie.firstFired = 0; + %zombie.canmove = 1; + } + else if(%obj.ZType == 4){ + %Zombie = new player(){ + Datablock = "DemonZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Demon Zombie"); + %zombie.mountImage(ZdummyslotImg, 4); + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.3),"0 0 -1.3"),%obj.getposition()); + } + else if(%obj.ZType == 5){ + %Zombie = new player(){ + Datablock = "RapierZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Rapier Zombie"); + %Zombie.mountImage(ZWingImage, 3); + %Zombie.mountImage(ZWingImage2, 4); + %zombie.setActionThread("scoutRoot",true); + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1),"0 0 -0.6"),%obj.getposition()); + } + else if(%obj.ZType == 6){ + %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); + %Zombie = DemonMotherCreate(%Cpos); + } + + %zombie.type = %obj.Ztype; + %Zombie.setTransform(%Cpos); + %Zombie.team = 0; + %zombie.HasCP = 1; + if(%obj.spawnTypeset == 1) + %obj.numZ = 3; + else + %zombie.CP = %obj; + AddToZombieGroup(%Zombie); + if(%obj.ZType != 6) + { + %zombie.canjump = 1; + %zombie.hastarget = 1; + schedule(1000, %zombie, "ZombieLookforTarget", %zombie); + } +} + +//This is for creation of a zombie at a location using the console +function StartAZombie(%pos, %type){ + if(ZombieGroup.getCount >= $Host::MaxZombies && $Host::MaxZombies != -1) + { + error("StartAZombie: Cannot spawn. There are too many zombies on the server."); + return; + } + + if(%Type == 1){ + %Zombie = new player(){ + Datablock = "ZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Zombie"); + } + if(%Type == 2){ + %Zombie = new player(){ + Datablock = "FZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Ravenger Zombie"); + } + if(%Type == 3){ + %Zombie = new player(){ + Datablock = "LordZombieArmor"; + }; + applyskin(%zombie,'ZLord',"Zombie Lord"); + %zombie.client = $zombie::Lclient; + %Zombie.mountImage(ZHead, 3); + %Zombie.mountImage(ZBack, 4); + %Zombie.mountImage(ZDummyslotImg, 5); + %Zombie.mountImage(ZDummyslotImg2, 6); + %zombie.firstFired = 0; + %zombie.canmove = 1; + } + if(%type == 4){ + %Zombie = new player(){ + Datablock = "DemonZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Demon Zombie"); + %zombie.mountImage(ZdummyslotImg, 4); + } + %zombie.type = %type; + %Zombie.setTransform(%pos); + %Zombie.team = 0; + %zombie.canjump = 1; + %zombie.hastarget = 1; + AddToZombieGroup(%Zombie); + schedule(1000, %zombie, "ZombieLookforTarget", %zombie); +} + +//This is for when someone is killed by a zombie and spawns a new one +function CreateZombie(%obj){ + if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) + return; + + %Cpos = %obj.getposition(); + %Zombie = new player(){ + Datablock = "ZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Zombie"); + %Zombie.setTransform(%Cpos); + %zombie.type = 1; + %Zombie.team = 0; + %zombie.canjump = 1; + %zombie.hastarget = 1; + AddToZombieGroup(%Zombie); + schedule(1000, %zombie, "ZombieLookforTarget", %zombie); +} + +function ZombieLookforTarget(%zombie) +{ + if(!isObject(%zombie)) { + return; + } + + if(%Zombie.getState() $= "dead") { + freeClientTarget(%zombie); + return; + } + + %pos = %zombie.getposition(); + %wbpos = %zombie.getworldboxcenter(); + %count = ClientGroup.getCount(); + %closestClient = -1; + %closestDistance = 32767; + for(%i = 0; %i < %count; %i++) + { + %cl = ClientGroup.getObject(%i); + if(isObject(%cl.player)){ + %testPos = %cl.player.getWorldBoxCenter(); + %distance = vectorDist(%wbpos, %testPos); + if (%distance > 0 && %distance < %closestDistance && %cl.player.isFTD != 1 && %cl.player.iszombie != 1) + { + %closestClient = %cl; + %closestDistance = %distance; + } + } + } + if(%closestClient){ + if (%zombie.type == 1) + Zombiemovetotarget(%zombie,%closestClient,%closestDistance); + else if (%zombie.type == 2) + FZombiemovetotarget(%zombie,%closestClient,%closestDistance); + else if (%zombie.type == 3) + LZombiemovetotarget(%zombie,%closestClient,%closestDistance); + else if (%zombie.type == 4) + DZombiemovetotarget(%zombie,%closestClient,%closestDistance); + else if (%zombie.type == 5) + RZombiemovetotarget(%zombie,%closestClient,%closestDistance); + } + %zombie.ZombieTargeting = schedule(500, %zombie, "ZombieLookForTarget", %zombie); +} + +function Zombiemovetotarget(%zombie,%closestClient,%closestDistance){ + %pos = %zombie.getworldboxcenter(); + %closestClient = %closestClient.Player; + if(%closestDistance <= $zombie::detectDist){ + if(%zombie.hastarget != 1){ + %zombie.hastarget = 1; + } + %chance = (getrandom() * 20); + if(%chance >= 19) + ZDoMoan(%zombie); + + %clpos = %closestClient.getPosition(); + %vector = vectorNormalize(vectorSub(%clpos, %pos)); + %v1 = getword(%vector, 0); + %v2 = getword(%vector, 1); + %nv1 = %v2; + %nv2 = (%v1 * -1); + %none = 0; + %vector2 = %nv1@" "@%nv2@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector2)); + + %fmultiplier = $Zombie::ForwardSpeed; + if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1) + %fmultiplier = (%fmultiplier * 4); + %vector = vectorscale(%vector, %Fmultiplier); + %upvec = "150"; + if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1){ + %upvec = %upvec * 2; + %zombie.canjump = 0; + schedule(1500, %zombie, "Zsetjump", %zombie); + } + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + if(%z >= 600) + %upvec = (%upvec * 5); + %vector = %x@" "@%y@" "@%upvec; + %zombie.applyImpulse(%pos, %vector); + } + else if(%zombie.hastarget == 1){ + %zombie.hastarget = 0; + %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); + } +} + +function FZombiemovetotarget(%zombie,%closestClient,%closestDistance){ + %pos = %zombie.getworldboxcenter(); + %closestClient = %closestClient.Player; + if(%closestDistance <= $zombie::detectDist){ + if(%zombie.hastarget != 1){ + %zombie.hastarget = 1; + } + %zombie.setActionThread("scoutRoot",true); + %upvec = "250"; + %fmultiplier = $Zombie::FForwardSpeed; + + //moanStuff + %chance = (getrandom() * 50); + if(%chance >= 49) + ZDoMoan(%zombie); + + //Rotation stuff + %clpos = %closestClient.getPosition(); + %vector = vectorNormalize(vectorSub(%clpos, %pos)); + %v1 = getword(%vector, 0); + %v2 = getword(%vector, 1); + %nv1 = %v2; + %nv2 = (%v1 * -1); + %none = 0; + %vector2 = %nv1@" "@%nv2@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector2)); + + //Move Stuff + if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1 && getword(%vector, 2) <= "0.8" ){ + %zombie.setvelocity("0 0 0"); + %fmultiplier = (%fmultiplier * 2); + %upvec = (%upvec * 3.5); + %zombie.canjump = 0; + schedule(2000, %zombie, "Zsetjump", %zombie); + } + %vector = vectorscale(%vector, %Fmultiplier); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + if(%z >= "1200" && %zombie.canjump == 1){ + %zombie.setvelocity("0 0 0"); + %upvec = (%upvec * 8); + %x = (%x * 0.5); + %y = (%y * 0.5); + %zombie.canjump = 0; + schedule(2500, %zombie, "Zsetjump", %zombie); + } + + %vector = %x@" "@%y@" "@%upvec; + %zombie.applyImpulse(%pos, %vector); + } + else if(%zombie.hastarget == 1){ + %zombie.hastarget = 0; + %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); + %zombie.setActionThread("ski",true); + } +} + +function LZombiemovetotarget(%zombie,%closestClient,%closestDistance){ + %pos = %zombie.getworldboxcenter(); + %closestClient = %closestClient.Player; + if(%closestDistance <= $zombie::detectDist && %zombie.canmove != 0){ + if(%zombie.hastarget != 1){ + LZDoYell(%zombie); + %zombie.hastarget = 1; + } + %chance = (getrandom() * 20); + if(%chance >= 19) + LZDoMoan(%zombie); + + %clpos = %closestClient.getPosition(); + %vector = vectorNormalize(vectorSub(%clpos, %pos)); + %nv2 = (getword(%vector, 0) * -1); + %nv1 = getword(%vector, 1); + %none = 0; + %vector2 = %nv1@" "@%nv2@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector2)); + if(%zombie.ATCount >= 20){ + %zombie.ATCount = 0; + %zombie.nomove = 1; + %zombie.Fire = schedule(1250, %zombie, "ZFire", %zombie, %closestClient); + %zombie.Charge = schedule(500, %zombie, "ChargeEmitter", %zombie); + %zombie.chargecount = 0; + } + if(%zombie.nomove != 1) { + %fmultiplier = $Zombie::LForwardSpeed; + %upvec = "150"; + if(%closestDistance <= $zombie::LKillDist && %zombie.canjump == 1){ + %vec = vectoradd(%pos,vectorScale(%vector,($zombie::LkillDist - 1.6))); + %mask = $TypeMasks::InteriorObjectType | $TypeMasks::StaticShapeObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType | $TypeMasks::TerrainObjectType | $TypeMasks::PlayerObjectType; + %searchResult = containerRayCast(vectoradd(%pos,vectorScale(%vector,1.6)), %vec, %mask, %zombie); + if(%searchResult){ + %searchObj = getWord(%searchResult,0); + if(%searchObj $= %closestClient){ + %chance = getrandom(1,5); + if(%chance == 1){ + %dir = %zombie.getEyeVector(); + %dir = vectornormalize(getword(%dir,0)@" "@getword(%dir,1)@" 0"); + %dir = vectoradd(vectorscale(%dir,7500),"0 0 1000"); + %closestclient.applyimpulse(%clpos,%dir); + %closestclient.damage(0, %clpos, 0.8, $DamageType::ZombieL); + } + else{ + %zombie.setvelocity("0 0 0"); + %zombie.canjump = 0; + schedule(1000, %zombie, "Zsetjump", %zombie); + Llifttarget(%zombie,%closestclient,0); + return; + } + } + } + } + else if(%closestDistance <= ($zombie::LKillDist + $zombie::lungDist)){ + %zombie.setvelocity("0 0 0"); + %fmultiplier = (%fmultiplier * 2.5); + } + %vector = vectorscale(%vector, %Fmultiplier); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + if(%z >= 4000) + %upvec = (%upvec * 5); + %vector = %x@" "@%y@" "@%upvec; + %zombie.applyImpulse(%pos, %vector); + %zombie.ATCount++; + } + } + else if(%zombie.hastarget == 1 && %zombie.canmove != 0){ + %zombie.hastarget = 0; + %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); + } +} + +function DZombiemovetotarget(%zombie,%closestClient,%closestDistance){ + %pos = %zombie.getworldboxcenter(); + %closestClient = %closestClient.Player; + if(%closestDistance <= $zombie::detectDist){ + if(%zombie.hastarget != 1 && %closestdistance >= 10 && %closestdistance <= 150){ + DzombieFire(%zombie,%closestclient); + %zombie.canjump = 0; + schedule(4000, %zombie, "Zsetjump", %zombie); + } + if(%zombie.hastarget != 1){ + LZDoYell(%zombie); + %zombie.hastarget = 1; + } + %chance = (getrandom() * 20); + if(%chance >= 19) + LZDoMoan(%zombie); + + %clpos = %closestClient.getPosition(); + %vector = vectorNormalize(vectorSub(%clpos, %pos)); + %v1 = getword(%vector, 0); + %v2 = getword(%vector, 1); + %nv1 = %v2; + %nv2 = (%v1 * -1); + %none = 0; + %vector2 = %nv1@" "@%nv2@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector2)); + + if (%closestdistance >= 10 && %closestdistance <= 150 && %zombie.canjump == 1){ + DzombieFire(%zombie,%closestclient); + %zombie.canjump = 0; + schedule(4000, %zombie, "Zsetjump", %zombie); + return; + } + %vector = vectorscale(%vector, $Zombie::DForwardSpeed); + %upvec = "150"; + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + if(%z >= ($Zombie::DForwardSpeed / 3 * 2)) + %upvec = (%upvec * 5); + %vector = %x@" "@%y@" "@%upvec; + %zombie.applyImpulse(%pos, %vector); + } + else if(%zombie.hastarget == 1){ + %zombie.hastarget = 0; + %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); + } +} + +function RZombiemovetotarget(%zombie,%closestClient,%closestDistance){ + %pos = %zombie.getworldboxcenter(); + %zombie.setActionThread("scoutRoot",true); + %closestClient = %closestClient.Player; + if(%closestDistance <= $zombie::detectDist){ + if(%zombie.wingset == 1){ + %zombie.wingset = 0; + %Zombie.mountImage(ZWingImage, 3); + %Zombie.mountImage(ZWingImage2, 4); + } + else{ + %zombie.wingset = 1; + %Zombie.mountImage(ZWingaltImage, 3); + %Zombie.mountImage(ZWingaltImage2, 4); + } + %chance = (getrandom() * 20); + if(%chance >= 19) + ZDoMoan(%zombie); + if(%zombie.iscarrying == 1){ + %vector = vectorscale(%zombie.getForwardVector(),($Zombie::RForwardSpeed / 2)); + %vector = getword(%vector, 0)@" "@getword(%vector, 1)@" "@($zombie::Rupvec * 1.5); + %zombie.applyImpulse(%zombie.getposition(), %vector); + return; + } + + %clpos = %closestClient.getWorldBoxCenter(); + %vector = vectorNormalize(vectorSub(%clpos, %pos)); + %v1 = getword(%vector, 0); + %v2 = getword(%vector, 1); + %nv1 = %v2; + %nv2 = (%v1 * -1); + %none = 0; + %vector2 = %nv1@" "@%nv2@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector2)); + + %z = Getword(%vector,2); + %spd = vectorLen(%zombie.getVelocity()); + %fallpoint = 0.05 - (%spd / 630); + if(%closestdistance <= 15 || %z > (0.25 + %fallpoint) || %z < (-1 * (0.25 + %fallpoint))){ + if(%z < 0) + %upvec = ($zombie::Rupvec * (%z - (%spd / 130))); + if(%z >= 0) + %upvec = ($zombie::Rupvec * (%z + 1)); + if(%spd <= 5) + %vector = vectorScale(%vector,3); + } + else{ + %upvec = $zombie::Rupvec * (%z + 1.2); + %spdmod = 1; + } + if(%z < 0) + %z = %z * -1; + + %Zz = getWord(%zombie.getVelocity(),2); + if(%Zz <= -40){ + %result = containerRayCast(%pos, vectoradd(%pos,vectorScale("0 0 1",%Zz * 2)), $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::TerrainObjectType, %zombie); + if(%result) + %upvec = $zombie::Rupvec * 5; + } + + %vector = vectorscale(%vector, ($Zombie::RForwardSpeed * (1 - %z))); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %vector = %x@" "@%y@" "@%upvec; + %zombie.applyImpulse(%pos, %vector); + } +} + +function ZDoMoan(%zombie){ + %chance = (getRandom() * 12); + if(%chance <= 11) + serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); + else + serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); +} + +function LZDoMoan(%zombie){ + serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); +} + +function LZDoYell(%zombie){ + serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); +} + +function Zsetjump(%zombie){ + %zombie.canjump = 1; +} + +function ChargeEmitter(%zombie){ + if(!isobject(%zombie)) + return; + if(%zombie.chargecount >= 2){ + %charge2 = new ParticleEmissionDummy() + { + position = %zombie.getMuzzlePoint(6); + dataBlock = "defaultEmissionDummy"; + emitter = "FlameEmitter"; + }; + MissionCleanup.add(%charge2); + %charge2.schedule(100, "delete"); + } + if(%zombie.chargecount <= 7){ + %charge = new ParticleEmissionDummy() + { + position = %zombie.getMuzzlePoint(5); + dataBlock = "defaultEmissionDummy"; + emitter = "FlameEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(100, "delete"); + } + if(%zombie.chargecount <= 9){ + %zombie.Fire = schedule(100, %zombie, "ChargeEmitter", %zombie); + %zombie.chargecount++; + } + else + %zombie.chargecount = 0; +} + +function ZFire(%zombie, %target){ + if(isobject(%zombie) && isobject(%target)){ + if(%Zombie.firstFired == 1){ + %vec = vectorsub(%target.getworldboxcenter(),%zombie.getMuzzlePoint(6)); + %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); + %zombie.firstFired = 0; + %zombie.nomove = 0; + %p = new TracerProjectile() + { + dataBlock = LZombieAcidBall; + initialDirection = %vec; + initialPosition = %zombie.getMuzzlePoint(6); + sourceObject = %zombie; + sourceSlot = 6; + }; + } + else{ + %vec = vectorsub(%target.getworldboxcenter(),%zombie.getMuzzlePoint(5)); + %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); + %p = new TracerProjectile() + { + dataBlock = LZombieAcidBall; + initialDirection = %vec; + initialPosition = %zombie.getMuzzlePoint(5); + sourceObject = %zombie; + sourceSlot = 5; + }; + %zombie.firstFired = 1; + %zombie.Fire = schedule(250, %zombie, "ZFire", %zombie, %target); + } + } + else{ + %zombie.firstFired = 0; + %zombie.nomove = 0; + } +} + +function Llifttarget(%zombie,%closestclient,%count){ + if(%count == 0) + %zombie.canmove = 0; + if(%closestclient.getState() $= "dead" || %Zombie.getState() $= "dead"){ + %zombie.canmove = 1; + return; + } + %target = %closestclient; + if(!isobject(%target)){ + %zombie.canmove = 1; + return; + } + %pos = %zombie.getworldboxcenter(); + %Tpos = %target.getworldboxcenter(); + %ZtoT = vectorsub(%tpos,%pos); + if (%count <= 12){ + %newpos = vectoradd(%ZtoT,vectoradd(%pos,"0 0 -0.6")); + %target.setTransform(%newpos); + %target.setvelocity("0 0 0"); + } + else { + %killtype = getrandom(1,2); + if(%killtype == 1){ + %closestwall = 20; + %nv2 = (getword(%ZtoT, 0) * -1); + %nv1 = getword(%ZtoT, 1); + %vector1 = vectorscale(vectornormalize(%nv1@" "@%nv2@" 0"),20); + %nvector1 = vectoradd(%tpos,%vector1); + %nv2 = getword(%ZtoT, 0); + %nv1 = (getword(%ZtoT, 1) * -1); + %vector2 = vectorscale(vectornormalize(%nv1@" "@%nv2@" 0"),20); + %nvector2 = vectoradd(%tpos,%vector2); + %searchresultR = containerRayCast(%tpos, %nvector1, $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType); + %searchresultL = containerRayCast(%tpos, %nvector2, $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType); + if(%searchresultR){ + %Hpos = getword(%searchresultR,1)@" "@getword(%searchresultR,2)@" "@getword(%searchresultR,3); + %distance = vectordist(%Tpos, %Hpos); + if(%distance <= %closestwall){ + %closestwall = %distance; + %vector = vectoradd(vectorscale(%vector1,1500),"0 0 100"); + } + } + if(%searchresultL){ + %Hpos = getword(%searchresultL,1)@" "@getword(%searchresultL,2)@" "@getword(%searchresultL,3); + %distance = vectordist(%Tpos, %Hpos); + if(%distance <= %closestwall){ + %closestwall = %distance; + %vector = vectoradd(vectorscale(%vector2,1500),"0 0 100"); + } + } + if(%closestwall == 20){ + %x = getword(%ZtoT, 0); + %y = getword(%ZtoT, 1); + %outvec = vectorscale(vectornormalize(%x@" "@%y@" 0"),50); + %vector = vectoradd("0 0 -15000",%outvec); + } + %target.applyimpulse(%target.getposition(),%vector); + } + else if(%killtype == 2){ + %target.infected = 1; + %target.damage(0, %target.getposition(), 10.0, $DamageType::ZombieL); + } + %count = 0; + %zombie.canmove = 1; + return; + } + %count++; + %zombie.killingplayer = schedule(150, %zombie, "Llifttarget", %zombie, %closestclient, %count); +} + + +function DZombieFire(%zombie,%closestclient){ + %pos = %zombie.getMuzzlePoint(4); + %tpos = %closestclient.getWorldBoxCenter(); + %tvel = %closestclient.getvelocity(); + %vec = vectorsub(%tpos,%pos); + %dist = vectorlen(%vec); + %velpredict = vectorscale(%tvel,(%dist / 50)); + %vector = vectoradd(%vec,%velpredict); + %ndist = vectorlen(%vector); + %upvec = "0 0 "@((%ndist / 50) * (%ndist / 50) * 2); + %vector = vectornormalize(vectoradd(%vector,%upvec)); + %p = new GrenadeProjectile() + { + dataBlock = DemonFireball; + initialDirection = %vector; + initialPosition = %pos; + sourceObject = %zombie; + sourceSlot = 4; + }; +} + +function RkillLoop(%zombie,%target,%count){ + if(!isObject(%zombie)){ + %zombie.iscarrying = 0; + %target.grabbed = 0; + return; + } + if(!isObject(%target)){ + %zombie.iscarrying = 0; + %target.grabbed = 0; + return; + } + if (%Zombie.getState() $= "dead"){ + %zombie.iscarrying = 0; + %target.grabbed = 0; + return; + } + if (%target.getState() $= "dead"){ + %zombie.iscarrying = 0; + %target.grabbed = 0; + return; + } + if(%count == 50){ + %chance = getRandom(1,3); + if(%chance == 3) + %target.damage(0, %tpos, 10.0, $DamageType::Zombie); + else{ + %target.isFTD = 1; + if(%target.getMountedImage($Backpackslot) !$= "") + %target.throwPack(); + %target.finishingfall = schedule(5000, 0, "stopFTD", %target); + } + %zombie.iscarrying = 0; + return; + } + %target.setPosition(vectoradd(%zombie.getPosition(),"0 0 -4")); + %target.setVelocity(%zombie.getVelocity()); + %count++; + %zombie.killingplayer = schedule(100, 0, "RkillLoop", %zombie, %target, %count); +} + +function stopFTD(%target){ + %target.isFTD = 0; + %target.grabbed = 0; +} + +function ZSetRandomMove(%zombie){ + if (!isobject(%zombie)) + return; + %RX = getrandom(-10, 10); + %RY = getrandom(-10, 10); + %RZ = getrandom(); + %vector = %RX@" "@%RY@" "@%RZ; + %zombie.direction = vectornormalize(%vector); + %zombie.Mnum = getrandom(1, 20); + %zombie.zombieRmove = schedule(500, %zombie, "ZrandommoveLoop", %zombie); +} + +function ZrandommoveLoop(%zombie){ + if (!isobject(%zombie)) { + return; + } + + if (%Zombie.getState() $= "dead") { + return; + } + + if (%zombie.hastarget == 1){ + %zombie.direction = ""; + return; + } + if (%zombie.Mnum >= 1){ + %X = getword(%zombie.direction, 1); + %Y = (getword(%zombie.direction, 0) * -1); + %none = 0; + %vector = %X@" "@%Y@" "@%none; + %zombie.setRotation(fullrot("0 0 0",%vector)); + if(%zombie.type == 1) + %speed = ($zombie::forwardspeed); + else if(%zombie.type == 2) + %speed = ($zombie::Fforwardspeed * 0.6); + else if(%zombie.type == 4) + %speed = ($zombie::Dforwardspeed * 0.75); + else if(%zombie.type == 3) + %speed = ($zombie::Lforwardspeed * 0.8); + %vector = vectorscale(%zombie.direction, %speed); + %zombie.applyimpulse(%zombie.getposition(), %vector); + %zombie.Mnum = (%zombie.Mnum - 1); + %zombie.zombieRmove = schedule(500, %zombie, "ZrandommoveLoop", %zombie); + } + else if(%zombie.Mnum == 0) + %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); +} + +function InfectLoop(%obj){ + if(%obj.isSentinel) + return; + + if((%obj.armor $= "Pure") || (%obj.armor $= "Light")) { + return; + } + + if ($Host::NoInfection) + { + %obj.Infected = 0; + cancel(%obj.infectedDamage); + + %obj.infectedDamage = ""; + %obj.beats = 0; + %obj.canZKill = 0; + + cancel(%player.zombieAttackImpulse); + return; + } + + if (%obj.getState() $= "dead") + return; + if(isObject(%obj)){ + if(%obj.beats $= "") + zombieAttackImpulse(%obj,0); + if(%obj.beats < 15) + %obj.setWhiteOut(%obj.beats * 0.05); + else + %obj.setDamageFlash(1); + if(%obj.beats == 15){ + %obj.canZkill = 1; + } + if(%obj.beats >=15) + serverPlay3d("ZombieMoan",%obj.getWorldBoxCenter()); + else if (%obj.beats >= 10) + playDeathCry(%obj); + else + playPain(%obj); + if(%obj.beats == 20){ + if($host::canZombie $= "") + $host::canZombie = 0; + if($host::canZombie == 1) + makePersonZombie(%obj.getTransform(), %obj.client, ZombieGetRandom()); + else + %obj.damage(0, %obj.getposition(), 10.0, $DamageType::Zombie); + return; + } + %obj.beats++; + %obj.infectedDamage = schedule(2000, %obj, "InfectLoop", %obj); + } +} + +function ZkillUpdateScore(%game, %client,%implement){ + if( %implement.getClassName() $= "Turret") + %client = %implement.getControllingClient(); + else if(%implement.getDataBlock().catagory $= "Vehicles") + %client = %implement.getControllingClient(); + %client.Zkills++; + %game.recalcScore(%client); +} + +function zombieSpawnLoop(%pos, %radius, %freq){ + if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) + return; + + if(%freq > 10) + %freq = 10; + if(%freq < 1) + %freq = 1; + %chance = getRandom(1,50); + if(%chance <= %freq && $numspawnedzombies < (%freq * 5)){ + %spawnPos = vectorAdd(%pos,(getRandom(0,%radius) - (%radius / 2))@" "@(getRandom(0,%radius) - (%radius / 2))@" getRandom(0,15)"); + %search = containerRayCast(%spawnPos, vectorAdd(%spawnPos,"0 0 -1000"), $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::TerrainObjectType); + if(%search) + %spawnPos = getWord(%search,1)@" "@getWord(%search,2)@" "@getWord(%search,3); + %chance = getRandom(1,65); + if(%chance <= 25){ + %Zombie = new player(){ + Datablock = "ZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Zombie"); + %Ztype = 1; + } + else if(%chance <= 35){ + %Zombie = new player(){ + Datablock = "FZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Ravenger Zombie"); + %Ztype = 2; + } + else if(%chance <= 40){ + %Zombie = new player(){ + Datablock = "LordZombieArmor"; + }; + applyskin(%zombie,'ZLord',"Zombie Lord"); + %Zombie.mountImage(ZHead, 3); + %Zombie.mountImage(ZBack, 4); + %Zombie.mountImage(ZDummyslotImg, 5); + %Zombie.mountImage(ZDummyslotImg2, 6); + %zombie.firstFired = 0; + %zombie.canmove = 1; + %Ztype = 3; + } + else if(%chance <= 55){ + %Zombie = new player(){ + Datablock = "DemonZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Demon Zombie"); + %zombie.mountImage(ZdummyslotImg, 4); + %Ztype = 4; + } + else if(%chance <= 65){ + %Zombie = new player(){ + Datablock = "RapierZombieArmor"; + }; + applyskin(%zombie,'Zombie',"Rapier Zombie"); + %Zombie.mountImage(ZWingImage, 3); + %Zombie.mountImage(ZWingImage2, 4); + %zombie.setActionThread("scoutRoot",true); + %Ztype = 5; + } + %zombie.type = %Ztype; + %Zombie.setTransform(%spawnPos); + %Zombie.team = 0; + %zombie.canjump = 1; + %zombie.hastarget = 1; + %zombie.randspawnerstarted = 1; + AddToZombieGroup(%Zombie); + schedule(1000, %zombie, "ZombieLookforTarget", %zombie); + $numspawnedzombies++; + } + $zombieloop = schedule(500, 0, "zombieSpawnLoop", %pos, %radius, %freq); +} + +function StopZombieSpawnLoop(){ + cancel($zombieloop); +} + +function ZombieBloodLust(%obj, %count){ + if(!isObject(%obj)) + return; + if (%obj.getState() $= "dead") + return; + %obj.setDamageFlash(0.5); + if(%count == 10){ + serverPlay3d("ZombieMoan",%obj.getWorldBoxCenter()); + %count = 0; + } + %count++; + schedule(200, %obj, "ZombieBloodLust", %obj, %count); +} + +function makePersonZombie(%trans, %client, %special) +{ + %client.player.delete(); + + %client.setWeaponsHudClearAll(); + if(%special == 1) + %data = "ControlLordZombieArmor"; + else if(%special == 2) + %data = "ControlRapierZombieArmor"; + else if(%special == 3) + %data = "ControlDemonZombieArmor"; + else + %data = "ZombieArmor"; + + %player = new Player() { + dataBlock = %data; + }; + + if(%special == 1) + { +// %player.mountImage(ZHead, 3); + %player.mountImage(ZBack, 4); + %player.mountImage(ZDummyslotImg, 5); + %player.mountImage(ZDummyslotImg2, 6); + } + else if(%special == 2) + { + %player.mountImage(ZWingImage, 3); + %player.mountImage(ZWingImage2, 4); + } + + %player.setTransform( %trans ); + AddToZombieGroup(%player); + + // setup some info + %player.setOwnerClient(%client); + %player.team = 0; + %client.outOfBounds = false; + %player.setEnergyLevel(0); + %client.player = %player; + + // updates client's target info for this player + %player.setTarget(%client.target); + setTargetDataBlock(%client.target, %player.getDatablock()); + setTargetSensorData(%client.target, PlayerSensor); + setTargetSensorGroup(%client.target, 1); + %client.setSensorGroup(1); + + %client.setControlObject(%player); + %player.client.clearBackpackIcon(); + + %player.iszombie = 1; + + if(%special == 1) + { + %player.setInventory(LordAcidGun, 1, true); + %player.use("LordAcidGun"); // Eolk - attempt to fix this problem. + } + else if(%special == 2) + RapierCarryCheck(%player); + else if(%special == 3) + { + %player.setInventory(DZShot, 1, true); + %player.use("DZShot"); // Eolk - attempt to fix this problem. + } + + ZombieBloodLust(%player,0); + if(!%special) + zombieAttackImpulse(%player,80); +} + +// This keeps the rapier-human squatting and acting like a real rapier when carrying someone to die. +function RapierCarryCheck(%obj) +{ + if(!isObject(%obj) || %obj.getState() $= "Dead") + return; + + if(%obj.isCarrying == 1) + { + %vector = VectorScale(%obj.getEyeVector(), $Zombie::RForwardSpeed + %obj.getDatablock().mass); + %vector = getword(%vector, 0) SPC getword(%vector, 1) SPC ($Zombie::rupvec * 1.5); + %obj.applyImpulse(%obj.position, %vector); + } + + %obj.setActionThread("scoutroot", 1); + %obj.RImpulse = schedule(500, 0, "RapierCarryCheck", %obj); +} + +function zombieAttackImpulse(%obj, %count){ + if(!isObject(%obj)) { + return; + } + + if (%obj.getState() $= "Dead") { + return; + } + + %pos = %obj.getposition(); + InitContainerRadiusSearch(%pos, %count, $TypeMasks::PlayerObjectType || $TypeMasks::VehicleObjectType); + while ((%objtarget = containerSearchNext()) != 0){ + if(isObject(%objtarget) && %objtarget !$= %obj){ + %objarmortype = %objtarget.getdatablock().getname(); + if(%objarmortype $= "ZombieArmor" || %objarmortype $= "FZombieArmor" || %objarmortype $= "LordZombieArmor" || %objarmortype $= "DemonZombieArmor" || %objarmortype $= "ControlDemonZombieArmor" || %objarmortype $= "RapierZombieArmor" || %objarmortype $= "ControlRapierZombieArmor" || %objarmortype $= "ControlLordZombieArmor") + %objiszomb = 1; + if(!(%objiszomb) && %objtarget.iszombie != 1) { + %vec = vectorNormalize(vectorSub(%objtarget.getWorldBoxCenter(),%obj.getWorldBoxCenter())); + if(vectorDist(%vec,%obj.getForwardVector()) <= 0.5){ + if(%count <= 200){ + %impulse = (%count / 20) * 90; + %up = (%count / 100) * 90; + } + else{ + %impulse = 900; + %up = 180; + } + %vec = vectorScale(%vec,%impulse); + %vec = vectorAdd(%vec,"0 0 "@%up); + %obj.applyimpulse(%obj.getPosition(),%vec); + %count++; + %obj.zombieAttackImpulse = schedule(500, 0, "zombieAttackImpulse", %obj, %count); + return; + } + } + } + %objiszomb = 0; + } + %count++; + %obj.zombieAttackImpulse = schedule(500, 0, "zombieAttackImpulse", %obj, %count); +} + +function AddToZombieGroup(%player) +{ + if(isObject(%player)) + { + %group = nameToID("MissionCleanup/ZombieGroup"); + if(!isObject(%group)) + { + %group = new SimGroup("ZombieGroup"); + MissionCleanup.add(%group); + } + + %group.add(%player); + } +} + +function RemoveFromZombieGroup(%player) +{ + if(isObject(%player)) + { + %group = nameToID("MissionCleanup/ZombieGroup"); + if(!isObject(%group)) + { + %group = new SimGroup("ZombieGroup"); + MissionCleanup.add(%group); + } + + %group.remove(%player); + } +} + +//--------------------------------------------------------------------- +//------------------------DEMON MOTHER STUFF--------------------------- +//--------------------------------------------------------------------- + +datablock SeekerProjectileData(DMMissile) +{ + casingShapeName = "weapon_missile_casement.dts"; + projectileShapeName = "weapon_missile_projectile.dts"; + hasDamageRadius = true; + indirectDamage = 0.5; + damageRadius = 5.0; + radiusDamageType = $DamageType::Zombie; + kickBackStrength = 2000; + + explosion = "MissileExplosion"; + splash = MissileSplash; + velInheritFactor = 1.0; // to compensate for slow starting velocity, this value + // is cranked up to full so the missile doesn't start + // out behind the player when the player is moving + // very quickly - bramage + + baseEmitter = MortarSmokeEmitter; + delayEmitter = MissileFireEmitter; + puffEmitter = MissilePuffEmitter; + bubbleEmitter = GrenadeBubbleEmitter; + bubbleEmitTime = 1.0; + + exhaustEmitter = MissileLauncherExhaustEmitter; + exhaustTimeMs = 300; + exhaustNodeName = "muzzlePoint1"; + + lifetimeMS = 10000; // z0dd - ZOD, 4/14/02. Was 6000 + muzzleVelocity = 10.0; + maxVelocity = 35.0; // z0dd - ZOD, 4/14/02. Was 80.0 + turningSpeed = 23.0; + acceleration = 15.0; + + proximityRadius = 2.5; + + terrainAvoidanceSpeed = 10; + terrainScanAhead = 7; + terrainHeightFail = 1; + terrainAvoidanceRadius = 3; + + flareDistance = 40; + flareAngle = 20; + minSeekHeat = 0.0; + + sound = MissileProjectileSound; + + hasLight = true; + lightRadius = 5.0; + lightColor = "0.2 0.05 0"; + + useFlechette = true; + flechetteDelayMs = 250; + casingDeb = FlechetteDebris; + + explodeOnWaterImpact = false; +}; + +datablock LinearFlareProjectileData(DMPlasma) +{ + doDynamicClientHits = true; + + directDamage = 0; + directDamageType = $DamageType::Zombie; + hasDamageRadius = true; + indirectDamage = 0.8; // z0dd - ZOD, 4/25/02. Was 0.5 + damageRadius = 15.0; + kickBackStrength = 1500; + radiusDamageType = $DamageType::Zombie; + explosion = MortarExplosion; + splash = PlasmaSplash; + + dryVelocity = 85.0; // z0dd - ZOD, 4/25/02. Was 50. Velocity of projectile out of water + wetVelocity = -1; + velInheritFactor = 1.0; + fizzleTimeMS = 4000; + lifetimeMS = 2500; // z0dd - ZOD, 4/25/02. Was 6000 + explodeOnDeath = true; + reflectOnWaterImpactAngle = 0.0; + explodeOnWaterImpact = true; + deflectionOnWaterImpact = 0.0; + fizzleUnderwaterMS = -1; + + activateDelayMS = 100; + + scale = "3.0 3.0 3.0"; + numFlares = 30; + flareColor = "0.1 0.3 1.0"; + flareModTexture = "flaremod"; + flareBaseTexture = "flarebase"; +}; + +function DemonMotherCreate(%pos){ + if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) + { + error("Too many zombies. Cannot create demon mother"); + return; + } + + %obj = new player(){ + Datablock = "DemonMotherZombieArmor"; + }; + %obj.setTransform(%pos); + %obj.team = 0; + MissionCleanup.add(%obj); + AddToZombieGroup(%obj); + schedule(1000, 0, "DemonMotherInitiate", %obj); + + // Eolk - Needs to return %obj now + return %obj; +} + +function DemonMotherInitiate(%obj){ + if(!isObject(%obj)) + return; + DemonMotherDefense(%obj); + DemonMotherThink(%obj); + %obj.mountImage(ZdummyslotImg, 4); + %obj.justshot = 0; + %obj.justmelee = 0; +} + +function DemonMotherThink(%obj){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + %pos = %obj.getposition(); + %count = ClientGroup.getCount(); + %closestClient = -1; + %closestDistance = 32767; + for(%i = 0; %i < %count; %i++) + { + %cl = ClientGroup.getObject(%i); + if(isObject(%cl.player)){ + %testPos = %cl.player.getWorldBoxCenter(); + %distance = vectorDist(%pos, %testPos); + if (%distance > 0 && %distance < %closestDistance && %cl.player.isFTD != 1 && %cl.player.iszombie != 1) + { + %closestClient = %cl; + %closestDistance = %distance; + } + } + } + if(%closestClient != -1){ + %searchobject = %closestclient.player; + %dist = vectorDist(%pos,%searchobject.getPosition()); + if(%dist <= 100){ + if(%dist <= 50){ //ok were now in combat mode, lets decide on what we should do, move attack, or shoot. + if(%obj.justmelee == 1){ //if we just used a melee attack, maybe we should follow it up with a shot attack. + if(%dist >= 10){ //good were far enough away, lets shoot em. + %rand = getrandom(1,3); + if(%rand <= 2) + DemonMotherSpermAttack(%obj,%searchobject); + else + DemonMotherFireRainAttack(%obj,%searchobject); + } + else //damn, to close, ok lung at him + DemonMotherLungAttack(%obj,%searchobject); + } + else{ + %rand = getRandom(1,5); //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. + if(%rand == 1) + DemonMotherPlasmaAttack(%obj,%searchobject); + else if(%rand <= 3) + DemonMotherStrafeAttack(%obj,%searchobject); + else + DemonMotherFlyAttack(%obj,%searchobject); + } + } + else{ //ok, were to far away, maybe we should shoot at them. + if(%obj.justshot == 1) //humm we just attacked, ok, let charge him, get in close + DemonMotherChargeIn(%obj,%searchobject); + else{ //were good to fire, FIRE AWAY! + %rand = getRandom(1,5); //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. + if(%rand == 1) + DemonMotherFireRainAttack(%obj,%searchobject); + else if(%rand <= 3) + DemonMotherMissileAttack(%obj,%searchobject); + else + DemonMotherSpermAttack(%obj,%searchobject); + } + } + } + else if(%dist > 200){ + %rand = getrandom(1,120); + if(%rand == 94) //please, dont ask why i choose this number, it just poped in my head + DemonMotherDemonSpawn(%obj); + else + DemonMotherMoveToTarget(%obj,%searchobject); + } + else + DemonMotherMoveToTarget(%obj,%searchobject); + + %obj.justshot = 0; + %obj.justmelee = 0; + } + else{ + schedule(500, 0, "DemonMotherThink", %obj); + } +} + +function DemonMotherDefense(%obj){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + %pos = %obj.getposition(); + InitContainerRadiusSearch(%pos, 250, $TypeMasks::ProjectileObjectType); + while ((%searchObject = containerSearchNext()) != 0){ + %projpos = %searchobject.getPosition(); + %dist = vectorDist(%pos,%projpos); + if(%dist <= 100){ + if(%searchobject.lastpos) + %searchobject.delete(); + } + else + %searchobject.lastpos = %projpos; + } + schedule(50, "DemonMotherDefense", %obj); +} + +function DemonMotherSpermAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(!isObject(%target)){ + DemonMotherThink(%obj); + return; + } + FaceTarget(%obj,%target); + if(%obj.chargecount $= "") + %obj.chargecount = 0; + %charge = new ParticleEmissionDummy() + { + position = %obj.getMuzzlePoint(4); + dataBlock = "defaultEmissionDummy"; + emitter = "FlameEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(100, "delete"); + + if(%obj.chargecount == 7){ + %vec = vectorsub(%target.getworldboxcenter(),%obj.getMuzzlePoint(4)); + %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); + %p = new TracerProjectile() + { + dataBlock = LZombieAcidBall; + initialDirection = %vec; + initialPosition = %obj.getMuzzlePoint(4); + sourceObject = %obj; + sourceSlot = 6; + }; + } + if(%obj.chargecount == 9){ + %vec = vectorsub(%target.getworldboxcenter(),%obj.getMuzzlePoint(4)); + %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); + %p = new TracerProjectile() + { + dataBlock = LZombieAcidBall; + initialDirection = %vec; + initialPosition = %obj.getMuzzlePoint(4); + sourceObject = %obj; + sourceSlot = 6; + }; + } + + if(%obj.chargecount <= 9){ + schedule(100, 0, "DemonMotherSpermAttack", %obj, %target); + %obj.chargecount++; + } + else{ + %obj.chargecount = 0; + %obj.justshot = 1; + DemonMotherThink(%obj); + } +} + +function DemonMotherLungAttack(%obj,%target){ + FaceTarget(%obj,%target); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); + %vector = vectorscale(%vector, 4000); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + %vector = %x@" "@%y@" 400"; + %obj.applyImpulse(%obj.getPosition(), %vector); + + %obj.justmelee = 1; + schedule(750, 0, "DemonMotherThink", %obj); +} + +function DemonMotherStrafeAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount <= 8){ + %obj.setVelocity("0 0 0"); + FaceTarget(%obj,%target); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); + %vector = vectorscale(%vector, 3250); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %nv1 = %y; + %nv2 = (%x * -1); + %vector = %nv1@" "@%nv2@" 0"; + %obj.applyImpulse(%obj.getPosition(), %vector); + } + else if(%obj.chargecount <= 11){ + %obj.setvelocity("0 0 0"); + FaceTarget(%obj,%target); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); + %vector = vectorscale(%vector, 4500); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + %vector = %x@" "@%y@" 150"; + %obj.applyImpulse(%obj.getPosition(), %vector); + } + else{ + %obj.chargecount = 0; + %obj.justmelee = 1; + schedule(250, 0, "DemonMotherThink", %obj); + return; + } + schedule(250, 0, "DemonMotherStrafeAttack", %obj, %target); + %obj.chargecount++; +} + +function DemonMotherFlyAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount <= 9){ + FaceTarget(%obj,%target); + %obj.setvelocity("0 0 10"); + %obj.chargecount++; + schedule(100, 0, "DemonMotherFlyAttack",%obj,%target); + } + else if(%obj.chargecount == 10){ + FaceTarget(%obj,%target); + %obj.setvelocity("0 0 5"); + %vector = vectorSub(%target.getPosition(),%obj.getPosition()); + %nVec = vectorNormalize(%vector); + %vector = vectorAdd(%vector,vectorscale(%nvec,-4)); + %obj.attackpos = vectorAdd(%obj.getPosition(),%vector); + %obj.attackdir = %nVec; +// echo(%obj.getPosition() SPC %target.getPosition() SPC %obj.attackpos SPC %obj.attackdir); + %obj.startFade(400, 0, true); + %obj.chargecount++; + schedule(400, 0, "DemonMotherFlyAttack",%obj,%target); + } + else if(%obj.chargecount >= 11){ + %obj.startFade(500, 0, false); + %obj.setPosition(%obj.attackpos); + %obj.setvelocity(vectorscale(%obj.attackdir,25)); + %obj.justmelee = 1; + %obj.chargecount = 0; +// echo(%obj.getPosition() SPC %target.getPosition() SPC %obj.attackpos SPC %obj.attackdir); + %obj.attackpos = ""; + %obj.attackdir = ""; + schedule(1000, 0, "DemonMotherThink",%obj); + } +} + +function DemonMotherFireRainAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount == 0){ + FaceTarget(%obj, %target); + for(%i = 0; %i < 10; %i++){ + %pos = %obj.getPosition(); + %x = getRandom(0,10) - 5; + %y = getRandom(0,10) - 5; + %vec = vectorAdd(%pos,%x SPC %y SPC "5"); + %searchResult = containerRayCast(%vec, vectorAdd(%vec,"0 0 -10"), $TypeMasks::TerrainObjectType, %obj); + + %charge = new ParticleEmissionDummy() + { + position = posFromRaycast(%searchresult); + dataBlock = "defaultEmissionDummy"; + emitter = "FlameEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(1500, "delete"); + } + %obj.chargecount++; + schedule(1000, 0, "DemonMotherFireRainAttack",%obj,%target); + } + else{ + %x = (getRandom() * 2) - 1; + %y = (getRandom() * 2) - 1; + %z = getRandom(); + %vec = vectorNormalize(%x SPC %y SPC %z); + %pos = vectorAdd(%target.getPosition(),vectorScale(%vec, 20)); + for(%i = 0;%i < 10;%i++){ + %x = getRandom(0,14) - 7; + %y = getRandom(0,14) - 7; + %spwpos = vectorAdd(%pos,%x SPC %y SPC "2"); + %p = new GrenadeProjectile() + { + dataBlock = DemonFireball; + initialDirection = vectorScale(%vec,-1); + initialPosition = %spwpos; + sourceObject = %obj; + sourceSlot = 4; + }; + } + %obj.justshot = 1; + %obj.chargecount = 0; + schedule(1000, 0, "DemonMotherThink",%obj); + } +} + +function DemonMotherMissileAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount == 0){ + %obj.chargecount++; + schedule(1000, 0, "DemonMotherMissileAttack", %obj, %target); + } + else{ + %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); + %p = new SeekerProjectile() + { + dataBlock = DMMissile; + initialDirection = %vec; + initialPosition = %obj.getMuzzlePoint(4); + sourceObject = %obj; + sourceSlot = 4; + }; + %beacon = new BeaconObject() { + dataBlock = "SubBeacon"; + beaconType = "vehicle"; + position = %target.getWorldBoxCenter(); + }; + %beacon.team = 0; + %beacon.setTarget(0); + MissionCleanup.add(%beacon); + %p.setObjectTarget(%beacon); + DemonMotherMissileFollow(%target,%beacon,%p); + + %obj.justshot = 1; + %obj.chargecount = 0; + schedule(1000, 0, "DemonMotherThink", %obj); + } +} + +function DemonMotherMissileFollow(%target,%beacon,%missile){ + if(!isObject(%target)){ + %beacon.delete(); + return; + } + if(!isObject(%missile)){ + %beacon.delete(); + return; + } + %beacon.setPosition(%target.getWorldBoxCenter()); + schedule(100, 0, "DemonMotherMissileFollow", %target, %beacon, %missile); +} + +function DemonMotherPlasmaAttack(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount <= 9){ + %obj.setVelocity("0 0 10"); + %obj.chargecount++; + schedule(100, 0, "DemonMotherPlasmaAttack", %obj, %target); + } + else{ + %obj.setVelocity("0 0 3"); + %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); + %p = new LinearFlareProjectile() + { + dataBlock = DMPlasma; + initialDirection = %vec; + initialPosition = %obj.getMuzzlePoint(4); + sourceObject = %obj; + sourceSlot = 4; + }; + %obj.chargecount = 0; + %obj.justshot = 1; + schedule(1000, 0, "DemonMotherThink", %obj); + } +} + +function DemonMotherChargeIn(%obj,%target){ + if(!isObject(%obj)) + return; + if(%obj.getState() $= "dead") + return; + if(%obj.chargecount $= "") + %obj.chargecount = 0; + if(%obj.chargecount <= 4){ + FaceTarget(%obj, %target); + %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); + %obj.setvelocity(vectorScale(%vec,50)); + %obj.chargecount++; + schedule(500, 0, "DemonMotherChargeIn", %obj, %target); + } + else{ + %obj.justmelee = 1; + %obj.chargecount = 0; + DemonMotherThink(%obj); + } +} + +function DemonMotherMoveToTarget(%obj,%target){ + FaceTarget(%obj,%target); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); + %vector = vectorscale(%vector, 1200); + %x = Getword(%vector,0); + %y = Getword(%vector,1); + %z = Getword(%vector,2); + %vector = %x@" "@%y@" 150"; + %obj.applyImpulse(%obj.getPosition(), %vector); + + schedule(500, 0, "DemonMotherThink", %obj); +} + +function DemonMotherDemonSpawn(%obj){ + for(%i = 0; %i < 5; %i++){ + %pos = %obj.getPosition(); + %x = getRandom(0,200) - 100; + %y = getRandom(0,200) - 100; + %vec = vectorAdd(%pos,%x SPC %y SPC "40"); + %searchResult = containerRayCast(%vec, vectorAdd(%vec,"0 0 -80"), $TypeMasks::TerrainObjectType, %obj); + + %charge = new ParticleEmissionDummy() + { + position = posFromRaycast(%searchresult); + dataBlock = "defaultEmissionDummy"; + emitter = "FlameEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(1100, "delete"); + schedule(1000, 0, "startAzombie", posFromRaycast(%searchresult), 4); + } + schedule(1500, 0, "DemonMotherThink", %obj); +} + +function FaceTarget(%obj,%target){ + %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); + %v1 = getword(%vector, 0); + %v2 = getword(%vector, 1); + %nv1 = %v2; + %nv2 = (%v1 * -1); + %vector2 = %nv1@" "@%nv2@" 0"; + %obj.setRotation(fullrot("0 0 0",%vector2)); +} diff --git a/scripts/modscripts/chatcommands/admin.cs b/scripts/modscripts/chatcommands/admin.cs index 0428024..6f1eeda 100644 --- a/scripts/modscripts/chatcommands/admin.cs +++ b/scripts/modscripts/chatcommands/admin.cs @@ -687,14 +687,17 @@ function ccLoadBuilding(%sender, %args) } // Blnukem -function ccTurrets(%sender) { +function ccTurrets(%sender) +{ if (!%sender.isAdmin) return; - if ($TurretEnableOverride) { + if ($TurretEnableOverride) + { $TurretEnableOverride = 0; messageAll('MsgAdminForce', "\c3"@%sender.nameBase@"\c2 has disabled turrets."); } - else { + else + { $TurretEnableOverride = 1; messageAll('MsgAdminForce', "\c3"@%sender.nameBase@"\c2 has enabled turrets."); } @@ -702,7 +705,8 @@ if (!%sender.isAdmin) } // Blnukem -function ccBuySCG(%sender) { +function ccBuySCG(%sender) +{ if (!%sender.isAdmin) return; diff --git a/scripts/modscripts/chatcommands/zombie.cs b/scripts/modscripts/chatcommands/zombie.cs index 3242471..3da6e12 100644 --- a/scripts/modscripts/chatcommands/zombie.cs +++ b/scripts/modscripts/chatcommands/zombie.cs @@ -261,7 +261,7 @@ function ccKillZombies(%sender) logEcho(%sender.nameBase@" ("@%sender@") killed all zombies and cured all infected people"); %zgroup = nameToID("MissionCleanup/ZombieGroup"); %zcount = %zgroup.getCount(); - for (%i = 0; %i < %zcount; %i++) + for (%i = %zcount; %i > 0; %i--) { %zombie = %zgroup.getObject(%i); if (isObject(%zombie)) diff --git a/scripts/pack.cs b/scripts/pack.cs index e81285c..a81c516 100644 --- a/scripts/pack.cs +++ b/scripts/pack.cs @@ -129,3 +129,6 @@ exec("scripts/packs/artillerybarrelpack.cs"); exec("scripts/packs/generator.cs"); exec("scripts/packs/solarpanel.cs"); exec("scripts/packs/switch.cs"); + +// --- Misc +exec("scripts/packs/waypointpack.cs"); diff --git a/scripts/packs/ZSpawnpack.cs b/scripts/packs/ZSpawnpack.cs index 9c366a6..dcb8e9d 100644 --- a/scripts/packs/ZSpawnpack.cs +++ b/scripts/packs/ZSpawnpack.cs @@ -275,1664 +275,3 @@ function DeployedZSpawnBase::onLosePowerDisabled(%data,%obj) { Cancel(%obj.ZCLoop); Parent::onLosePowerDisabled(%data,%obj); } - -function ZcreateLoop(%obj) -{ - if(isObject(%obj)) - { - if(%obj.timedout == 0){ - if((%obj.numZ <= 2 || %obj.numZ $= "") && (ZombieGroup.getCount() < $Host::MaxZombies || $Host::MaxZombies == -1)){ - ZPCreateZombie(%obj); - if(%obj.numZ $= "") - %obj.numZ = 0; - %obj.numZ++; - %obj.timedout = 1; - schedule(10000, %obj, "TimedInF", %obj); - } - } - %obj.ZCLoop = schedule(2000, 0, "ZcreateLoop", %obj); - } -} - -function TimedInF(%obj){ - %obj.timedout = 0; -} - -//this is for when a ZSpawn spawns a zombie -function ZPCreateZombie(%obj){ - %Cpos = vectorAdd(%obj.getposition() ,%obj.getUpvector()); - if(%obj.Ztype $= ""){ - %obj.ZType = 1; - } - if(%obj.ZType == 1){ - %Zombie = new player(){ - Datablock = "ZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Zombie"); - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); - } - else if(%obj.ZType == 2){ - %Zombie = new player(){ - Datablock = "FZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Ravenger Zombie"); - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); - } - else if(%obj.ZType == 3){ - %Zombie = new player(){ - Datablock = "LordZombieArmor"; - }; - applyskin(%zombie,'ZLord',"Zombie Lord"); - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),2.4),"0 0 -2.4"),%obj.getposition()); - %Zombie.mountImage(ZHead, 3); - %Zombie.mountImage(ZBack, 4); - %Zombie.mountImage(ZDummyslotImg, 5); - %Zombie.mountImage(ZDummyslotImg2, 6); - %zombie.firstFired = 0; - %zombie.canmove = 1; - } - else if(%obj.ZType == 4){ - %Zombie = new player(){ - Datablock = "DemonZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Demon Zombie"); - %zombie.mountImage(ZdummyslotImg, 4); - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.3),"0 0 -1.3"),%obj.getposition()); - } - else if(%obj.ZType == 5){ - %Zombie = new player(){ - Datablock = "RapierZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Rapier Zombie"); - %Zombie.mountImage(ZWingImage, 3); - %Zombie.mountImage(ZWingImage2, 4); - %zombie.setActionThread("scoutRoot",true); - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1),"0 0 -0.6"),%obj.getposition()); - } - else if(%obj.ZType == 6){ - %Cpos = vectoradd(vectoradd(vectorscale(%obj.getUpvector(),1.15),"0 0 -1.15"),%obj.getposition()); - %Zombie = DemonMotherCreate(%Cpos); - } - - %zombie.type = %obj.Ztype; - %Zombie.setTransform(%Cpos); - %Zombie.team = 0; - %zombie.HasCP = 1; - if(%obj.spawnTypeset == 1) - %obj.numZ = 3; - else - %zombie.CP = %obj; - AddToZombieGroup(%Zombie); - if(%obj.ZType != 6) - { - %zombie.canjump = 1; - %zombie.hastarget = 1; - schedule(1000, %zombie, "ZombieLookforTarget", %zombie); - } -} - -//This is for creation of a zombie at a location using the console -function StartAZombie(%pos, %type){ - if(ZombieGroup.getCount >= $Host::MaxZombies && $Host::MaxZombies != -1) - { - error("StartAZombie: Cannot spawn. There are too many zombies on the server."); - return; - } - - if(%Type == 1){ - %Zombie = new player(){ - Datablock = "ZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Zombie"); - } - if(%Type == 2){ - %Zombie = new player(){ - Datablock = "FZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Ravenger Zombie"); - } - if(%Type == 3){ - %Zombie = new player(){ - Datablock = "LordZombieArmor"; - }; - applyskin(%zombie,'ZLord',"Zombie Lord"); - %zombie.client = $zombie::Lclient; - %Zombie.mountImage(ZHead, 3); - %Zombie.mountImage(ZBack, 4); - %Zombie.mountImage(ZDummyslotImg, 5); - %Zombie.mountImage(ZDummyslotImg2, 6); - %zombie.firstFired = 0; - %zombie.canmove = 1; - } - if(%type == 4){ - %Zombie = new player(){ - Datablock = "DemonZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Demon Zombie"); - %zombie.mountImage(ZdummyslotImg, 4); - } - %zombie.type = %type; - %Zombie.setTransform(%pos); - %Zombie.team = 0; - %zombie.canjump = 1; - %zombie.hastarget = 1; - AddToZombieGroup(%Zombie); - schedule(1000, %zombie, "ZombieLookforTarget", %zombie); -} - -//This is for when someone is killed by a zombie and spawns a new one -function CreateZombie(%obj){ - if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) - return; - - %Cpos = %obj.getposition(); - %Zombie = new player(){ - Datablock = "ZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Zombie"); - %Zombie.setTransform(%Cpos); - %zombie.type = 1; - %Zombie.team = 0; - %zombie.canjump = 1; - %zombie.hastarget = 1; - AddToZombieGroup(%Zombie); - schedule(1000, %zombie, "ZombieLookforTarget", %zombie); -} - -function ZombieLookforTarget(%zombie) -{ - if(!isObject(%zombie)) { - return; - } - - if(%Zombie.getState() $= "dead") { - freeClientTarget(%zombie); - return; - } - - %pos = %zombie.getposition(); - %wbpos = %zombie.getworldboxcenter(); - %count = ClientGroup.getCount(); - %closestClient = -1; - %closestDistance = 32767; - for(%i = 0; %i < %count; %i++) - { - %cl = ClientGroup.getObject(%i); - if(isObject(%cl.player)){ - %testPos = %cl.player.getWorldBoxCenter(); - %distance = vectorDist(%wbpos, %testPos); - if (%distance > 0 && %distance < %closestDistance && %cl.player.isFTD != 1 && %cl.player.iszombie != 1) - { - %closestClient = %cl; - %closestDistance = %distance; - } - } - } - if(%closestClient){ - if (%zombie.type == 1) - Zombiemovetotarget(%zombie,%closestClient,%closestDistance); - else if (%zombie.type == 2) - FZombiemovetotarget(%zombie,%closestClient,%closestDistance); - else if (%zombie.type == 3) - LZombiemovetotarget(%zombie,%closestClient,%closestDistance); - else if (%zombie.type == 4) - DZombiemovetotarget(%zombie,%closestClient,%closestDistance); - else if (%zombie.type == 5) - RZombiemovetotarget(%zombie,%closestClient,%closestDistance); - } - %zombie.ZombieTargeting = schedule(500, %zombie, "ZombieLookForTarget", %zombie); -} - -function Zombiemovetotarget(%zombie,%closestClient,%closestDistance){ - %pos = %zombie.getworldboxcenter(); - %closestClient = %closestClient.Player; - if(%closestDistance <= $zombie::detectDist){ - if(%zombie.hastarget != 1){ - %zombie.hastarget = 1; - } - %chance = (getrandom() * 20); - if(%chance >= 19) - ZDoMoan(%zombie); - - %clpos = %closestClient.getPosition(); - %vector = vectorNormalize(vectorSub(%clpos, %pos)); - %v1 = getword(%vector, 0); - %v2 = getword(%vector, 1); - %nv1 = %v2; - %nv2 = (%v1 * -1); - %none = 0; - %vector2 = %nv1@" "@%nv2@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector2)); - - %fmultiplier = $Zombie::ForwardSpeed; - if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1) - %fmultiplier = (%fmultiplier * 4); - %vector = vectorscale(%vector, %Fmultiplier); - %upvec = "150"; - if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1){ - %upvec = %upvec * 2; - %zombie.canjump = 0; - schedule(1500, %zombie, "Zsetjump", %zombie); - } - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - if(%z >= 600) - %upvec = (%upvec * 5); - %vector = %x@" "@%y@" "@%upvec; - %zombie.applyImpulse(%pos, %vector); - } - else if(%zombie.hastarget == 1){ - %zombie.hastarget = 0; - %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); - } -} - -function FZombiemovetotarget(%zombie,%closestClient,%closestDistance){ - %pos = %zombie.getworldboxcenter(); - %closestClient = %closestClient.Player; - if(%closestDistance <= $zombie::detectDist){ - if(%zombie.hastarget != 1){ - %zombie.hastarget = 1; - } - %zombie.setActionThread("scoutRoot",true); - %upvec = "250"; - %fmultiplier = $Zombie::FForwardSpeed; - - //moanStuff - %chance = (getrandom() * 50); - if(%chance >= 49) - ZDoMoan(%zombie); - - //Rotation stuff - %clpos = %closestClient.getPosition(); - %vector = vectorNormalize(vectorSub(%clpos, %pos)); - %v1 = getword(%vector, 0); - %v2 = getword(%vector, 1); - %nv1 = %v2; - %nv2 = (%v1 * -1); - %none = 0; - %vector2 = %nv1@" "@%nv2@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector2)); - - //Move Stuff - if(%closestDistance <= $zombie::lungDist && %zombie.canjump == 1 && getword(%vector, 2) <= "0.8" ){ - %zombie.setvelocity("0 0 0"); - %fmultiplier = (%fmultiplier * 2); - %upvec = (%upvec * 3.5); - %zombie.canjump = 0; - schedule(2000, %zombie, "Zsetjump", %zombie); - } - %vector = vectorscale(%vector, %Fmultiplier); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - if(%z >= "1200" && %zombie.canjump == 1){ - %zombie.setvelocity("0 0 0"); - %upvec = (%upvec * 8); - %x = (%x * 0.5); - %y = (%y * 0.5); - %zombie.canjump = 0; - schedule(2500, %zombie, "Zsetjump", %zombie); - } - - %vector = %x@" "@%y@" "@%upvec; - %zombie.applyImpulse(%pos, %vector); - } - else if(%zombie.hastarget == 1){ - %zombie.hastarget = 0; - %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); - %zombie.setActionThread("ski",true); - } -} - -function LZombiemovetotarget(%zombie,%closestClient,%closestDistance){ - %pos = %zombie.getworldboxcenter(); - %closestClient = %closestClient.Player; - if(%closestDistance <= $zombie::detectDist && %zombie.canmove != 0){ - if(%zombie.hastarget != 1){ - LZDoYell(%zombie); - %zombie.hastarget = 1; - } - %chance = (getrandom() * 20); - if(%chance >= 19) - LZDoMoan(%zombie); - - %clpos = %closestClient.getPosition(); - %vector = vectorNormalize(vectorSub(%clpos, %pos)); - %nv2 = (getword(%vector, 0) * -1); - %nv1 = getword(%vector, 1); - %none = 0; - %vector2 = %nv1@" "@%nv2@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector2)); - if(%zombie.ATCount >= 20){ - %zombie.ATCount = 0; - %zombie.nomove = 1; - %zombie.Fire = schedule(1250, %zombie, "ZFire", %zombie, %closestClient); - %zombie.Charge = schedule(500, %zombie, "ChargeEmitter", %zombie); - %zombie.chargecount = 0; - } - if(%zombie.nomove != 1) { - %fmultiplier = $Zombie::LForwardSpeed; - %upvec = "150"; - if(%closestDistance <= $zombie::LKillDist && %zombie.canjump == 1){ - %vec = vectoradd(%pos,vectorScale(%vector,($zombie::LkillDist - 1.6))); - %mask = $TypeMasks::InteriorObjectType | $TypeMasks::StaticShapeObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType | $TypeMasks::TerrainObjectType | $TypeMasks::PlayerObjectType; - %searchResult = containerRayCast(vectoradd(%pos,vectorScale(%vector,1.6)), %vec, %mask, %zombie); - if(%searchResult){ - %searchObj = getWord(%searchResult,0); - if(%searchObj $= %closestClient){ - %chance = getrandom(1,5); - if(%chance == 1){ - %dir = %zombie.getEyeVector(); - %dir = vectornormalize(getword(%dir,0)@" "@getword(%dir,1)@" 0"); - %dir = vectoradd(vectorscale(%dir,7500),"0 0 1000"); - %closestclient.applyimpulse(%clpos,%dir); - %closestclient.damage(0, %clpos, 0.8, $DamageType::ZombieL); - } - else{ - %zombie.setvelocity("0 0 0"); - %zombie.canjump = 0; - schedule(1000, %zombie, "Zsetjump", %zombie); - Llifttarget(%zombie,%closestclient,0); - return; - } - } - } - } - else if(%closestDistance <= ($zombie::LKillDist + $zombie::lungDist)){ - %zombie.setvelocity("0 0 0"); - %fmultiplier = (%fmultiplier * 2.5); - } - %vector = vectorscale(%vector, %Fmultiplier); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - if(%z >= 4000) - %upvec = (%upvec * 5); - %vector = %x@" "@%y@" "@%upvec; - %zombie.applyImpulse(%pos, %vector); - %zombie.ATCount++; - } - } - else if(%zombie.hastarget == 1 && %zombie.canmove != 0){ - %zombie.hastarget = 0; - %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); - } -} - -function DZombiemovetotarget(%zombie,%closestClient,%closestDistance){ - %pos = %zombie.getworldboxcenter(); - %closestClient = %closestClient.Player; - if(%closestDistance <= $zombie::detectDist){ - if(%zombie.hastarget != 1 && %closestdistance >= 10 && %closestdistance <= 150){ - DzombieFire(%zombie,%closestclient); - %zombie.canjump = 0; - schedule(4000, %zombie, "Zsetjump", %zombie); - } - if(%zombie.hastarget != 1){ - LZDoYell(%zombie); - %zombie.hastarget = 1; - } - %chance = (getrandom() * 20); - if(%chance >= 19) - LZDoMoan(%zombie); - - %clpos = %closestClient.getPosition(); - %vector = vectorNormalize(vectorSub(%clpos, %pos)); - %v1 = getword(%vector, 0); - %v2 = getword(%vector, 1); - %nv1 = %v2; - %nv2 = (%v1 * -1); - %none = 0; - %vector2 = %nv1@" "@%nv2@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector2)); - - if (%closestdistance >= 10 && %closestdistance <= 150 && %zombie.canjump == 1){ - DzombieFire(%zombie,%closestclient); - %zombie.canjump = 0; - schedule(4000, %zombie, "Zsetjump", %zombie); - return; - } - %vector = vectorscale(%vector, $Zombie::DForwardSpeed); - %upvec = "150"; - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - if(%z >= ($Zombie::DForwardSpeed / 3 * 2)) - %upvec = (%upvec * 5); - %vector = %x@" "@%y@" "@%upvec; - %zombie.applyImpulse(%pos, %vector); - } - else if(%zombie.hastarget == 1){ - %zombie.hastarget = 0; - %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); - } -} - -function RZombiemovetotarget(%zombie,%closestClient,%closestDistance){ - %pos = %zombie.getworldboxcenter(); - %zombie.setActionThread("scoutRoot",true); - %closestClient = %closestClient.Player; - if(%closestDistance <= $zombie::detectDist){ - if(%zombie.wingset == 1){ - %zombie.wingset = 0; - %Zombie.mountImage(ZWingImage, 3); - %Zombie.mountImage(ZWingImage2, 4); - } - else{ - %zombie.wingset = 1; - %Zombie.mountImage(ZWingaltImage, 3); - %Zombie.mountImage(ZWingaltImage2, 4); - } - %chance = (getrandom() * 20); - if(%chance >= 19) - ZDoMoan(%zombie); - if(%zombie.iscarrying == 1){ - %vector = vectorscale(%zombie.getForwardVector(),($Zombie::RForwardSpeed / 2)); - %vector = getword(%vector, 0)@" "@getword(%vector, 1)@" "@($zombie::Rupvec * 1.5); - %zombie.applyImpulse(%zombie.getposition(), %vector); - return; - } - - %clpos = %closestClient.getWorldBoxCenter(); - %vector = vectorNormalize(vectorSub(%clpos, %pos)); - %v1 = getword(%vector, 0); - %v2 = getword(%vector, 1); - %nv1 = %v2; - %nv2 = (%v1 * -1); - %none = 0; - %vector2 = %nv1@" "@%nv2@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector2)); - - %z = Getword(%vector,2); - %spd = vectorLen(%zombie.getVelocity()); - %fallpoint = 0.05 - (%spd / 630); - if(%closestdistance <= 15 || %z > (0.25 + %fallpoint) || %z < (-1 * (0.25 + %fallpoint))){ - if(%z < 0) - %upvec = ($zombie::Rupvec * (%z - (%spd / 130))); - if(%z >= 0) - %upvec = ($zombie::Rupvec * (%z + 1)); - if(%spd <= 5) - %vector = vectorScale(%vector,3); - } - else{ - %upvec = $zombie::Rupvec * (%z + 1.2); - %spdmod = 1; - } - if(%z < 0) - %z = %z * -1; - - %Zz = getWord(%zombie.getVelocity(),2); - if(%Zz <= -40){ - %result = containerRayCast(%pos, vectoradd(%pos,vectorScale("0 0 1",%Zz * 2)), $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::TerrainObjectType, %zombie); - if(%result) - %upvec = $zombie::Rupvec * 5; - } - - %vector = vectorscale(%vector, ($Zombie::RForwardSpeed * (1 - %z))); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %vector = %x@" "@%y@" "@%upvec; - %zombie.applyImpulse(%pos, %vector); - } -} - -function ZDoMoan(%zombie){ - %chance = (getRandom() * 12); - if(%chance <= 11) - serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); - else - serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); -} - -function LZDoMoan(%zombie){ - serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); -} - -function LZDoYell(%zombie){ - serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); -} - -function Zsetjump(%zombie){ - %zombie.canjump = 1; -} - -function ChargeEmitter(%zombie){ - if(!isobject(%zombie)) - return; - if(%zombie.chargecount >= 2){ - %charge2 = new ParticleEmissionDummy() - { - position = %zombie.getMuzzlePoint(6); - dataBlock = "defaultEmissionDummy"; - emitter = "FlameEmitter"; - }; - MissionCleanup.add(%charge2); - %charge2.schedule(100, "delete"); - } - if(%zombie.chargecount <= 7){ - %charge = new ParticleEmissionDummy() - { - position = %zombie.getMuzzlePoint(5); - dataBlock = "defaultEmissionDummy"; - emitter = "FlameEmitter"; - }; - MissionCleanup.add(%charge); - %charge.schedule(100, "delete"); - } - if(%zombie.chargecount <= 9){ - %zombie.Fire = schedule(100, %zombie, "ChargeEmitter", %zombie); - %zombie.chargecount++; - } - else - %zombie.chargecount = 0; -} - -function ZFire(%zombie, %target){ - if(isobject(%zombie) && isobject(%target)){ - if(%Zombie.firstFired == 1){ - %vec = vectorsub(%target.getworldboxcenter(),%zombie.getMuzzlePoint(6)); - %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); - %zombie.firstFired = 0; - %zombie.nomove = 0; - %p = new TracerProjectile() - { - dataBlock = LZombieAcidBall; - initialDirection = %vec; - initialPosition = %zombie.getMuzzlePoint(6); - sourceObject = %zombie; - sourceSlot = 6; - }; - } - else{ - %vec = vectorsub(%target.getworldboxcenter(),%zombie.getMuzzlePoint(5)); - %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); - %p = new TracerProjectile() - { - dataBlock = LZombieAcidBall; - initialDirection = %vec; - initialPosition = %zombie.getMuzzlePoint(5); - sourceObject = %zombie; - sourceSlot = 5; - }; - %zombie.firstFired = 1; - %zombie.Fire = schedule(250, %zombie, "ZFire", %zombie, %target); - } - } - else{ - %zombie.firstFired = 0; - %zombie.nomove = 0; - } -} - -function Llifttarget(%zombie,%closestclient,%count){ - if(%count == 0) - %zombie.canmove = 0; - if(%closestclient.getState() $= "dead" || %Zombie.getState() $= "dead"){ - %zombie.canmove = 1; - return; - } - %target = %closestclient; - if(!isobject(%target)){ - %zombie.canmove = 1; - return; - } - %pos = %zombie.getworldboxcenter(); - %Tpos = %target.getworldboxcenter(); - %ZtoT = vectorsub(%tpos,%pos); - if (%count <= 12){ - %newpos = vectoradd(%ZtoT,vectoradd(%pos,"0 0 -0.6")); - %target.setTransform(%newpos); - %target.setvelocity("0 0 0"); - } - else { - %killtype = getrandom(1,2); - if(%killtype == 1){ - %closestwall = 20; - %nv2 = (getword(%ZtoT, 0) * -1); - %nv1 = getword(%ZtoT, 1); - %vector1 = vectorscale(vectornormalize(%nv1@" "@%nv2@" 0"),20); - %nvector1 = vectoradd(%tpos,%vector1); - %nv2 = getword(%ZtoT, 0); - %nv1 = (getword(%ZtoT, 1) * -1); - %vector2 = vectorscale(vectornormalize(%nv1@" "@%nv2@" 0"),20); - %nvector2 = vectoradd(%tpos,%vector2); - %searchresultR = containerRayCast(%tpos, %nvector1, $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType); - %searchresultL = containerRayCast(%tpos, %nvector2, $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::VehicleObjectType); - if(%searchresultR){ - %Hpos = getword(%searchresultR,1)@" "@getword(%searchresultR,2)@" "@getword(%searchresultR,3); - %distance = vectordist(%Tpos, %Hpos); - if(%distance <= %closestwall){ - %closestwall = %distance; - %vector = vectoradd(vectorscale(%vector1,1500),"0 0 100"); - } - } - if(%searchresultL){ - %Hpos = getword(%searchresultL,1)@" "@getword(%searchresultL,2)@" "@getword(%searchresultL,3); - %distance = vectordist(%Tpos, %Hpos); - if(%distance <= %closestwall){ - %closestwall = %distance; - %vector = vectoradd(vectorscale(%vector2,1500),"0 0 100"); - } - } - if(%closestwall == 20){ - %x = getword(%ZtoT, 0); - %y = getword(%ZtoT, 1); - %outvec = vectorscale(vectornormalize(%x@" "@%y@" 0"),50); - %vector = vectoradd("0 0 -15000",%outvec); - } - %target.applyimpulse(%target.getposition(),%vector); - } - else if(%killtype == 2){ - %target.infected = 1; - %target.damage(0, %target.getposition(), 10.0, $DamageType::ZombieL); - } - %count = 0; - %zombie.canmove = 1; - return; - } - %count++; - %zombie.killingplayer = schedule(150, %zombie, "Llifttarget", %zombie, %closestclient, %count); -} - - -function DZombieFire(%zombie,%closestclient){ - %pos = %zombie.getMuzzlePoint(4); - %tpos = %closestclient.getWorldBoxCenter(); - %tvel = %closestclient.getvelocity(); - %vec = vectorsub(%tpos,%pos); - %dist = vectorlen(%vec); - %velpredict = vectorscale(%tvel,(%dist / 50)); - %vector = vectoradd(%vec,%velpredict); - %ndist = vectorlen(%vector); - %upvec = "0 0 "@((%ndist / 50) * (%ndist / 50) * 2); - %vector = vectornormalize(vectoradd(%vector,%upvec)); - %p = new GrenadeProjectile() - { - dataBlock = DemonFireball; - initialDirection = %vector; - initialPosition = %pos; - sourceObject = %zombie; - sourceSlot = 4; - }; -} - -function RkillLoop(%zombie,%target,%count){ - if(!isObject(%zombie)){ - %zombie.iscarrying = 0; - %target.grabbed = 0; - return; - } - if(!isObject(%target)){ - %zombie.iscarrying = 0; - %target.grabbed = 0; - return; - } - if (%Zombie.getState() $= "dead"){ - %zombie.iscarrying = 0; - %target.grabbed = 0; - return; - } - if (%target.getState() $= "dead"){ - %zombie.iscarrying = 0; - %target.grabbed = 0; - return; - } - if(%count == 50){ - %chance = getRandom(1,3); - if(%chance == 3) - %target.damage(0, %tpos, 10.0, $DamageType::Zombie); - else{ - %target.isFTD = 1; - if(%target.getMountedImage($Backpackslot) !$= "") - %target.throwPack(); - %target.finishingfall = schedule(5000, 0, "stopFTD", %target); - } - %zombie.iscarrying = 0; - return; - } - %target.setPosition(vectoradd(%zombie.getPosition(),"0 0 -4")); - %target.setVelocity(%zombie.getVelocity()); - %count++; - %zombie.killingplayer = schedule(100, 0, "RkillLoop", %zombie, %target, %count); -} - -function stopFTD(%target){ - %target.isFTD = 0; - %target.grabbed = 0; -} - -function ZSetRandomMove(%zombie){ - if (!isobject(%zombie)) - return; - %RX = getrandom(-10, 10); - %RY = getrandom(-10, 10); - %RZ = getrandom(); - %vector = %RX@" "@%RY@" "@%RZ; - %zombie.direction = vectornormalize(%vector); - %zombie.Mnum = getrandom(1, 20); - %zombie.zombieRmove = schedule(500, %zombie, "ZrandommoveLoop", %zombie); -} - -function ZrandommoveLoop(%zombie){ - if (!isobject(%zombie)) { - return; - } - - if (%Zombie.getState() $= "dead") { - return; - } - - if (%zombie.hastarget == 1){ - %zombie.direction = ""; - return; - } - if (%zombie.Mnum >= 1){ - %X = getword(%zombie.direction, 1); - %Y = (getword(%zombie.direction, 0) * -1); - %none = 0; - %vector = %X@" "@%Y@" "@%none; - %zombie.setRotation(fullrot("0 0 0",%vector)); - if(%zombie.type == 1) - %speed = ($zombie::forwardspeed); - else if(%zombie.type == 2) - %speed = ($zombie::Fforwardspeed * 0.6); - else if(%zombie.type == 4) - %speed = ($zombie::Dforwardspeed * 0.75); - else if(%zombie.type == 3) - %speed = ($zombie::Lforwardspeed * 0.8); - %vector = vectorscale(%zombie.direction, %speed); - %zombie.applyimpulse(%zombie.getposition(), %vector); - %zombie.Mnum = (%zombie.Mnum - 1); - %zombie.zombieRmove = schedule(500, %zombie, "ZrandommoveLoop", %zombie); - } - else if(%zombie.Mnum == 0) - %zombie.zombieRmove = schedule(100, %zombie, "ZSetRandomMove", %zombie); -} - -function InfectLoop(%obj){ - if(%obj.isSentinel) - return; - - if((%obj.armor $= "Pure") || (%obj.armor $= "Light")) { - return; - } - - if ($Host::NoInfection) - { - %obj.Infected = 0; - cancel(%obj.infectedDamage); - - %obj.infectedDamage = ""; - %obj.beats = 0; - %obj.canZKill = 0; - - cancel(%player.zombieAttackImpulse); - return; - } - - if (%obj.getState() $= "dead") - return; - if(isObject(%obj)){ - if(%obj.beats $= "") - zombieAttackImpulse(%obj,0); - if(%obj.beats < 15) - %obj.setWhiteOut(%obj.beats * 0.05); - else - %obj.setDamageFlash(1); - if(%obj.beats == 15){ - %obj.canZkill = 1; - } - if(%obj.beats >=15) - serverPlay3d("ZombieMoan",%obj.getWorldBoxCenter()); - else if (%obj.beats >= 10) - playDeathCry(%obj); - else - playPain(%obj); - if(%obj.beats == 20){ - if($host::canZombie $= "") - $host::canZombie = 0; - if($host::canZombie == 1) - makePersonZombie(%obj.getTransform(), %obj.client, ZombieGetRandom()); - else - %obj.damage(0, %obj.getposition(), 10.0, $DamageType::Zombie); - return; - } - %obj.beats++; - %obj.infectedDamage = schedule(2000, %obj, "InfectLoop", %obj); - } -} - -function ZkillUpdateScore(%game, %client,%implement){ - if( %implement.getClassName() $= "Turret") - %client = %implement.getControllingClient(); - else if(%implement.getDataBlock().catagory $= "Vehicles") - %client = %implement.getControllingClient(); - %client.Zkills++; - %game.recalcScore(%client); -} - -function zombieSpawnLoop(%pos, %radius, %freq){ - if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) - return; - - if(%freq > 10) - %freq = 10; - if(%freq < 1) - %freq = 1; - %chance = getRandom(1,50); - if(%chance <= %freq && $numspawnedzombies < (%freq * 5)){ - %spawnPos = vectorAdd(%pos,(getRandom(0,%radius) - (%radius / 2))@" "@(getRandom(0,%radius) - (%radius / 2))@" getRandom(0,15)"); - %search = containerRayCast(%spawnPos, vectorAdd(%spawnPos,"0 0 -1000"), $TypeMasks::StaticShapeObjectType | $TypeMasks::InteriorObjectType | $TypeMasks::ForceFieldObjectType | $TypeMasks::TerrainObjectType); - if(%search) - %spawnPos = getWord(%search,1)@" "@getWord(%search,2)@" "@getWord(%search,3); - %chance = getRandom(1,65); - if(%chance <= 25){ - %Zombie = new player(){ - Datablock = "ZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Zombie"); - %Ztype = 1; - } - else if(%chance <= 35){ - %Zombie = new player(){ - Datablock = "FZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Ravenger Zombie"); - %Ztype = 2; - } - else if(%chance <= 40){ - %Zombie = new player(){ - Datablock = "LordZombieArmor"; - }; - applyskin(%zombie,'ZLord',"Zombie Lord"); - %Zombie.mountImage(ZHead, 3); - %Zombie.mountImage(ZBack, 4); - %Zombie.mountImage(ZDummyslotImg, 5); - %Zombie.mountImage(ZDummyslotImg2, 6); - %zombie.firstFired = 0; - %zombie.canmove = 1; - %Ztype = 3; - } - else if(%chance <= 55){ - %Zombie = new player(){ - Datablock = "DemonZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Demon Zombie"); - %zombie.mountImage(ZdummyslotImg, 4); - %Ztype = 4; - } - else if(%chance <= 65){ - %Zombie = new player(){ - Datablock = "RapierZombieArmor"; - }; - applyskin(%zombie,'Zombie',"Rapier Zombie"); - %Zombie.mountImage(ZWingImage, 3); - %Zombie.mountImage(ZWingImage2, 4); - %zombie.setActionThread("scoutRoot",true); - %Ztype = 5; - } - %zombie.type = %Ztype; - %Zombie.setTransform(%spawnPos); - %Zombie.team = 0; - %zombie.canjump = 1; - %zombie.hastarget = 1; - %zombie.randspawnerstarted = 1; - AddToZombieGroup(%Zombie); - schedule(1000, %zombie, "ZombieLookforTarget", %zombie); - $numspawnedzombies++; - } - $zombieloop = schedule(500, 0, "zombieSpawnLoop", %pos, %radius, %freq); -} - -function StopZombieSpawnLoop(){ - cancel($zombieloop); -} - -function ZombieBloodLust(%obj, %count){ - if(!isObject(%obj)) - return; - if (%obj.getState() $= "dead") - return; - %obj.setDamageFlash(0.5); - if(%count == 10){ - serverPlay3d("ZombieMoan",%obj.getWorldBoxCenter()); - %count = 0; - } - %count++; - schedule(200, %obj, "ZombieBloodLust", %obj, %count); -} - -function makePersonZombie(%trans, %client, %special) -{ - %client.player.delete(); - - %client.setWeaponsHudClearAll(); - if(%special == 1) - %data = "ControlLordZombieArmor"; - else if(%special == 2) - %data = "ControlRapierZombieArmor"; - else if(%special == 3) - %data = "ControlDemonZombieArmor"; - else - %data = "ZombieArmor"; - - %player = new Player() { - dataBlock = %data; - }; - - if(%special == 1) - { -// %player.mountImage(ZHead, 3); - %player.mountImage(ZBack, 4); - %player.mountImage(ZDummyslotImg, 5); - %player.mountImage(ZDummyslotImg2, 6); - } - else if(%special == 2) - { - %player.mountImage(ZWingImage, 3); - %player.mountImage(ZWingImage2, 4); - } - - %player.setTransform( %trans ); - AddToZombieGroup(%player); - - // setup some info - %player.setOwnerClient(%client); - %player.team = 0; - %client.outOfBounds = false; - %player.setEnergyLevel(0); - %client.player = %player; - - // updates client's target info for this player - %player.setTarget(%client.target); - setTargetDataBlock(%client.target, %player.getDatablock()); - setTargetSensorData(%client.target, PlayerSensor); - setTargetSensorGroup(%client.target, 1); - %client.setSensorGroup(1); - - %client.setControlObject(%player); - %player.client.clearBackpackIcon(); - - %player.iszombie = 1; - - if(%special == 1) - { - %player.setInventory(LordAcidGun, 1, true); - %player.use("LordAcidGun"); // Eolk - attempt to fix this problem. - } - else if(%special == 2) - RapierCarryCheck(%player); - else if(%special == 3) - { - %player.setInventory(DZShot, 1, true); - %player.use("DZShot"); // Eolk - attempt to fix this problem. - } - - ZombieBloodLust(%player,0); - if(!%special) - zombieAttackImpulse(%player,80); -} - -// This keeps the rapier-human squatting and acting like a real rapier when carrying someone to die. -function RapierCarryCheck(%obj) -{ - if(!isObject(%obj) || %obj.getState() $= "Dead") - return; - - if(%obj.isCarrying == 1) - { - %vector = VectorScale(%obj.getEyeVector(), $Zombie::RForwardSpeed + %obj.getDatablock().mass); - %vector = getword(%vector, 0) SPC getword(%vector, 1) SPC ($Zombie::rupvec * 1.5); - %obj.applyImpulse(%obj.position, %vector); - } - - %obj.setActionThread("scoutroot", 1); - %obj.RImpulse = schedule(500, 0, "RapierCarryCheck", %obj); -} - -function zombieAttackImpulse(%obj, %count){ - if(!isObject(%obj)) { - return; - } - - if (%obj.getState() $= "Dead") { - return; - } - - %pos = %obj.getposition(); - InitContainerRadiusSearch(%pos, %count, $TypeMasks::PlayerObjectType || $TypeMasks::VehicleObjectType); - while ((%objtarget = containerSearchNext()) != 0){ - if(isObject(%objtarget) && %objtarget !$= %obj){ - %objarmortype = %objtarget.getdatablock().getname(); - if(%objarmortype $= "ZombieArmor" || %objarmortype $= "FZombieArmor" || %objarmortype $= "LordZombieArmor" || %objarmortype $= "DemonZombieArmor" || %objarmortype $= "ControlDemonZombieArmor" || %objarmortype $= "RapierZombieArmor" || %objarmortype $= "ControlRapierZombieArmor" || %objarmortype $= "ControlLordZombieArmor") - %objiszomb = 1; - if(!(%objiszomb) && %objtarget.iszombie != 1) { - %vec = vectorNormalize(vectorSub(%objtarget.getWorldBoxCenter(),%obj.getWorldBoxCenter())); - if(vectorDist(%vec,%obj.getForwardVector()) <= 0.5){ - if(%count <= 200){ - %impulse = (%count / 20) * 90; - %up = (%count / 100) * 90; - } - else{ - %impulse = 900; - %up = 180; - } - %vec = vectorScale(%vec,%impulse); - %vec = vectorAdd(%vec,"0 0 "@%up); - %obj.applyimpulse(%obj.getPosition(),%vec); - %count++; - %obj.zombieAttackImpulse = schedule(500, 0, "zombieAttackImpulse", %obj, %count); - return; - } - } - } - %objiszomb = 0; - } - %count++; - %obj.zombieAttackImpulse = schedule(500, 0, "zombieAttackImpulse", %obj, %count); -} - -function AddToZombieGroup(%player) -{ - if(isObject(%player)) - { - %group = nameToID("MissionCleanup/ZombieGroup"); - if(!isObject(%group)) - { - %group = new SimGroup("ZombieGroup"); - MissionCleanup.add(%group); - } - - %group.add(%player); - } -} - -function RemoveFromZombieGroup(%player) -{ - if(isObject(%player)) - { - %group = nameToID("MissionCleanup/ZombieGroup"); - if(!isObject(%group)) - { - %group = new SimGroup("ZombieGroup"); - MissionCleanup.add(%group); - } - - %group.remove(%player); - } -} - -//--------------------------------------------------------------------- -//------------------------DEMON MOTHER STUFF--------------------------- -//--------------------------------------------------------------------- - -datablock SeekerProjectileData(DMMissile) -{ - casingShapeName = "weapon_missile_casement.dts"; - projectileShapeName = "weapon_missile_projectile.dts"; - hasDamageRadius = true; - indirectDamage = 0.5; - damageRadius = 5.0; - radiusDamageType = $DamageType::Zombie; - kickBackStrength = 2000; - - explosion = "MissileExplosion"; - splash = MissileSplash; - velInheritFactor = 1.0; // to compensate for slow starting velocity, this value - // is cranked up to full so the missile doesn't start - // out behind the player when the player is moving - // very quickly - bramage - - baseEmitter = MortarSmokeEmitter; - delayEmitter = MissileFireEmitter; - puffEmitter = MissilePuffEmitter; - bubbleEmitter = GrenadeBubbleEmitter; - bubbleEmitTime = 1.0; - - exhaustEmitter = MissileLauncherExhaustEmitter; - exhaustTimeMs = 300; - exhaustNodeName = "muzzlePoint1"; - - lifetimeMS = 10000; // z0dd - ZOD, 4/14/02. Was 6000 - muzzleVelocity = 10.0; - maxVelocity = 35.0; // z0dd - ZOD, 4/14/02. Was 80.0 - turningSpeed = 23.0; - acceleration = 15.0; - - proximityRadius = 2.5; - - terrainAvoidanceSpeed = 10; - terrainScanAhead = 7; - terrainHeightFail = 1; - terrainAvoidanceRadius = 3; - - flareDistance = 40; - flareAngle = 20; - minSeekHeat = 0.0; - - sound = MissileProjectileSound; - - hasLight = true; - lightRadius = 5.0; - lightColor = "0.2 0.05 0"; - - useFlechette = true; - flechetteDelayMs = 250; - casingDeb = FlechetteDebris; - - explodeOnWaterImpact = false; -}; - -datablock LinearFlareProjectileData(DMPlasma) -{ - doDynamicClientHits = true; - - directDamage = 0; - directDamageType = $DamageType::Zombie; - hasDamageRadius = true; - indirectDamage = 0.8; // z0dd - ZOD, 4/25/02. Was 0.5 - damageRadius = 15.0; - kickBackStrength = 1500; - radiusDamageType = $DamageType::Zombie; - explosion = MortarExplosion; - splash = PlasmaSplash; - - dryVelocity = 85.0; // z0dd - ZOD, 4/25/02. Was 50. Velocity of projectile out of water - wetVelocity = -1; - velInheritFactor = 1.0; - fizzleTimeMS = 4000; - lifetimeMS = 2500; // z0dd - ZOD, 4/25/02. Was 6000 - explodeOnDeath = true; - reflectOnWaterImpactAngle = 0.0; - explodeOnWaterImpact = true; - deflectionOnWaterImpact = 0.0; - fizzleUnderwaterMS = -1; - - activateDelayMS = 100; - - scale = "3.0 3.0 3.0"; - numFlares = 30; - flareColor = "0.1 0.3 1.0"; - flareModTexture = "flaremod"; - flareBaseTexture = "flarebase"; -}; - -function DemonMotherCreate(%pos){ - if(ZombieGroup.getCount() >= $Host::MaxZombies && $Host::MaxZombies != -1) - { - error("Too many zombies. Cannot create demon mother"); - return; - } - - %obj = new player(){ - Datablock = "DemonMotherZombieArmor"; - }; - %obj.setTransform(%pos); - %obj.team = 0; - MissionCleanup.add(%obj); - AddToZombieGroup(%obj); - schedule(1000, 0, "DemonMotherInitiate", %obj); - - // Eolk - Needs to return %obj now - return %obj; -} - -function DemonMotherInitiate(%obj){ - if(!isObject(%obj)) - return; - DemonMotherDefense(%obj); - DemonMotherThink(%obj); - %obj.mountImage(ZdummyslotImg, 4); - %obj.justshot = 0; - %obj.justmelee = 0; -} - -function DemonMotherThink(%obj){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - %pos = %obj.getposition(); - %count = ClientGroup.getCount(); - %closestClient = -1; - %closestDistance = 32767; - for(%i = 0; %i < %count; %i++) - { - %cl = ClientGroup.getObject(%i); - if(isObject(%cl.player)){ - %testPos = %cl.player.getWorldBoxCenter(); - %distance = vectorDist(%pos, %testPos); - if (%distance > 0 && %distance < %closestDistance && %cl.player.isFTD != 1 && %cl.player.iszombie != 1) - { - %closestClient = %cl; - %closestDistance = %distance; - } - } - } - if(%closestClient != -1){ - %searchobject = %closestclient.player; - %dist = vectorDist(%pos,%searchobject.getPosition()); - if(%dist <= 100){ - if(%dist <= 50){ //ok were now in combat mode, lets decide on what we should do, move attack, or shoot. - if(%obj.justmelee == 1){ //if we just used a melee attack, maybe we should follow it up with a shot attack. - if(%dist >= 10){ //good were far enough away, lets shoot em. - %rand = getrandom(1,3); - if(%rand <= 2) - DemonMotherSpermAttack(%obj,%searchobject); - else - DemonMotherFireRainAttack(%obj,%searchobject); - } - else //damn, to close, ok lung at him - DemonMotherLungAttack(%obj,%searchobject); - } - else{ - %rand = getRandom(1,5); //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. - if(%rand == 1) - DemonMotherPlasmaAttack(%obj,%searchobject); - else if(%rand <= 3) - DemonMotherStrafeAttack(%obj,%searchobject); - else - DemonMotherFlyAttack(%obj,%searchobject); - } - } - else{ //ok, were to far away, maybe we should shoot at them. - if(%obj.justshot == 1) //humm we just attacked, ok, let charge him, get in close - DemonMotherChargeIn(%obj,%searchobject); - else{ //were good to fire, FIRE AWAY! - %rand = getRandom(1,5); //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. - if(%rand == 1) - DemonMotherFireRainAttack(%obj,%searchobject); - else if(%rand <= 3) - DemonMotherMissileAttack(%obj,%searchobject); - else - DemonMotherSpermAttack(%obj,%searchobject); - } - } - } - else if(%dist > 200){ - %rand = getrandom(1,120); - if(%rand == 94) //please, dont ask why i choose this number, it just poped in my head - DemonMotherDemonSpawn(%obj); - else - DemonMotherMoveToTarget(%obj,%searchobject); - } - else - DemonMotherMoveToTarget(%obj,%searchobject); - - %obj.justshot = 0; - %obj.justmelee = 0; - } - else{ - schedule(500, 0, "DemonMotherThink", %obj); - } -} - -function DemonMotherDefense(%obj){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - %pos = %obj.getposition(); - InitContainerRadiusSearch(%pos, 250, $TypeMasks::ProjectileObjectType); - while ((%searchObject = containerSearchNext()) != 0){ - %projpos = %searchobject.getPosition(); - %dist = vectorDist(%pos,%projpos); - if(%dist <= 100){ - if(%searchobject.lastpos) - %searchobject.delete(); - } - else - %searchobject.lastpos = %projpos; - } - schedule(50, "DemonMotherDefense", %obj); -} - -function DemonMotherSpermAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(!isObject(%target)){ - DemonMotherThink(%obj); - return; - } - FaceTarget(%obj,%target); - if(%obj.chargecount $= "") - %obj.chargecount = 0; - %charge = new ParticleEmissionDummy() - { - position = %obj.getMuzzlePoint(4); - dataBlock = "defaultEmissionDummy"; - emitter = "FlameEmitter"; - }; - MissionCleanup.add(%charge); - %charge.schedule(100, "delete"); - - if(%obj.chargecount == 7){ - %vec = vectorsub(%target.getworldboxcenter(),%obj.getMuzzlePoint(4)); - %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); - %p = new TracerProjectile() - { - dataBlock = LZombieAcidBall; - initialDirection = %vec; - initialPosition = %obj.getMuzzlePoint(4); - sourceObject = %obj; - sourceSlot = 6; - }; - } - if(%obj.chargecount == 9){ - %vec = vectorsub(%target.getworldboxcenter(),%obj.getMuzzlePoint(4)); - %vec = vectoradd(%vec, vectorscale(%target.getvelocity(),vectorlen(%vec)/100)); - %p = new TracerProjectile() - { - dataBlock = LZombieAcidBall; - initialDirection = %vec; - initialPosition = %obj.getMuzzlePoint(4); - sourceObject = %obj; - sourceSlot = 6; - }; - } - - if(%obj.chargecount <= 9){ - schedule(100, 0, "DemonMotherSpermAttack", %obj, %target); - %obj.chargecount++; - } - else{ - %obj.chargecount = 0; - %obj.justshot = 1; - DemonMotherThink(%obj); - } -} - -function DemonMotherLungAttack(%obj,%target){ - FaceTarget(%obj,%target); - %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); - %vector = vectorscale(%vector, 4000); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - %vector = %x@" "@%y@" 400"; - %obj.applyImpulse(%obj.getPosition(), %vector); - - %obj.justmelee = 1; - schedule(750, 0, "DemonMotherThink", %obj); -} - -function DemonMotherStrafeAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount <= 8){ - %obj.setVelocity("0 0 0"); - FaceTarget(%obj,%target); - %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); - %vector = vectorscale(%vector, 3250); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %nv1 = %y; - %nv2 = (%x * -1); - %vector = %nv1@" "@%nv2@" 0"; - %obj.applyImpulse(%obj.getPosition(), %vector); - } - else if(%obj.chargecount <= 11){ - %obj.setvelocity("0 0 0"); - FaceTarget(%obj,%target); - %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); - %vector = vectorscale(%vector, 4500); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - %vector = %x@" "@%y@" 150"; - %obj.applyImpulse(%obj.getPosition(), %vector); - } - else{ - %obj.chargecount = 0; - %obj.justmelee = 1; - schedule(250, 0, "DemonMotherThink", %obj); - return; - } - schedule(250, 0, "DemonMotherStrafeAttack", %obj, %target); - %obj.chargecount++; -} - -function DemonMotherFlyAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount <= 9){ - FaceTarget(%obj,%target); - %obj.setvelocity("0 0 10"); - %obj.chargecount++; - schedule(100, 0, "DemonMotherFlyAttack",%obj,%target); - } - else if(%obj.chargecount == 10){ - FaceTarget(%obj,%target); - %obj.setvelocity("0 0 5"); - %vector = vectorSub(%target.getPosition(),%obj.getPosition()); - %nVec = vectorNormalize(%vector); - %vector = vectorAdd(%vector,vectorscale(%nvec,-4)); - %obj.attackpos = vectorAdd(%obj.getPosition(),%vector); - %obj.attackdir = %nVec; -// echo(%obj.getPosition() SPC %target.getPosition() SPC %obj.attackpos SPC %obj.attackdir); - %obj.startFade(400, 0, true); - %obj.chargecount++; - schedule(400, 0, "DemonMotherFlyAttack",%obj,%target); - } - else if(%obj.chargecount >= 11){ - %obj.startFade(500, 0, false); - %obj.setPosition(%obj.attackpos); - %obj.setvelocity(vectorscale(%obj.attackdir,25)); - %obj.justmelee = 1; - %obj.chargecount = 0; -// echo(%obj.getPosition() SPC %target.getPosition() SPC %obj.attackpos SPC %obj.attackdir); - %obj.attackpos = ""; - %obj.attackdir = ""; - schedule(1000, 0, "DemonMotherThink",%obj); - } -} - -function DemonMotherFireRainAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount == 0){ - FaceTarget(%obj, %target); - for(%i = 0; %i < 10; %i++){ - %pos = %obj.getPosition(); - %x = getRandom(0,10) - 5; - %y = getRandom(0,10) - 5; - %vec = vectorAdd(%pos,%x SPC %y SPC "5"); - %searchResult = containerRayCast(%vec, vectorAdd(%vec,"0 0 -10"), $TypeMasks::TerrainObjectType, %obj); - - %charge = new ParticleEmissionDummy() - { - position = posFromRaycast(%searchresult); - dataBlock = "defaultEmissionDummy"; - emitter = "FlameEmitter"; - }; - MissionCleanup.add(%charge); - %charge.schedule(1500, "delete"); - } - %obj.chargecount++; - schedule(1000, 0, "DemonMotherFireRainAttack",%obj,%target); - } - else{ - %x = (getRandom() * 2) - 1; - %y = (getRandom() * 2) - 1; - %z = getRandom(); - %vec = vectorNormalize(%x SPC %y SPC %z); - %pos = vectorAdd(%target.getPosition(),vectorScale(%vec, 20)); - for(%i = 0;%i < 10;%i++){ - %x = getRandom(0,14) - 7; - %y = getRandom(0,14) - 7; - %spwpos = vectorAdd(%pos,%x SPC %y SPC "2"); - %p = new GrenadeProjectile() - { - dataBlock = DemonFireball; - initialDirection = vectorScale(%vec,-1); - initialPosition = %spwpos; - sourceObject = %obj; - sourceSlot = 4; - }; - } - %obj.justshot = 1; - %obj.chargecount = 0; - schedule(1000, 0, "DemonMotherThink",%obj); - } -} - -function DemonMotherMissileAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount == 0){ - %obj.chargecount++; - schedule(1000, 0, "DemonMotherMissileAttack", %obj, %target); - } - else{ - %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); - %p = new SeekerProjectile() - { - dataBlock = DMMissile; - initialDirection = %vec; - initialPosition = %obj.getMuzzlePoint(4); - sourceObject = %obj; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %target.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%target,%beacon,%p); - - %obj.justshot = 1; - %obj.chargecount = 0; - schedule(1000, 0, "DemonMotherThink", %obj); - } -} - -function DemonMotherMissileFollow(%target,%beacon,%missile){ - if(!isObject(%target)){ - %beacon.delete(); - return; - } - if(!isObject(%missile)){ - %beacon.delete(); - return; - } - %beacon.setPosition(%target.getWorldBoxCenter()); - schedule(100, 0, "DemonMotherMissileFollow", %target, %beacon, %missile); -} - -function DemonMotherPlasmaAttack(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount <= 9){ - %obj.setVelocity("0 0 10"); - %obj.chargecount++; - schedule(100, 0, "DemonMotherPlasmaAttack", %obj, %target); - } - else{ - %obj.setVelocity("0 0 3"); - %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); - %p = new LinearFlareProjectile() - { - dataBlock = DMPlasma; - initialDirection = %vec; - initialPosition = %obj.getMuzzlePoint(4); - sourceObject = %obj; - sourceSlot = 4; - }; - %obj.chargecount = 0; - %obj.justshot = 1; - schedule(1000, 0, "DemonMotherThink", %obj); - } -} - -function DemonMotherChargeIn(%obj,%target){ - if(!isObject(%obj)) - return; - if(%obj.getState() $= "dead") - return; - if(%obj.chargecount $= "") - %obj.chargecount = 0; - if(%obj.chargecount <= 4){ - FaceTarget(%obj, %target); - %vec = vectorNormalize(vectorSub(%target.getPosition(),%obj.getPosition())); - %obj.setvelocity(vectorScale(%vec,50)); - %obj.chargecount++; - schedule(500, 0, "DemonMotherChargeIn", %obj, %target); - } - else{ - %obj.justmelee = 1; - %obj.chargecount = 0; - DemonMotherThink(%obj); - } -} - -function DemonMotherMoveToTarget(%obj,%target){ - FaceTarget(%obj,%target); - %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); - %vector = vectorscale(%vector, 1200); - %x = Getword(%vector,0); - %y = Getword(%vector,1); - %z = Getword(%vector,2); - %vector = %x@" "@%y@" 150"; - %obj.applyImpulse(%obj.getPosition(), %vector); - - schedule(500, 0, "DemonMotherThink", %obj); -} - -function DemonMotherDemonSpawn(%obj){ - for(%i = 0; %i < 5; %i++){ - %pos = %obj.getPosition(); - %x = getRandom(0,200) - 100; - %y = getRandom(0,200) - 100; - %vec = vectorAdd(%pos,%x SPC %y SPC "40"); - %searchResult = containerRayCast(%vec, vectorAdd(%vec,"0 0 -80"), $TypeMasks::TerrainObjectType, %obj); - - %charge = new ParticleEmissionDummy() - { - position = posFromRaycast(%searchresult); - dataBlock = "defaultEmissionDummy"; - emitter = "FlameEmitter"; - }; - MissionCleanup.add(%charge); - %charge.schedule(1100, "delete"); - schedule(1000, 0, "startAzombie", posFromRaycast(%searchresult), 4); - } - schedule(1500, 0, "DemonMotherThink", %obj); -} - -function FaceTarget(%obj,%target){ - %vector = vectorNormalize(vectorSub(%target.getPosition(), %obj.getPosition())); - %v1 = getword(%vector, 0); - %v2 = getword(%vector, 1); - %nv1 = %v2; - %nv2 = (%v1 * -1); - %vector2 = %nv1@" "@%nv2@" 0"; - %obj.setRotation(fullrot("0 0 0",%vector2)); -} diff --git a/scripts/power.cs b/scripts/power.cs index d020730..f79767a 100644 --- a/scripts/power.cs +++ b/scripts/power.cs @@ -209,6 +209,8 @@ function globalPowerCheck() { function checkPowerGenerator(%powerObj,%stateChange) { %group = nameToID("MissionCleanup/Deployables"); + if (!isObject(%group)) + return; %count = %group.getCount(); for(%i=0;%i<%count;%i++) { %obj = %group.getObject(%i); diff --git a/scripts/server.cs b/scripts/server.cs index d919eb0..453e432 100644 --- a/scripts/server.cs +++ b/scripts/server.cs @@ -8,7 +8,7 @@ $SB::WODec = 0.004; $SB::DFDec = 0.02; $DefaultGravity = -20; -setperfcounterenable(0); // Blnukem - Do not change this. It's lag protection. +setPerfCounterEnable(0); // Blnukem - Do not change this. It's lag protection. CheckClientCount(); function onTelnetConnect(%ip, %access) { @@ -117,24 +117,28 @@ function CreateServer(%mission, %missionType) { exec("scripts/chatCommands.cs"); exec("scripts/skywrite.cs"); exec("scripts/dEffects.cs"); - exec("scripts/rankstuff.cs"); - exec("scripts/SpecOpsFeatures.cs"); - exec("scripts/modscripts/ModFunctions.cs"); - exec("scripts/modscripts/ChatCommands/AdminCommands.cs"); - exec("scripts/modscripts/ChatCommands/AICommands.cs"); - exec("scripts/modscripts/ChatCommands/SACommands.cs"); - exec("scripts/modscripts/ChatCommands/ZombieCommands.cs"); - exec("scripts/modscripts/ChatCommands/HelpCommand.cs"); - exec("scripts/modscripts/AI/DroneAI.cs"); - exec("scripts/modscripts/AI/S11AI.cs"); - exec("scripts/modscripts/AI/S17AI.cs"); - exec("scripts/modscripts/AI/SentinelData.cs"); - exec("scripts/modscripts/AI/SentinelAI.cs"); + + // -- ACCM Executes + exec("scripts/modscripts/ranking.cs"); + exec("scripts/modscripts/specops.cs"); + exec("scripts/modscripts/modfunctions.cs"); + + exec("scripts/modscripts/chatcommands/admin.cs"); + exec("scripts/modscripts/chatcommands/ai.cs"); + exec("scripts/modscripts/chatcommands/sa.cs"); + exec("scripts/modscripts/chatcommands/zombie.cs"); + exec("scripts/modscripts/chatcommands/help.cs"); + + exec("scripts/modscripts/ai/drone.cs"); + exec("scripts/modscripts/ai/s11.cs"); + exec("scripts/modscripts/ai/s17.cs"); + exec("scripts/modscripts/ai/zombie.cs"); + exec("scripts/turrets/mortarBarrelLarge.cs"); - exec("scripts/packs/waypointpack.cs"); - exec("scripts/Data/PulseData.cs"); - exec("scripts/Data/MessageData.cs"); - exec("scripts/Data/VariableDefaults.cs"); + exec("scripts/data/PulseData.cs"); + exec("scripts/data/MessageData.cs"); + exec("scripts/data/VariableDefaults.cs"); + exec("scripts/modscripts/player.cs"); if (!isDemo()) { diff --git a/scripts/vehicles/vehicle_shrike.cs b/scripts/vehicles/vehicle_shrike.cs index 3260a05..61e12c5 100644 --- a/scripts/vehicles/vehicle_shrike.cs +++ b/scripts/vehicles/vehicle_shrike.cs @@ -617,7 +617,9 @@ datablock ShapeBaseImageData(ScoutChaingunParam) function shrikeMissileImage::onFire(%data,%obj,%slot) { %p = Parent::onFire(%data, %obj, %slot); - %obj.getMountNodeObject(0).decInventory(%data.ammo, 1); + %mountNodeObj = %obj.getMountNodeObject(0); + if (isObject(%mountNodeObj)) + %mountnodeObj.decInventory(%data.ammo, 1); MissileSet.add(%p); if(%obj.isdrone == 1) @@ -729,4 +731,4 @@ function fighterdropflares(%obj,%time,%life,%chance){ serverPlay3D(GrenadeThrowSound, getBoxCenter(%obj.getWorldBox())); %p.schedule(%life, "delete"); schedule(%time,0,"FighterDropFlares",%obj,%time,%life,%chance); -} \ No newline at end of file +} diff --git a/scripts/weapTurretCode.cs b/scripts/weapTurretCode.cs index ff207e7..180048e 100644 --- a/scripts/weapTurretCode.cs +++ b/scripts/weapTurretCode.cs @@ -249,6 +249,9 @@ function ScoutChaingunPairImage::onFire(%data,%obj,%slot) function fireNextGun(%obj) { + if (!isObject(%obj)) + return; + if(%obj.fireWeapon) { if(%obj.nextWeaponFire == 2) @@ -1043,4 +1046,4 @@ function MineDeployed::onDestroyed(%data, %obj, %lastState) %data.kickBackStrength, %obj.sourceObject, %data.radiusDamageType); %obj.schedule(600, "delete"); -} \ No newline at end of file +}