diff --git a/README.md b/README.md index 038a79a..6662059 100644 --- a/README.md +++ b/README.md @@ -89,6 +89,11 @@ PLEASE NOTE: I've moved all old changelogs into the version_history folder. This * Players will be knocked back with a higher force when hit by demon zombies * Air Rapier * Modified the damage scalar of missiles to be a OHK on rapier zombies + * Demon Lord + * Cleaned up this script file substantially + * Replaced the standard lunge with a fire lunge which creates a firey explosion on impact + * Reduced the hit damage of the demon lord from 0.8 to 0.5 + * Demon Lords, like the regular demons will no longer infect on collision, but set the player on fire instead * Added Boss Proficiency * Hidden challenges embedded in boss fights that award additional experience for completing tough feats * For example: Defeat the shade lord without dying by the elemental shades @@ -117,6 +122,8 @@ PLEASE NOTE: I've moved all old changelogs into the version_history folder. This * Lord Vardison * Fixed an erraneous text prompt that would appear when the shadow rift detonated outside of WTF difficulty stating vardison had healed when in fact he did not * General Enhancements + * Centralized some of the datablocks that were shared across the mod to allow for easier access / modification + * Centralized the demon lord's missile seeking logic that was used across multiple zombies & bosses to allow for easier access and editing * Modified the vote logic in admin.cs to clean up a ton of redundant if/else paths * Re-did the player collision logic in player.cs to make things a whole lot easier to modify in the future * Did a pass through all of the weapon files, cleaning the code up and making each unique weapon have its own damage type. @@ -141,10 +148,13 @@ PLEASE NOTE: I've moved all old changelogs into the version_history folder. This * Added a 100.0 damage modifier to all zombie types for Blade of Vengeance * This includes player zombies. * Removed the clause that bosses could not be damaged by the Blade of Vengeance - * Bosses now take 65HP damage from the blade. + * Bosses now take 6.5 (650 HP) damage from the blade. * Plasmasaber * Removed the damage flag on player type - * Now deals a flat damage of 5.0 to all targets (OHK to all players, low tier zombies), 500HP damage to bosses. + * Now deals a flat damage of 5.0 to all targets (OHK to all players, low tier zombies), 500 HP damage to bosses. + * Reduced the melee attack cooldown from 1.5 seconds to 0.8 seconds. + * Holding the Plasmasaber will grant you a protective buff preventing zombie infection from impact damage. + * You can still be infected by taking zombie based projectile damage. * Sidearms * At the moment, the two statistical outliers in the pool (Crimson Hawk and Pulse Phaser) feel close to being perfect, some minor tuning will help get them there. * Crimson Hawk Pistol diff --git a/scripts/TWM2/ArmorFunctions.cs b/scripts/TWM2/ArmorFunctions.cs index eac10e3..1b3e0dd 100644 --- a/scripts/TWM2/ArmorFunctions.cs +++ b/scripts/TWM2/ArmorFunctions.cs @@ -1,153 +1,153 @@ //CUSTOM ARMOR FUNCTIONS function MicroburstMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 4) { - // Throw grenade - if (%val == 1) { - %player.grenTimer = 1; - } - else { - if (%player.grenTimer == 0) { - // Bad throw for some reason - } - else { - %player.use(Grenade); - %player.grenTimer = 0; - } - } - } - else if (%triggerNum == 5) { - // Throw mine - if (%val == 1) { - %player.mineTimer = 1; - } - else { - if (%player.mineTimer == 0) { - // Bad throw for some reason - } - else { - if(%player.inv[C4] > 0) { - %player.use(C4); - %player.mineTimer = 0; - } - else { - %player.use(Mine); - %player.mineTimer = 0; - } - } - } - } - else if (%triggerNum == 3) { - // val = 1 when jet key (LMB) first pressed down - // val = 0 when jet key released - // MES - do we need this at all any more? - if(!%player.CantFireS3Shock) { - %image = %player.getMountedImage($WeaponSlot).getName(); + if (%triggerNum == 4) { + // Throw grenade + if (%val == 1) { + %player.grenTimer = 1; + } + else { + if (%player.grenTimer == 0) { + // Bad throw for some reason + } + else { + %player.use(Grenade); + %player.grenTimer = 0; + } + } + } + else if (%triggerNum == 5) { + // Throw mine + if (%val == 1) { + %player.mineTimer = 1; + } + else { + if (%player.mineTimer == 0) { + // Bad throw for some reason + } + else { + if(%player.inv[C4] > 0) { + %player.use(C4); + %player.mineTimer = 0; + } + else { + %player.use(Mine); + %player.mineTimer = 0; + } + } + } + } + else if (%triggerNum == 3) { + // val = 1 when jet key (LMB) first pressed down + // val = 0 when jet key released + // MES - do we need this at all any more? + if(!%player.CantFireS3Shock) { + %image = %player.getMountedImage($WeaponSlot).getName(); - if(%image $= "S3RifleImage") { - %obj = %player; - %slot = 0; - //Shocklance Stuff - %muzzlePos = %obj.getMuzzlePoint(%slot); - %muzzleVec = %obj.getMuzzleVector(%slot); + if(%image $= "S3RifleImage") { + %obj = %player; + %slot = 0; + //Shocklance Stuff + %muzzlePos = %obj.getMuzzlePoint(%slot); + %muzzleVec = %obj.getMuzzleVector(%slot); - %endPos = VectorAdd(%muzzlePos, VectorScale(%muzzleVec, S3Shocker.extension)); + %endPos = VectorAdd(%muzzlePos, VectorScale(%muzzleVec, S3Shocker.extension)); - %damageMasks = $TypeMasks::PlayerObjectType | $TypeMasks::VehicleObjectType | - $TypeMasks::StationObjectType | $TypeMasks::GeneratorObjectType | - $TypeMasks::SensorObjectType | $TypeMasks::TurretObjectType; + %damageMasks = $TypeMasks::PlayerObjectType | $TypeMasks::VehicleObjectType | + $TypeMasks::StationObjectType | $TypeMasks::GeneratorObjectType | + $TypeMasks::SensorObjectType | $TypeMasks::TurretObjectType; - %everythingElseMask = $TypeMasks::TerrainObjectType | - $TypeMasks::InteriorObjectType | - $TypeMasks::ForceFieldObjectType | - $TypeMasks::StaticObjectType | - $TypeMasks::MoveableObjectType | - $TypeMasks::DamagableItemObjectType; + %everythingElseMask = $TypeMasks::TerrainObjectType | + $TypeMasks::InteriorObjectType | + $TypeMasks::ForceFieldObjectType | + $TypeMasks::StaticObjectType | + $TypeMasks::MoveableObjectType | + $TypeMasks::DamagableItemObjectType; - // did I miss anything? players, vehicles, stations, gens, sensors, turrets - %hit = ContainerRayCast(%muzzlePos, %endPos, %damageMasks | %everythingElseMask, %obj); + // did I miss anything? players, vehicles, stations, gens, sensors, turrets + %hit = ContainerRayCast(%muzzlePos, %endPos, %damageMasks | %everythingElseMask, %obj); - %noDisplay = true; - if (%hit !$= "0") { - %obj.setEnergyLevel(%obj.getEnergyLevel() - 15); + %noDisplay = true; + if (%hit !$= "0") { + %obj.setEnergyLevel(%obj.getEnergyLevel() - 15); - %hitobj = getWord(%hit, 0); - %hitpos = getWord(%hit, 1) @ " " @ getWord(%hit, 2) @ " " @ getWord(%hit, 3); + %hitobj = getWord(%hit, 0); + %hitpos = getWord(%hit, 1) @ " " @ getWord(%hit, 2) @ " " @ getWord(%hit, 3); - if ( %hitObj.getType() & %damageMasks ) { - %hitobj.applyImpulse(%hitpos, VectorScale(%muzzleVec, S3Shocker.impulse)); - %obj.playAudio(0, ShockLanceHitSound); + if ( %hitObj.getType() & %damageMasks ) { + %hitobj.applyImpulse(%hitpos, VectorScale(%muzzleVec, S3Shocker.impulse)); + %obj.playAudio(0, ShockLanceHitSound); - // This is truly lame, but we need the sourceobject property present... - %p = new ShockLanceProjectile() { - dataBlock = S3Shocker; - initialDirection = %obj.getMuzzleVector(%slot); - initialPosition = %obj.getMuzzlePoint(%slot); - sourceObject = %obj; - sourceSlot = %slot; - targetId = %hit; - }; - MissionCleanup.add(%p); - %p.WeaponImageSource = "S3RifleImage"; + // This is truly lame, but we need the sourceobject property present... + %p = new ShockLanceProjectile() { + dataBlock = S3Shocker; + initialDirection = %obj.getMuzzleVector(%slot); + initialPosition = %obj.getMuzzlePoint(%slot); + sourceObject = %obj; + sourceSlot = %slot; + targetId = %hit; + }; + MissionCleanup.add(%p); + %p.WeaponImageSource = "S3RifleImage"; - %damageMultiplier = 1.0; + %damageMultiplier = 1.0; - if(%hitObj.getDataBlock().getClassName() $= "PlayerData") { - // Now we see if we hit from behind... - %forwardVec = %hitobj.getForwardVector(); - %objDir2D = getWord(%forwardVec, 0) @ " " @ getWord(%forwardVec,1) @ " " @ "0.0"; - %objPos = %hitObj.getPosition(); - %dif = VectorSub(%objPos, %muzzlePos); - %dif = getWord(%dif, 0) @ " " @ getWord(%dif, 1) @ " 0"; - %dif = VectorNormalize(%dif); - %dot = VectorDot(%dif, %objDir2D); + if(%hitObj.getDataBlock().getClassName() $= "PlayerData") { + // Now we see if we hit from behind... + %forwardVec = %hitobj.getForwardVector(); + %objDir2D = getWord(%forwardVec, 0) @ " " @ getWord(%forwardVec,1) @ " " @ "0.0"; + %objPos = %hitObj.getPosition(); + %dif = VectorSub(%objPos, %muzzlePos); + %dif = getWord(%dif, 0) @ " " @ getWord(%dif, 1) @ " 0"; + %dif = VectorNormalize(%dif); + %dot = VectorDot(%dif, %objDir2D); - // 120 Deg angle test... - // 1.05 == 60 degrees in radians - if (%dot >= mCos(1.05)) { - // Rear hit - %damageMultiplier = 3.0; - } - } + // 120 Deg angle test... + // 1.05 == 60 degrees in radians + if (%dot >= mCos(1.05)) { + // Rear hit + %damageMultiplier = 3.0; + } + } - %totalDamage = S3Shocker.DirectDamage * %damageMultiplier; - %hitObj.getDataBlock().damageObject(%hitobj, %p.sourceObject, %hitpos, %totalDamage, $DamageType::ShockLance); + %totalDamage = S3Shocker.DirectDamage * %damageMultiplier; + %hitObj.getDataBlock().damageObject(%hitobj, %p.sourceObject, %hitpos, %totalDamage, $DamageType::ShockLance); - %noDisplay = false; - } - } - if( %noDisplay ) { - // Miss - %obj.setEnergyLevel(%obj.getEnergyLevel() - 0); - %obj.playAudio(0, ShockLanceMissSound); + %noDisplay = false; + } + } + if( %noDisplay ) { + // Miss + %obj.setEnergyLevel(%obj.getEnergyLevel() - 0); + %obj.playAudio(0, ShockLanceMissSound); - %p = new ShockLanceProjectile() { - dataBlock = S3Shocker; - initialDirection = %obj.getMuzzleVector(%slot); - initialPosition = %obj.getMuzzlePoint(%slot); - sourceObject = %obj; - sourceSlot = %slot; - }; - MissionCleanup.add(%p); - %p.WeaponImageSource = "S3RifleImage"; - } - //END STUFF - %player.CantFireS3Shock = 1; - schedule(6000, 0, "ResetS3Shock", %player); - } - } - } + %p = new ShockLanceProjectile() { + dataBlock = S3Shocker; + initialDirection = %obj.getMuzzleVector(%slot); + initialPosition = %obj.getMuzzlePoint(%slot); + sourceObject = %obj; + sourceSlot = %slot; + }; + MissionCleanup.add(%p); + %p.WeaponImageSource = "S3RifleImage"; + } + //END STUFF + %player.CantFireS3Shock = 1; + schedule(6000, 0, "ResetS3Shock", %player); + } + } + } } function MicroburstFemaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val) { - MicroburstMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); + MicroburstMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); } function MicroburstMaleBiodermArmor::onTrigger(%data, %player, %triggerNum, %val) { - MicroburstMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); + MicroburstMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); } function ResetS3Shock(%player) { - %player.CantFireS3Shock = 0; + %player.CantFireS3Shock = 0; } @@ -173,75 +173,75 @@ function ResetS3Shock(%player) { function ShadowCommandoMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 4) { - // Throw grenade - if (%val == 1) { - %player.grenTimer = 1; - } - else { - if (%player.grenTimer == 0) { - // Bad throw for some reason - } - else { - %player.use(Grenade); - %player.grenTimer = 0; - } - } - } - else if (%triggerNum == 5) { - // Throw mine - if (%val == 1) { - %player.mineTimer = 1; - } - else { - if (%player.mineTimer == 0) { - // Bad throw for some reason - } - else { - if(%player.inv[C4] > 0) { - %player.use(C4); - %player.mineTimer = 0; - } - else { - %player.use(Mine); - %player.mineTimer = 0; - } - } - } - } - else if (%triggerNum == 3) { - // val = 1 when jet key (LMB) first pressed down - // val = 0 when jet key released - // MES - do we need this at all any more? - if(%player.RecentAttack["Shade"] == 1) { - return; - } - else { - messageClient(%player.client, 'MsgShd', "\c5TWM2: Activating Shade"); - %player.RecentAttack["Shade"] = 1; - schedule(90000, 0, "ResetPlayerDLAttack", %player, "Shade"); - %player.zapObject(); - %player.setCloaked(true); - %player.setCloakStatus(true); - %player.startFade(2000, 0, true); - %player.schedule(15000, "zapObject"); - %player.schedule(15000, "setCloaked", false); - %player.schedule(15000, "startFade", 5000, 0, false); - %player.schedule(15000, "setCloakStatus", false); - } - } + if (%triggerNum == 4) { + // Throw grenade + if (%val == 1) { + %player.grenTimer = 1; + } + else { + if (%player.grenTimer == 0) { + // Bad throw for some reason + } + else { + %player.use(Grenade); + %player.grenTimer = 0; + } + } + } + else if (%triggerNum == 5) { + // Throw mine + if (%val == 1) { + %player.mineTimer = 1; + } + else { + if (%player.mineTimer == 0) { + // Bad throw for some reason + } + else { + if(%player.inv[C4] > 0) { + %player.use(C4); + %player.mineTimer = 0; + } + else { + %player.use(Mine); + %player.mineTimer = 0; + } + } + } + } + else if (%triggerNum == 3) { + // val = 1 when jet key (LMB) first pressed down + // val = 0 when jet key released + // MES - do we need this at all any more? + if(%player.RecentAttack["Shade"] == 1) { + return; + } + else { + messageClient(%player.client, 'MsgShd', "\c5TWM2: Activating Shade"); + %player.RecentAttack["Shade"] = 1; + schedule(90000, 0, "ResetPlayerDLAttack", %player, "Shade"); + %player.zapObject(); + %player.setCloaked(true); + %player.setCloakStatus(true); + %player.startFade(2000, 0, true); + %player.schedule(15000, "zapObject"); + %player.schedule(15000, "setCloaked", false); + %player.schedule(15000, "startFade", 5000, 0, false); + %player.schedule(15000, "setCloakStatus", false); + } + } } function Player::setCloakStatus(%player, %status) { - %player.stealthed = %status; + %player.stealthed = %status; } function ShadowCommandoFemaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val) { - ShadowCommandoMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); + ShadowCommandoMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); } function ShadowCommandoMaleBiodermArmor::onTrigger(%data, %player, %triggerNum, %val) { - ShadowCommandoMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); + ShadowCommandoMaleHumanArmor::onTrigger(%data, %player, %triggerNum, %val); } @@ -263,20 +263,20 @@ function ShadowCommandoMaleBiodermArmor::onTrigger(%data, %player, %triggerNum, //ZOMBAHS function ZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { - if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) - %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); - } - } + if (%triggerNum == 3) { + if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) + %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); + } + } } function LordZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 0) { //shooting - PlayerLordFire1(%player); - } - else if (%triggerNum == 5) { //lifting - playerLiftTarget(%player,0); - } + if (%triggerNum == 0) { //shooting + PlayerLordFire1(%player); + } + else if (%triggerNum == 5) { //lifting + playerLiftTarget(%player,0); + } } function SniperZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { @@ -317,11 +317,11 @@ function DemonZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { return; } %p = new GrenadeProjectile() { - dataBlock = DemonFireball; - initialDirection = %player.getMuzzleVector(0); - initialPosition = vectoradd(%player.getMuzzlePoint(0), "0 0 1.5"); - sourceObject = %player; - sourceSlot = 6; + dataBlock = DemonFireball; + initialDirection = %player.getMuzzleVector(0); + initialPosition = vectoradd(%player.getMuzzlePoint(0), "0 0 1.5"); + sourceObject = %player; + sourceSlot = 6; }; MissionCleanup.add(%p); %player.recharging = 1; @@ -330,358 +330,317 @@ function DemonZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { } function RapierZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { //flying - if(%val == 1) - %player.isJetting = true; - else { - %player.isJetting = false; - } - } - if (%triggerNum == 0) { //speeding - if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) - %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); - } - } + if (%triggerNum == 3) { //flying + if(%val == 1) { + %player.isJetting = true; + } + else { + %player.isJetting = false; + } + } + if (%triggerNum == 0) { //speeding + if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) + %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); + } + } } function ResetPlayerDLAttack(%player, %attack) { - %player.RecentAttack[""@%attack@""] = 0; + %player.RecentAttack[""@%attack@""] = 0; } function DemonMotherZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 0) { //shooting - PlayerLordFire1(%player); - } - else if (%triggerNum == 3) { //flying - if(%player.RecentAttack["Fly"] == 1) { - return; - } - else { - %attack = getRandom(1, 2); - %targetInfo = ZombieLookforTarget(%player); - %target = getWord(%targetInfo, 0); - if(%target.player.IsAlive()) { - %player.RecentAttack["Fly"] = 1; - schedule(17000, 0, "ResetPlayerDLAttack", %player, "Fly"); - if(%attack == 1) { - PlayerDemonLordFlyAttack(%player, %target.player); - } - else { - PlayerDemonLordPlasmaAttack(%player, %target.player); - } - } - } - } - else if (%triggerNum == 4) { - if(%player.RecentAttack["Missile"] == 1) { - return; - } - else { - %targetInfo = ZombieLookforTarget(%player); - %target = getWord(%targetInfo, 0); - if(%target.player.IsAlive()) { - %player.RecentAttack["Missile"] = 1; - schedule(17000, 0, "ResetPlayerDLAttack", %player, "Missile"); - //t3h missile - %target = %target.player; - %vec = vectorNormalize(vectorSub(%target.getPosition(),%player.getPosition())); - %p = new SeekerProjectile() { - dataBlock = DMMissile; - initialDirection = %vec; - initialPosition = %player.getMuzzlePoint(4); - sourceObject = %player; - 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); - // - } - } - } - else if (%triggerNum == 5) { - if(%player.RecentAttack["Firestorm"] == 1) { - return; - } - else { - %targetInfo = ZombieLookforTarget(%player); - %target = getWord(%targetInfo, 0); - if(%target.player.IsAlive()) { - %player.RecentAttack["Firestorm"] = 1; - schedule(17000, 0, "ResetPlayerDLAttack", %player, "Firestorm"); - PlayerDemonLordFireRainAttack(%player, %target.player); - } - } - } + if (%triggerNum == 0) { //shooting + PlayerLordFire1(%player); + } + else if (%triggerNum == 3) { //flying + if(%player.RecentAttack["Fly"] == 1) { + return; + } + else { + %attack = getRandom(1, 2); + %targetInfo = TWM2Lib_Zombie_Core("lookForTarget", %player); + %target = getWord(%targetInfo, 0); + if(%target.player.IsAlive()) { + %player.RecentAttack["Fly"] = 1; + schedule(17000, 0, "ResetPlayerDLAttack", %player, "Fly"); + if(%attack == 1) { + PlayerDemonLordFlyAttack(%player, %target.player); + } + else { + PlayerDemonLordPlasmaAttack(%player, %target.player); + } + } + } + } + else if (%triggerNum == 4) { + if(%player.RecentAttack["Missile"] == 1) { + return; + } + else { + %targetInfo = TWM2Lib_Zombie_Core("lookForTarget", %player); + %target = getWord(%targetInfo, 0); + if(%target.player.IsAlive()) { + %player.RecentAttack["Missile"] = 1; + schedule(17000, 0, "ResetPlayerDLAttack", %player, "Missile"); + //t3h missile + %target = %target.player; + %vec = vectorNormalize(vectorSub(%target.getPosition(),%player.getPosition())); + createMissileSeekingProjectile("DMMissile", %target, %player, %player.getMuzzlePoint(4), %vec, 4, 100); + // + } + } + } + else if (%triggerNum == 5) { + if(%player.RecentAttack["Firestorm"] == 1) { + return; + } + else { + %targetInfo = TWM2Lib_Zombie_Core("lookForTarget", %player); + %target = getWord(%targetInfo, 0); + if(%target.player.IsAlive()) { + %player.RecentAttack["Firestorm"] = 1; + schedule(17000, 0, "ResetPlayerDLAttack", %player, "Firestorm"); + PlayerDemonLordFireRainAttack(%player, %target.player); + } + } + } } function YvexZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 0) { //shooting - if(%player.RecentAttack["Pulse"] == 1) { - return; - } - else { - %attack = getRandom(1, 2); - %player.RecentAttack["Pulse"] = 1; - schedule(14000, 0, "ResetPlayerDLAttack", %player, "Pulse"); - if(%attack == 1) { - %p = new LinearFlareProjectile() { - dataBlock = KillerPulse; - initialDirection = %player.getMuzzleVector(0); - initialPosition = %player.getMuzzlePoint(0); - sourceObject = %player; - sourceSlot = 0; - }; - } - else { - %p = new LinearFlareProjectile() { - dataBlock = YvexSniperShot; - initialDirection = %player.getMuzzleVector(0); - initialPosition = %player.getMuzzlePoint(0); - sourceObject = %player; - sourceSlot = 0; - }; - } - } - } - else if (%triggerNum == 3) { //flying - if(%player.RecentAttack["RandNight"] == 1) { - return; - } - else { - %player.RecentAttack["RandNight"] = 1; - schedule(20000, 0, "ResetPlayerDLAttack", %player, "RandNight"); - %client = FindValidTarget(%player); - %counts = 0; - messageClient(%player.client,'msgZombie',"\c3Attempting Random Nightmare."); - if(isObject(%client.player) && %client.player.getState !$= "dead" && !%client.ignoredbyZombs) { - %c = createEmitter(%client.player.position,InfNightmareGlobeEmitter,"1 0 0"); //Rotate it - MissionCleanup.add(%c); // I think This should be used - schedule(3000,0,"killit",%c); - %luck = getrandom(1,5); - switch(%luck) { - case 1: - messageClient(%player.client,'msgZombie',"\c3Success!!!"); - Yvexnightmareloop(%player,%client); - messageClient(%client,'msgClient',"~wfx/misc/diagnostic_on.wav"); - case 2: - messageClient(%player.client,'msgZombie',"\c3Failed."); - case 3: - messageClient(%player.client,'msgZombie',"\c3Success!!!"); - Yvexnightmareloop(%player,%client); - messageClient(%client,'msgClient',"~wfx/misc/diagnostic_on.wav"); - case 4: - messageClient(%player.client,'msgZombie',"\c3Failed."); - case 5: - messageClient(%player.client,'msgZombie',"\c3Success!!!"); - Yvexnightmareloop(%player,%client); - messageClient(%client,'msgClient',"~wfx/misc/diagnostic_on.wav"); - } - } - else { - messageClient(%player.client,'msgZombie',"\c3Failed."); - } - } - } - else if (%triggerNum == 4) { - if(%player.RecentAttack["Missile"] == 1) { - return; - } - else { - %targetInfo = ZombieLookforTarget(%player); - %target = getWord(%targetInfo, 0); - if(%target.player.IsAlive()) { - %player.RecentAttack["Missile"] = 1; - schedule(27500, 0, "ResetPlayerDLAttack", %player, "Missile"); - //t3h missile - %target = %target.player; - %vec = vectorNormalize(vectorSub(%target.getPosition(),%player.getPosition())); - %p = new SeekerProjectile() { - dataBlock = YvexZombieMakerMissile; - initialDirection = %vec; - initialPosition = %player.getMuzzlePoint(4); - sourceObject = %player; - 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); - // - } - } - } - else if (%triggerNum == 5) { - if(%player.RecentAttack["Summon"] == 1) { - return; - } - else { - %player.RecentAttack["Summon"] = 1; - schedule(40000, 0, "ResetPlayerDLAttack", %player, "Summon"); - PlayerSummon(%player, 5); - } - } + if (%triggerNum == 0) { //shooting + if(%player.RecentAttack["Pulse"] == 1) { + return; + } + else { + %attack = getRandom(1, 2); + %player.RecentAttack["Pulse"] = 1; + schedule(14000, 0, "ResetPlayerDLAttack", %player, "Pulse"); + if(%attack == 1) { + %p = new LinearFlareProjectile() { + dataBlock = KillerPulse; + initialDirection = %player.getMuzzleVector(0); + initialPosition = %player.getMuzzlePoint(0); + sourceObject = %player; + sourceSlot = 0; + }; + } + else { + %p = new LinearFlareProjectile() { + dataBlock = YvexSniperShot; + initialDirection = %player.getMuzzleVector(0); + initialPosition = %player.getMuzzlePoint(0); + sourceObject = %player; + sourceSlot = 0; + }; + } + } + } + else if (%triggerNum == 3) { //flying + if(%player.RecentAttack["RandNight"] == 1) { + return; + } + else { + %player.RecentAttack["RandNight"] = 1; + schedule(20000, 0, "ResetPlayerDLAttack", %player, "RandNight"); + %client = FindValidTarget(%player); + %counts = 0; + messageClient(%player.client,'msgZombie',"\c3Attempting Random Nightmare."); + if(isObject(%client.player) && %client.player.getState !$= "dead" && !%client.ignoredbyZombs) { + %c = createEmitter(%client.player.position,InfNightmareGlobeEmitter,"1 0 0"); //Rotate it + MissionCleanup.add(%c); // I think This should be used + schedule(3000, 0, "killit", %c); + %luck = getrandom(1, 5); + switch(%luck) { + case 1 or 3 or 5: + messageClient(%player.client, 'msgZombie', "\c3Success!!!"); + Yvexnightmareloop(%player, %client); + messageClient(%client, 'msgClient', "~wfx/misc/diagnostic_on.wav"); + case 2 or 4: + messageClient(%player.client, 'msgZombie', "\c3Failed."); + } + } + else { + messageClient(%player.client, 'msgZombie', "\c3Failed."); + } + } + } + else if (%triggerNum == 4) { + if(%player.RecentAttack["Missile"] == 1) { + return; + } + else { + %targetInfo = TWM2Lib_Zombie_Core("lookForTarget", %player); + %target = getWord(%targetInfo, 0); + if(%target.player.IsAlive()) { + %player.RecentAttack["Missile"] = 1; + schedule(27500, 0, "ResetPlayerDLAttack", %player, "Missile"); + //t3h missile + %target = %target.player; + %vec = vectorNormalize(vectorSub(%target.getPosition(), %player.getPosition())); + createMissileSeekingProjectile("YvexZombieMakerMissile", %target, %player, %player.getMuzzlePoint(4), %vec, 4, 100); + // + } + } + } + else if (%triggerNum == 5) { + if(%player.RecentAttack["Summon"] == 1) { + return; + } + else { + %player.RecentAttack["Summon"] = 1; + schedule(40000, 0, "ResetPlayerDLAttack", %player, "Summon"); + PlayerSummon(%player, 5); + } + } } function LordRogZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 0) { //shooting - if(%player.RecentAttack["BOV"] == 1) { - return; - } - else { - %player.RecentAttack["BOV"] = 1; - schedule(1000, 0, "ResetPlayerDLAttack", %player, "BOV"); - %p = new (LinearProjectile)() { - dataBlock = BOVhit; - initialDirection = %player.getMuzzleVector(0); - initialPosition = %player.getMuzzlePoint(0); - sourceObject = %player; - sourceSlot = 0; - }; - MissionCleanup.add(%p); - } - } - else if (%triggerNum == 3) { //flying - if(%player.RecentAttack["Summon"] == 1) { - return; - } - else { - %player.RecentAttack["Summon"] = 1; - schedule(35000, 0, "ResetPlayerDLAttack", %player, "Summon"); - PlayerSummon(%player, 6); - } - } - else if (%triggerNum == 5) { - if(%player.RecentAttack["RandAttack"] == 1) { - return; - } - else { - %player.RecentAttack["RandAttack"] = 1; - schedule(27500, 0, "ResetPlayerDLAttack", %player, "RandAttack"); - PlayerLRAbilities(%player); - } - } + if (%triggerNum == 0) { //shooting + if(%player.RecentAttack["BOV"] == 1) { + return; + } + else { + %player.RecentAttack["BOV"] = 1; + schedule(1000, 0, "ResetPlayerDLAttack", %player, "BOV"); + %p = new (LinearProjectile)() { + dataBlock = BOVhit; + initialDirection = %player.getMuzzleVector(0); + initialPosition = %player.getMuzzlePoint(0); + sourceObject = %player; + sourceSlot = 0; + }; + MissionCleanup.add(%p); + } + } + else if (%triggerNum == 3) { //flying + if(%player.RecentAttack["Summon"] == 1) { + return; + } + else { + %player.RecentAttack["Summon"] = 1; + schedule(35000, 0, "ResetPlayerDLAttack", %player, "Summon"); + PlayerSummon(%player, 6); + } + } + else if (%triggerNum == 5) { + if(%player.RecentAttack["RandAttack"] == 1) { + return; + } + else { + %player.RecentAttack["RandAttack"] = 1; + schedule(27500, 0, "ResetPlayerDLAttack", %player, "RandAttack"); + PlayerLRAbilities(%player); + } + } } function ShifterZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { //flying - if(%player.RecentAttack["Teleport"] == 1) { - return; - } - else { - %targetInfo = ZombieLookforTarget(%player); - %target = getWord(%targetInfo, 0); - if(%target.player.IsAlive()) { - %player.RecentAttack["Teleport"] = 1; - schedule(3500, 0, "ResetPlayerDLAttack", %player, "Teleport"); - %player.setVelocity("0 0 10"); - %player.startFade(500, 0, true); - %player.schedule(600, "SetPosition", VectorAdd(%target.player.getPosition(), "0 0 3")); - %player.startFade(750, 0, false); - } - } - } + if (%triggerNum == 3) { //flying + if(%player.RecentAttack["Teleport"] == 1) { + return; + } + else { + %targetInfo = TWM2Lib_Zombie_Core("lookForTarget", %player); + %target = getWord(%targetInfo, 0); + if(%target.player.IsAlive()) { + %player.RecentAttack["Teleport"] = 1; + schedule(3500, 0, "ResetPlayerDLAttack", %player, "Teleport"); + %player.setVelocity("0 0 10"); + %player.startFade(500, 0, true); + %player.schedule(600, "SetPosition", VectorAdd(%target.player.getPosition(), "0 0 3")); + %player.startFade(750, 0, false); + } + } + } } function SummonerZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { //flying - if(%player.RecentAttack["Summon"] == 1) { - return; - } - else { - %player.RecentAttack["Summon"] = 1; - schedule(25000, 0, "ResetPlayerDLAttack", %player, "Summon"); - %Ct = GetRandom(1,3); - %type = GetRandom(1, 8); - if(%type > 5) { - %type += 3; - if(%type == 10) { //summoners don;t summon more summoners - %type = 12; - } - } - %SumPos = vectorAdd(VectorAdd(TWM2Lib_MainControl("getRandomPosition", 20 TAB 1), "0 0 7"), %player.getPosition()); - %c = CreateEmitter(%SumPos, NightmareGlobeEmitter, "0 0 1"); - %c.schedule(((%Ct * 1000) + 500), "delete"); - for(%i = 1; %i <= %ct; %i++) { - %time = %i * 1000; - schedule(%time, 0, "TWM2Lib_Zombie_Core" "SpawnZombie", "zSpawnCommand", %type, %SumPos); - } - } - } + if (%triggerNum == 3) { //flying + if(%player.RecentAttack["Summon"] == 1) { + return; + } + else { + %player.RecentAttack["Summon"] = 1; + schedule(25000, 0, "ResetPlayerDLAttack", %player, "Summon"); + %Ct = GetRandom(1, 3); + %type = GetRandom(1, 8); + if(%type > 5) { + %type += 3; + if(%type == 10) { //summoners don;t summon more summoners + %type = 12; + } + } + %SumPos = vectorAdd(VectorAdd(TWM2Lib_MainControl("getRandomPosition", 20 TAB 1), "0 0 7"), %player.getPosition()); + %c = CreateEmitter(%SumPos, NightmareGlobeEmitter, "0 0 1"); + %c.schedule(((%Ct * 1000) + 500), "delete"); + for(%i = 1; %i <= %ct; %i++) { + %time = %i * 1000; + schedule(%time, 0, "TWM2Lib_Zombie_Core" "SpawnZombie", "zSpawnCommand", %type, %SumPos); + } + } + } } function DemonUltraZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 0) { //shooting - if(%player.recharging) { - return; - } - %p = new GrenadeProjectile() { - dataBlock = DemonFireball; - initialDirection = %player.getMuzzleVector(0); - initialPosition = vectoradd(%player.getMuzzlePoint(0), "0 0 1.5"); - sourceObject = %player; - sourceSlot = 6; - }; - MissionCleanup.add(%p); - %player.recharging = 1; - schedule(1000,0,"ResetZombieCharge",%player); - } - else if (%triggerNum == 3) { - if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) - %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); - createBiodermProjection(%player); - } - } + if (%triggerNum == 0) { //shooting + if(%player.recharging) { + return; + } + %p = new GrenadeProjectile() { + dataBlock = DemonFireball; + initialDirection = %player.getMuzzleVector(0); + initialPosition = vectoradd(%player.getMuzzlePoint(0), "0 0 1.5"); + sourceObject = %player; + sourceSlot = 6; + }; + MissionCleanup.add(%p); + %player.recharging = 1; + schedule(1000,0,"ResetZombieCharge", %player); + } + else if (%triggerNum == 3) { + if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) + %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); + createBiodermProjection(%player); + } + } } function VolatileRavagerZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { - if(!%player.detonatedVRavC4) { - ServerPlay3D("SatchelChargeExplosionSound", %player.getPosition()); - %c4 = new Item() { - datablock = C4Deployed; - position = %player.getPosition(); - scale = ".1 .1 .1"; - }; - MissionCleanup.add(%c4); - schedule(770, 0, "C4GoBoom", %c4); - - %c4.theClient = %player.client; - %player.detonatedVRavC4 = true; - return; - } - } + if (%triggerNum == 3) { + if(!%player.detonatedVRavC4) { + ServerPlay3D("SatchelChargeExplosionSound", %player.getPosition()); + %c4 = new Item() { + datablock = C4Deployed; + position = %player.getPosition(); + scale = ".1 .1 .1"; + }; + MissionCleanup.add(%c4); + schedule(770, 0, "C4GoBoom", %c4); + + %c4.theClient = %player.client; + %player.detonatedVRavC4 = true; + return; + } + } } function WraithZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { - if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) - %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); - } - } + if (%triggerNum == 3) { + if(vectorLen(%player.getVelocity()) < 30) { //we dont want hyper speed zombies :) + %player.applyImpulse(%player.getPosition(),vectorScale(%player.getMuzzleVector(0),$Zombie::forwardspeed)); + } + } } function ROGZombieArmor::onTrigger(%data, %player, %triggerNum, %val) { - if (%triggerNum == 3) { - if(%player.state["canUseMG"]) { - playerRogFire(%player); - } - } - - if(%triggerNum == 0) { - %player.SALoop = RapierShieldAttack(%player, %val, 0); - } + if (%triggerNum == 3) { + if(%player.state["canUseMG"]) { + playerRogFire(%player); + } + } + + if(%triggerNum == 0) { + %player.SALoop = RapierShieldAttack(%player, %val, 0); + } } diff --git a/scripts/TWM2/Bosses/ColonelWindshear.cs b/scripts/TWM2/Bosses/ColonelWindshear.cs index 23b04d1..a39e2a0 100644 --- a/scripts/TWM2/Bosses/ColonelWindshear.cs +++ b/scripts/TWM2/Bosses/ColonelWindshear.cs @@ -127,50 +127,6 @@ function DroneFindNearestPilot(%radius, %drone) { return %closestClient; } - -datablock SeekerProjectileData(BossMissiles) -{ - casingShapeName = "weapon_missile_casement.dts"; - projectileShapeName = "weapon_missile_projectile.dts"; - hasDamageRadius = true; - indirectDamage = 0.1; - damageRadius = 6.0; - radiusDamageType = $DamageType::MissileTurret; - kickBackStrength = 500; - - flareDistance = 200; - flareAngle = 30; - minSeekHeat = 0.0; - - explosion = "MissileExplosion"; - velInheritFactor = 1.0; - - splash = MissileSplash; - baseEmitter = MortarSmokeEmitter; - delayEmitter = MissileFireEmitter; - puffEmitter = MissilePuffEmitter; - - lifetimeMS = 15000; // z0dd - ZOD, 4/14/02. Was 6000 - muzzleVelocity = 12.0; - maxVelocity = 225.0; // z0dd - ZOD, 4/14/02. Was 80.0 - turningSpeed = 50.0; - acceleration = 100.0; - - proximityRadius = 4; - - terrainAvoidanceSpeed = 100; - terrainScanAhead = 50; - terrainHeightFail = 50; - terrainAvoidanceRadius = 150; - - useFlechette = true; - flechetteDelayMs = 225; - casingDeb = FlechetteDebris; -}; - - - - function WindshearAttacks(%drone) { if(!isObject(%drone)) { return; diff --git a/scripts/TWM2/Bosses/GeneralVegenor.cs b/scripts/TWM2/Bosses/GeneralVegenor.cs index 134455b..1a22663 100644 --- a/scripts/TWM2/Bosses/GeneralVegenor.cs +++ b/scripts/TWM2/Bosses/GeneralVegenor.cs @@ -292,23 +292,7 @@ function VegenorAttack_FUNC(%att, %args) { case "FlameMissileSingle": %Tobj = getWord(%args, 0); %vec = vectorNormalize(vectorSub(%Tobj.getPosition(), %z.getPosition())); - %p = new SeekerProjectile() { - dataBlock = VegenorFireMissile; - initialDirection = %vec; - initialPosition = %z.getMuzzlePoint(4); - sourceObject = %z; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %Tobj.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%Tobj, %beacon,%p); + createMissileSeekingProjectile("VegenorFireMissile", %Tobj, %z, %z.getMuzzlePoint(4), %vec, 4, 100); case "MeteorDrop": %t = getWord(%args, 0); %fpos = vectoradd(%t.getposition(), TWM2Lib_MainControl("getRandomPosition", 50 TAB 0)); diff --git a/scripts/TWM2/Bosses/GhostOfLightning.cs b/scripts/TWM2/Bosses/GhostOfLightning.cs index b78faea..53bd760 100644 --- a/scripts/TWM2/Bosses/GhostOfLightning.cs +++ b/scripts/TWM2/Bosses/GhostOfLightning.cs @@ -260,23 +260,7 @@ function DoGoLAttacks(%ghost) { } MessageAll('msgBossAlertAttack', "\c4"@$TWM2::BossName["GoL"]@": Watch Electricity Chase You!!!"); %vec = vectorNormalize(vectorSub(%target.player.getPosition(),%ghost.getPosition())); - %p = new SeekerProjectile() { - dataBlock = IonMissile; - initialDirection = %vec; - initialPosition = %ghost.getMuzzlePoint(0); - sourceObject = %ghost; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %target.player.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%target.player,%beacon,%p); + createMissileSeekingProjectile("IonMissile", %target, %ghost, %ghost.getMuzzlePoint(0), %vec, 4, 100); case 3: %target = FindValidTarget(%ghost); if(!isObject(%target.player)) { @@ -307,23 +291,7 @@ function DoGoLAttacks(%ghost) { %cl = ClientGroup.getObject(%i); if(isObject(%cl.player) && %cl.player.getState() !$= "dead") { %vec = vectorNormalize(vectorSub(%cl.player.getPosition(),%ghost.getPosition())); - %p = new SeekerProjectile() { - dataBlock = IonMissile; - initialDirection = %vec; - initialPosition = %ghost.getMuzzlePoint(0); - sourceObject = %ghost; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %cl.player.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%cl.player,%beacon,%p); + createMissileSeekingProjectile("IonMissile", %cl.player, %ghost, %ghost.getMuzzlePoint(4), %vec, 4, 100); } } } diff --git a/scripts/TWM2/Bosses/LordVardison.cs b/scripts/TWM2/Bosses/LordVardison.cs index 653b326..9dbdd50 100644 --- a/scripts/TWM2/Bosses/LordVardison.cs +++ b/scripts/TWM2/Bosses/LordVardison.cs @@ -1443,23 +1443,7 @@ function VardisonNamedAttack(%Boss, %attack, %args) { %target = getField(%args, 0); %sPos = vectorAdd(%bPos, "0 0 25"); %vec = vectorNormalize(vectorSub(%target.getPosition(), %sPos)); - %p = new SeekerProjectile() { - dataBlock = YvexNightmareMissile; - initialDirection = %vec; - initialPosition = %sPos; - sourceSlot = 4; - }; - %p.sourceObject = %Boss; - %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); + createMissileSeekingProjectile("YvexNightmareMissile", %target, %Boss, %Boss.getMuzzlePoint(4), %vec, 4, 100); case "ShadowFissure": %sPos = getField(%args, 0); @@ -1485,23 +1469,7 @@ function VardisonNamedAttack(%Boss, %attack, %args) { %target = getField(%args, 0); %sPos = vectorAdd(%bPos, "0 0 25"); %vec = vectorNormalize(vectorSub(%target.getPosition(), %sPos)); - %p = new SeekerProjectile() { - dataBlock = VegenorFireMissile; - initialDirection = %vec; - initialPosition = %sPos; - sourceSlot = 4; - }; - %p.sourceObject = %Boss; - %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); + createMissileSeekingProjectile("VegenorFireMissile", %target, %Boss, %Boss.getMuzzlePoint(4), %vec, 4, 100); case "MinionFlood": //Summon Maximum Minions & then Phase out until the team drops them diff --git a/scripts/TWM2/Bosses/LordYvex.cs b/scripts/TWM2/Bosses/LordYvex.cs index 8b3fd2d..47f406e 100644 --- a/scripts/TWM2/Bosses/LordYvex.cs +++ b/scripts/TWM2/Bosses/LordYvex.cs @@ -22,629 +22,211 @@ $Boss::DamageScaling["Yvex"] = 5.0; $Boss::ScaleReduction["Yvex"] = 0.15; //DATABLOCKS -datablock ParticleData(InflictionNightmareGlobeSmoke) { - dragCoefficient = 50;/////////----------------------- - gravityCoefficient = 0.0; - inheritedVelFactor = 1.0; - constantAcceleration = 0.0; - lifetimeMS = 5050; - lifetimeVarianceMS = 0; - useInvAlpha = true; - spinRandomMin = -360.0; - spinRandomMax = 360.0; - textureName = "particleTest"; - colors[0] = "0.5 0.1 0.9 1.0"; - colors[1] = "0.5 0.1 0.9 1.0"; - colors[2] = "0.5 0.1 0.9 1.0"; - colors[3] = "0.5 0.1 0.9"; - sizes[0] = 1.0; - sizes[1] = 1.0; - sizes[2] = 1.0; - sizes[3] = 1.0; - times[0] = 0.0; - times[1] = 0.33; - times[2] = 0.66; - times[3] = 1.0; - mass = 0.7; - elasticity = 0.2; - friction = 1; - computeCRC = true; - haslight = true; - lightType = "PulsingLight"; - lightColor = "0.2 0.0 0.5 1.0"; - lightTime = "200"; - lightRadius = "2.0"; -}; - -datablock ParticleEmitterData(InfNightmareGlobeEmitter) { - ejectionPeriodMS = 0.1; - periodVarianceMS = 0; - ejectionVelocity = 0.0; - velocityVariance = 0.0; - ejectionOffset = 5; - thetaMin = 0; - thetaMax = 180; - overrideAdvances = false; - particles = "InflictionNightmareGlobeSmoke"; -}; - - -datablock ParticleData(NightmareGlobeSmoke) { - dragCoefficient = 50;/////////----------------------- - gravityCoefficient = 0.0; - inheritedVelFactor = 1.0; - constantAcceleration = 0.0; - lifetimeMS = 5050; - lifetimeVarianceMS = 0; - useInvAlpha = true; - spinRandomMin = -360.0; - spinRandomMax = 360.0; - textureName = "particleTest"; - colors[0] = "0.1 0.1 0.1 1.0";// //////////////////// - colors[1] = "0.1 0.1 0.1 1.0";// //////////////////// - colors[2] = "0.1 0.1 0.1 1.0";// \\\\\\\\\\\\\\\\\\\\ - colors[3] = "0.1 0.1 0.1 1.0";// \\\\\\\\\\\\\\\\\\\\ - sizes[0] = 1.0; - sizes[1] = 1.0; - sizes[2] = 1.0; - sizes[3] = 1.0; - times[0] = 0.0; - times[1] = 0.33; - times[2] = 0.66; - times[3] = 1.0; - mass = 0.7; - elasticity = 0.2; - friction = 1; - computeCRC = true; - haslight = true; - lightType = "PulsingLight"; - lightColor = "0.2 0.0 0.5 1.0"; - lightTime = "200"; - lightRadius = "2.0"; -}; - -datablock ParticleEmitterData(NightmareGlobeEmitter) { - ejectionPeriodMS = 0.1; - periodVarianceMS = 0; - ejectionVelocity = 0.0; - velocityVariance = 0.0; - ejectionOffset = 5; - thetaMin = 0; - thetaMax = 180; - overrideAdvances = false; - particles = "NightmareGlobeSmoke"; -}; - -//Yvex STUFF.. MORE -datablock ParticleData(GreenEmitParticle) { - dragCoeffiecient = 1; - gravityCoefficient = -0.3; // rises slowly - inheritedVelFactor = 0; - - lifetimeMS = 300; - lifetimeVarianceMS = 0; - useInvAlpha = false; - spinRandomMin = 0.0; - spinRandomMax = 0.0; - - animateTexture = false; - - textureName = "flareBase"; // "special/Smoke/bigSmoke" - - colors[0] = "0 1 0"; - colors[1] = "0 1 0"; - colors[2] = "0 1 0"; - - sizes[0] = 0.8; - sizes[1] = 0.8; - sizes[2] = 0.8; - - times[0] = 0.0; - times[1] = 1.0; - times[2] = 5.0; - -}; - -datablock ParticleEmitterData(PulseGreenEmitter) { - ejectionPeriodMS = 2; - periodVarianceMS = 1; - - ejectionVelocity = 10; - velocityVariance = 0; - - thetaMin = 89.0; - thetaMax = 90.0; - - orientParticles = false; - - particles = "GreenEmitParticle"; -}; - -datablock SeekerProjectileData(YvexNightmareMissile){ - casingShapeName = "weapon_missile_casement.dts"; - projectileShapeName = "weapon_missile_projectile.dts"; - hasDamageRadius = true; - indirectDamage = 0.8; - damageRadius = 8.0; - radiusDamageType = $DamageType::Missile; - 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 - - delayEmitter = MissileFireEmitter; - puffEmitter = MissilePuffEmitter; - bubbleEmitter = GrenadeBubbleEmitter; - bubbleEmitTime = 1.0; - - exhaustEmitter = MissileLauncherExhaustEmitter; - exhaustTimeMs = 300; - exhaustNodeName = "muzzlePoint1"; - - lifetimeMS = 30000; - muzzleVelocity = 10.0; - maxVelocity = 150.0; - turningSpeed = 110.0; - acceleration = 350.0; - - proximityRadius = 3; - - terrainAvoidanceSpeed = 180; - terrainScanAhead = 25; - terrainHeightFail = 12; - terrainAvoidanceRadius = 100; - - flareDistance = 200; - flareAngle = 30; - - sound = MissileProjectileSound; - - hasLight = true; - lightRadius = 5.0; - lightColor = "0.2 0.05 0"; - - useFlechette = true; - flechetteDelayMs = 550; - casingDeb = FlechetteDebris; - - explodeOnWaterImpact = false; - - baseEmitter = NMMissileBaseEmitter; -}; - function YvexNightmareMissile::OnExplode(%data, %proj, %pos, %mod) { - %source = %proj.SourceObject; - InitContainerRadiusSearch(%proj.getPosition(), 6, $TypeMasks::PlayerObjectType); - while ((%potentialTarget = ContainerSearchNext()) != 0) { - %cl = %potentialTarget.client; - if(%cl !$= "") - Yvexnightmareloop(%source, %cl); - } + %source = %proj.SourceObject; + InitContainerRadiusSearch(%proj.getPosition(), 6, $TypeMasks::PlayerObjectType); + while ((%potentialTarget = ContainerSearchNext()) != 0) { + %cl = %potentialTarget.client; + if(%cl !$= "") { + Yvexnightmareloop(%source, %cl); + } + } } datablock LinearFlareProjectileData(KillerPulse) { - scale = "1.0 1.0 1.0"; - faceViewer = false; - directDamage = 0.00001; - hasDamageRadius = false; - indirectDamage = 0.6; - damageRadius = 10.0; - kickBackStrength = 100.0; - directDamageType = $DamageType::Admin; - indirectDamageType = $DamageType::Admin; + scale = "1.0 1.0 1.0"; + faceViewer = false; + directDamage = 0.00001; + hasDamageRadius = false; + indirectDamage = 0.6; + damageRadius = 10.0; + kickBackStrength = 100.0; + directDamageType = $DamageType::Admin; + indirectDamageType = $DamageType::Admin; - explosion = "BlasterExplosion"; - splash = PlasmaSplash; + explosion = "BlasterExplosion"; + splash = PlasmaSplash; - dryVelocity = 200.0; - wetVelocity = 10; - velInheritFactor = 0.5; - fizzleTimeMS = 30000; - lifetimeMS = 30000; - explodeOnDeath = false; - reflectOnWaterImpactAngle = 0.0; - explodeOnWaterImpact = true; - deflectionOnWaterImpact = 0.0; - fizzleUnderwaterMS = -1; + dryVelocity = 200.0; + wetVelocity = 10; + velInheritFactor = 0.5; + fizzleTimeMS = 30000; + lifetimeMS = 30000; + explodeOnDeath = false; + reflectOnWaterImpactAngle = 0.0; + explodeOnWaterImpact = true; + deflectionOnWaterImpact = 0.0; + fizzleUnderwaterMS = -1; - baseEmitter = PulseGreenEmitter; - delayEmitter = PulseGreenEmitter; - bubbleEmitter = PulseGreenEmitter; + baseEmitter = PulseGreenEmitter; + delayEmitter = PulseGreenEmitter; + bubbleEmitter = PulseGreenEmitter; - //activateDelayMS = 100; - activateDelayMS = -1; + //activateDelayMS = 100; + activateDelayMS = -1; - size[0] = 0.2; - size[1] = 0.2; - size[2] = 0.2; + size[0] = 0.2; + size[1] = 0.2; + size[2] = 0.2; - numFlares = 15; - flareColor = "0 1 0"; - flareModTexture = "flaremod"; - flareBaseTexture = "flarebase"; + numFlares = 15; + flareColor = "0 1 0"; + flareModTexture = "flaremod"; + flareBaseTexture = "flarebase"; - sound = MissileProjectileSound; - fireSound = PlasmaFireSound; - wetFireSound = PlasmaFireWetSound; + sound = MissileProjectileSound; + fireSound = PlasmaFireSound; + wetFireSound = PlasmaFireWetSound; - hasLight = true; - lightRadius = 3.0; - lightColor = "0 1 0"; - -}; - -datablock ParticleData(PurpleNightmareEmitParticle) { - dragCoeffiecient = 1; - gravityCoefficient = -0.3; // rises slowly - inheritedVelFactor = 0; - - lifetimeMS = 300; - lifetimeVarianceMS = 0; - useInvAlpha = false; - spinRandomMin = 0.0; - spinRandomMax = 0.0; - - animateTexture = false; - - textureName = "flareBase"; // "special/Smoke/bigSmoke" - - colors[0] = "0.5 0.1 0.9 1.0"; - colors[1] = "0.5 0.1 0.9 1.0"; - colors[2] = "0.5 0.1 0.9"; - - sizes[0] = 0.4; - sizes[1] = 0.4; - sizes[2] = 0.4; - - times[0] = 0.0; - times[1] = 1.0; - times[2] = 5.0; - -}; - -datablock ParticleEmitterData(YvexSniperEmitter) { - ejectionPeriodMS = 2; - periodVarianceMS = 1; - - ejectionVelocity = 10; - velocityVariance = 0; - - thetaMin = 89.0; - thetaMax = 90.0; - - orientParticles = false; - - particles = "PurpleNightmareEmitParticle"; + hasLight = true; + lightRadius = 3.0; + lightColor = "0 1 0"; }; datablock LinearFlareProjectileData(YvexSniperShot) { - projectileShapeName = "weapon_missile_projectile.dts"; - scale = "3.0 5.0 3.0"; - faceViewer = true; - directDamage = 0.01; - kickBackStrength = 4000.0; - DirectDamageType = $DamageType::Zombie; + projectileShapeName = "weapon_missile_projectile.dts"; + scale = "3.0 5.0 3.0"; + faceViewer = true; + directDamage = 0.01; + kickBackStrength = 4000.0; + DirectDamageType = $DamageType::Zombie; - explosion = "BlasterExplosion"; + explosion = "BlasterExplosion"; - dryVelocity = 150.0; - wetVelocity = -1; - velInheritFactor = 0.3; - fizzleTimeMS = 10000; - lifetimeMS = 10000; - explodeOnDeath = true; - reflectOnWaterImpactAngle = 0.0; - explodeOnWaterImpact = true; - deflectionOnWaterImpact = 0.0; - fizzleUnderwaterMS = -1; + dryVelocity = 150.0; + wetVelocity = -1; + velInheritFactor = 0.3; + fizzleTimeMS = 10000; + lifetimeMS = 10000; + explodeOnDeath = true; + reflectOnWaterImpactAngle = 0.0; + explodeOnWaterImpact = true; + deflectionOnWaterImpact = 0.0; + fizzleUnderwaterMS = -1; - activateDelayMS = 100; - activateDelayMS = -1; + activateDelayMS = 100; + activateDelayMS = -1; - baseEmitter = YvexSniperEmitter; + baseEmitter = YvexSniperEmitter; - size[0] = 0.0; - size[1] = 0.0; - size[2] = 0.0; + size[0] = 0.0; + size[1] = 0.0; + size[2] = 0.0; - numFlares = 0; - flareColor = "0.0 0.0 0.0"; - flareModTexture = "flaremod"; - flareBaseTexture = "flarebase"; + numFlares = 0; + flareColor = "0.0 0.0 0.0"; + flareModTexture = "flaremod"; + flareBaseTexture = "flarebase"; sound = PlasmaProjectileSound; - fireSound = PlasmaFireSound; - wetFireSound = PlasmaFireWetSound; + fireSound = PlasmaFireSound; + wetFireSound = PlasmaFireWetSound; - hasLight = true; - lightRadius = 3.0; - lightColor = "1 0.75 0.25"; -}; - -datablock SeekerProjectileData(YvexZombieMakerMissile) { - 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 = 30000; // z0dd - ZOD, 4/14/02. Was 6000 - muzzleVelocity = 30.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; + hasLight = true; + lightRadius = 3.0; + lightColor = "1 0.75 0.25"; }; datablock PlayerData(YvexZombieArmor) : LightMaleHumanArmor { - boundingBox = "1.63 1.63 2.6"; - maxDamage = 400.0; - minImpactSpeed = 35; - shapeFile = "medium_male.dts"; + boundingBox = "1.63 1.63 2.6"; + maxDamage = 400.0; + minImpactSpeed = 35; + shapeFile = "medium_male.dts"; - debrisShapeName = "bio_player_debris.dts"; + debrisShapeName = "bio_player_debris.dts"; - //Foot Prints - decalData = HeavyBiodermFootprint; - decalOffset = 0.4; + //Foot Prints + decalData = HeavyBiodermFootprint; + decalOffset = 0.4; - waterBreathSound = WaterBreathBiodermSound; + waterBreathSound = WaterBreathBiodermSound; - damageScale[$DamageType::W1700] = 3.0; - damageScale[$DamageType::Bullet] = 0.10; //I deny you shrike n0bs - - max[RepairKit] = 0; - max[Mine] = 0; - max[Grenade] = 0; - max[SmokeGrenade] = 0; - max[BeaconSmokeGrenade] = 0; - max[Blaster] = 0; - max[Plasma] = 0; - max[PlasmaAmmo] = 0; - max[Disc] = 0; - max[DiscAmmo] = 0; - max[SniperRifle] = 0; - max[GrenadeLauncher] = 0; - max[GrenadeLauncherAmmo] = 0; - max[Mortar] = 0; - max[MortarAmmo] = 0; - max[MissileLauncher] = 0; - max[MissileLauncherAmmo] = 0; - max[Chaingun] = 0; - max[ChaingunAmmo] = 0; - max[RepairGun] = 0; - max[CloakingPack] = 0; - max[SensorJammerPack] = 0; - max[EnergyPack] = 0; - max[RepairPack] = 0; - max[ShieldPack] = 0; - max[AmmoPack] = 0; - max[SatchelCharge] = 0; - max[MortarBarrelPack] = 0; - max[MissileBarrelPack] = 0; - max[AABarrelPack] = 0; - max[PlasmaBarrelPack] = 0; - max[ELFBarrelPack] = 0; - max[artillerybarrelpack] = 0; - max[MedPack] = 0; - max[InventoryDeployable] = 0; - max[MotionSensorDeployable] = 0; - max[PulseSensorDeployable] = 0; - max[TurretOutdoorDeployable] = 0; - max[TurretIndoorDeployable] = 0; - max[FlashGrenade] = 0; - max[ConcussionGrenade] = 0; - max[FlareGrenade] = 0; - max[TargetingLaser] = 0; - max[ELFGun] = 0; - max[ShockLance] = 0; - max[CameraGrenade] = 0; - max[Beacon] = 0; - max[flamerAmmoPack] = 0; - max[ParachutePack] = 0; - max[ConstructionTool] = 0; - max[MergeTool] = 0; - max[NerfGun] = 0; - max[NerfBallLauncher] = 0; - max[NerfBallLauncherAmmo] = 0; - max[SuperChaingun] = 0; - max[SuperChaingunAmmo] = 0; - max[RPChaingun] = 0; - max[RPChaingunAmmo] = 0; - max[MGClip] = 0; - max[LSMG] = 0; - max[LSMGAmmo] = 0; - max[LSMGClip] = 0; - max[snipergun] = 0; - max[snipergunAmmo] = 0; - max[Bazooka] = 0; - max[BazookaAmmo] = 0; - max[BunkerBuster] = 0; - max[MG42] = 0; - max[MG42Ammo] = 0; - max[SPistol] = 0; - max[Pistol] = 0; - max[PistolAmmo] = 0; - max[Pistolclip] = 0; - max[flamer] = 0; - max[flamerAmmo] = 0; - max[AALauncher] = 0; - max[AALauncherAmmo] = 0; - max[melee] = 0; - max[SOmelee] = 0; - max[KriegRifle] = 0; - max[KriegAmmo] = 0; - max[Rifleclip] = 0; - max[Shotgun] = 0; - max[ShotgunAmmo] = 0; - max[ShotgunClip] = 0; - max[RShotgun] = 0; - max[RShotgunAmmo] = 0; - max[RShotgunClip] = 0; - max[LMissileLauncher] = 0; - max[LMissileLauncherAmmo] = 0; - max[HRPChaingun] = 0; - max[RPGAmmo] = 0; - max[RPGItem] = 0; - max[spineDeployable] = 0; - max[mspineDeployable] = 0; - max[wWallDeployable] = 0; - max[floorDeployable] = 0; - max[WallDeployable] = 0; - max[DoorDeployable] = 0; - max[TurretLaserDeployable] = 0; - max[TurretMissileRackDeployable]= 0; - max[DiscTurretDeployable] = 0; - max[EnergizerDeployable] = 0; - max[TreeDeployable] = 0; - max[CrateDeployable] = 0; - max[DecorationDeployable] = 0; - max[LogoProjectorDeployable] = 0; - max[LightDeployable] = 0; - max[TripwireDeployable] = 0; - max[TelePadPack] = 0; - max[TurretBasePack] = 0; - max[LargeInventoryDeployable] = 0; - max[GeneratorDeployable] = 0; - max[SolarPanelDeployable] = 0; - max[SwitchDeployable] = 0; - max[MediumSensorDeployable] = 0; - max[LargeSensorDeployable] = 0; - max[SpySatelliteDeployable] = 0; - max[JumpadDeployable] = 0; - max[EscapePodDeployable] = 0; - max[ForceFieldDeployable] = 0; - max[GravityFieldDeployable] = 0; - max[VehiclePadPack] = 0; + damageScale[$DamageType::M1700] = 3.0; + damageScale[$DamageType::Bullet] = 0.10; //I deny you shrike n0bs }; //CREATION function SpawnYvex(%position) { - %Zombie = new player(){ - Datablock = "YvexZombieArmor"; - }; - %Cpos = vectorAdd(%position, "0 0 5"); - MessageAll('MsgYvexreturn', "\c4"@$TWM2::ZombieName[7]@": Did you miss me? Because... I WANT MY REVENGE!!!"); + %Zombie = new player(){ + Datablock = "YvexZombieArmor"; + }; + %Cpos = vectorAdd(%position, "0 0 5"); + MessageAll('MsgYvexreturn', "\c4"@$TWM2::ZombieName[7]@": Did you miss me? Because... I WANT MY REVENGE!!!"); - %command = "Yvexmovetotarget"; - %zombie.ticks = 0; - InitiateBoss(%zombie, "Yvex"); - - YvexAttack_FUNC("ZombieSummon", %zombie); - YvexAttacks(%zombie); - - %Zombie.team = 30; - %zname = $TWM2::ZombieName[7]; // <- To Hosts, Enjoy, You can - //Change the Zombie Names now!!! - %zombie.target = createTarget(%zombie, %zname, "", "Derm3", '', %zombie.team, PlayerSensor); - setTargetSensorData(%zombie.target, PlayerSensor); - setTargetSensorGroup(%zombie.target, 30); - setTargetName(%zombie.target, addtaggedstring(%zname)); - setTargetSkin(%zombie.target, 'Horde'); - // - %zombie.type = %type; - %Zombie.setTransform(%cpos); - %zombie.canjump = 1; - %zombie.hastarget = 1; - %zombie.isZombie = 1; - MissionCleanup.add(%Zombie); - schedule(1000, %zombie, %command, %zombie); + %command = "Yvexmovetotarget"; + %zombie.ticks = 0; + InitiateBoss(%zombie, "Yvex"); + + YvexAttack_FUNC("ZombieSummon", %zombie); + YvexAttacks(%zombie); + + %Zombie.team = 30; + %zname = $TWM2::ZombieName[7]; // <- To Hosts, Enjoy, You can + //Change the Zombie Names now!!! + %zombie.target = createTarget(%zombie, %zname, "", "Derm3", '', %zombie.team, PlayerSensor); + setTargetSensorData(%zombie.target, PlayerSensor); + setTargetSensorGroup(%zombie.target, 30); + setTargetName(%zombie.target, addtaggedstring(%zname)); + setTargetSkin(%zombie.target, 'Horde'); + // + %zombie.type = %type; + %Zombie.setTransform(%cpos); + %zombie.canjump = 1; + %zombie.hastarget = 1; + %zombie.isZombie = 1; + MissionCleanup.add(%Zombie); + schedule(1000, %zombie, %command, %zombie); } //AI function Yvexmovetotarget(%zombie){ - if(!isobject(%zombie)) - return; - if(%zombie.getState() $= "dead") - return; - %pos = %zombie.getworldboxcenter(); - %z = getWord(%pos, 2); - if(%z < -300) { - %zombie.startFade(400, 0, true); - %zombie.startFade(1000, 0, false); - %zombie.setPosition(vectorAdd(vectoradd(%closestclient.player.getPosition(), "0 0 20"), TWM2Lib_MainControl("getRandomPosition", 25 TAB 1))); - %zombie.setVelocity("0 0 0"); - MessageAll('msgYvexAttack', "\c4"@$TWM2::ZombieName[7]@": I shall not fall to my end!"); - } - %closestClient = ZombieLookForTarget(%zombie); - %closestDistance = getWord(%closestClient,1); - %closestClient = getWord(%closestClient,0).Player; - if(%closestDistance <= $zombie::detectDist){ - if(%zombie.hastarget != 1){ - serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); - %zombie.hastarget = 1; + if(!isobject(%zombie)) + return; + if(%zombie.getState() $= "dead") + return; + %pos = %zombie.getworldboxcenter(); + %z = getWord(%pos, 2); + if(%z < -300) { + %zombie.startFade(400, 0, true); + %zombie.startFade(1000, 0, false); + %zombie.setPosition(vectorAdd(vectoradd(%closestclient.player.getPosition(), "0 0 20"), TWM2Lib_MainControl("getRandomPosition", 25 TAB 1))); + %zombie.setVelocity("0 0 0"); + MessageAll('msgYvexAttack', "\c4"@$TWM2::ZombieName[7]@": I shall not fall to my end!"); } - %chance = (getrandom() * 20); - if(%chance >= 19) - serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); + %closestClient = ZombieLookForTarget(%zombie); + %closestDistance = getWord(%closestClient,1); + %closestClient = getWord(%closestClient,0).Player; + if(%closestDistance <= $zombie::detectDist){ + if(%zombie.hastarget != 1){ + serverPlay3d("ZombieHOWL",%zombie.getWorldBoxCenter()); + %zombie.hastarget = 1; + } + %chance = (getrandom() * 20); + if(%chance >= 19) + serverPlay3d("ZombieMoan",%zombie.getWorldBoxCenter()); - %vector = ZgetFacingDirection(%zombie,%closestClient,%pos); + %vector = ZgetFacingDirection(%zombie,%closestClient,%pos); - %zombie.ticks++; - %vector = vectorscale(%vector, $Zombie::DForwardSpeed / 2); - %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); - } - %zombie.moveloop = schedule(500, %zombie, "Yvexmovetotarget", %zombie); + %zombie.ticks++; + %vector = vectorscale(%vector, $Zombie::DForwardSpeed / 2); + %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); + } + %zombie.moveloop = schedule(500, %zombie, "Yvexmovetotarget", %zombie); } //ATTACKS @@ -747,23 +329,7 @@ function YvexAttack_FUNC(%att, %args) { %z = getWord(%args, 0); %t = getWord(%args, 1); %vec = vectorNormalize(vectorSub(%t.getPosition(),%z.getPosition())); - %p = new SeekerProjectile() { - dataBlock = YvexZombieMakerMissile; - initialDirection = %vec; - initialPosition = %z.getMuzzlePoint(4); - sourceObject = %z; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %t.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%t, %beacon, %p); + createMissileSeekingProjectile("YvexZombieMakerMissile", %t, %z, %z.getMuzzlePoint(4), %vec, 4, 100); case "RiftPulse": %t = getWord(%args, 0); @@ -783,23 +349,7 @@ function YvexAttack_FUNC(%att, %args) { %z = getWord(%args, 0); %t = getWord(%args, 1); %vec = vectorNormalize(vectorSub(%t.getPosition(),%z.getPosition())); - %p = new SeekerProjectile() { - dataBlock = YvexNightmareMissile; - initialDirection = %vec; - initialPosition = %z.getMuzzlePoint(4); - sourceObject = %z; - sourceSlot = 4; - }; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %t.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%t, %beacon, %p); + createMissileSeekingProjectile("YvexNightmareMissile", %t, %z, %z.getMuzzlePoint(4), %vec, 4, 100); case "KillLoop": %player = getWord(%args, 0); diff --git a/scripts/TWM2/Bosses/ShadeLord.cs b/scripts/TWM2/Bosses/ShadeLord.cs index 346bfa8..3441bfc 100644 --- a/scripts/TWM2/Bosses/ShadeLord.cs +++ b/scripts/TWM2/Bosses/ShadeLord.cs @@ -464,23 +464,7 @@ function ShadeLordFunction(%boss, %function, %args) { %neg = %i % 2 == 0 ? 1 : -1; %start = vectorAdd(%start1, %neg*%interval*%i@" 0 0"); %vec = vectorNormalize(vectorSub(%go,%start)); - %p = new SeekerProjectile() { - dataBlock = ShadeLordSword; - initialDirection = %vec; - initialPosition = %start; - }; - %p.sourceObject = %boss; - %p.targetedPlayer = %target; - %beacon = new BeaconObject() { - dataBlock = "SubBeacon"; - beaconType = "vehicle"; - position = %target.player.getWorldBoxCenter(); - }; - %beacon.team = 0; - %beacon.setTarget(0); - MissionCleanup.add(%beacon); - %p.setObjectTarget(%beacon); - DemonMotherMissileFollow(%target,%beacon,%p); + createMissileSeekingProjectile("ShadeLordSword", %target, %boss, %start, %vec, 4, 100); } case "Att_HealSequence": @@ -883,23 +867,7 @@ function ShadeLordFunction(%boss, %function, %args) { %target = getWord(%args, 0); %incoming = vectorAdd(%target.getPosition(), vectorAdd(TWM2Lib_MainControl("getRandomPosition", 70 TAB 1), "0 0 250")); %vec = vectorNormalize(vectorSub(%target.getPosition(),%incoming)); - %p = new SeekerProjectile() { - dataBlock = ShadeLordSword; - initialDirection = %vec; - initialPosition = %incoming; - }; - %p.sourceObject = %boss; - %p.targetedPlayer = %target; - %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); + createMissileSeekingProjectile("ShadeLordSword", %target, %boss, %incoming, %vec, 4, 100); //------------- //Misc Functions diff --git a/scripts/TWM2/LoadMod.cs b/scripts/TWM2/LoadMod.cs index cf73c6b..10417dd 100644 --- a/scripts/TWM2/LoadMod.cs +++ b/scripts/TWM2/LoadMod.cs @@ -5,8 +5,9 @@ echo("********************************************"); echo("******** EXECUTING TWM2 MOD SCRIPTS ********"); echo("********************************************"); echo("********************************************"); - //Mod Systems -exec("serverControl.cs"); //Server Settings + + //Mod Systems +exec("serverControl.cs"); //Server Settings exec("scripts/TWM2/Systems/Directorate.cs"); //Client Container Objects exec("scripts/TWM2/Systems/AdvancedRankSystem.cs"); //Adv. Ranks @@ -37,20 +38,20 @@ exec("scripts/TWM2/Systems/weaponModes.cs"); //Global Defines for Weapon exec("scripts/TWM2/AI/DroneAI.cs"); //Drones exec("scripts/TWM2/Systems/HarbingersWrath.cs"); //Harbinger's Wrath - //Mod Objects + //Mod Objects exec("scripts/TWM2/ModObjects/UAMS.cs"); //UAMS Missile Satellite - //Mod Dependancies + //Mod Dependancies -exec("scripts/TWM2/loadmenu.cs"); //loadscreen -exec("scripts/TWM2/WeaponFunctions.cs"); //TWM2 Weapon Functions -exec("scripts/TWM2/Zombie/LoadZombieScripts.cs"); //TWM2 Zombie Script Load -exec("scripts/TWM2/CustomCamera.cs"); //TWM2 Cameras -exec("scripts/TWM2/CustomArmors.cs"); //TWM2 Armors -exec("scripts/TWM2/ArmorFunctions.cs"); //TWM2 Armors Functions -exec("scripts/TWM2/VehicleReticles.cs"); //Vehicle Reticles +exec("scripts/TWM2/loadmenu.cs"); //loadscreen +exec("scripts/TWM2/WeaponFunctions.cs"); //TWM2 Weapon Functions +exec("scripts/TWM2/Zombie/LoadZombieScripts.cs"); //TWM2 Zombie Script Load +exec("scripts/TWM2/CustomCamera.cs"); //TWM2 Cameras +exec("scripts/TWM2/CustomArmors.cs"); //TWM2 Armors +exec("scripts/TWM2/ArmorFunctions.cs"); //TWM2 Armors Functions +exec("scripts/TWM2/VehicleReticles.cs"); //Vehicle Reticles - //Universal Systems + //Universal Systems exec("scripts/TWM2/PGDConnect/ConnectionQueue.cs"); //TCP Connection List exec("scripts/TWM2/PGDConnect/UniversalSupport.cs"); //Support Script exec("scripts/TWM2/PGDConnect/UniversalSaving_Client.cs");//Saver diff --git a/scripts/TWM2/MultiUseDatablocks.cs b/scripts/TWM2/MultiUseDatablocks.cs new file mode 100644 index 0000000..58ee9aa --- /dev/null +++ b/scripts/TWM2/MultiUseDatablocks.cs @@ -0,0 +1,678 @@ +// +// MultiUseDatablocks.cs +// TWM2 3.9.2 +// Phantom139 +// +// Contains datablock instances that are shared across multiple script files in the mod to allow for removal of re-definitions +// Any datablock that requires use in multiple weapons, or in special instance objects should be defined in this file as it is +// loaded first in the mod instances. + +//********************************************** +// AUDIO DATABLOCKS +//********************************************** +datablock AudioProfile(ZombieMoan) { + filename = "fx/environment/growl3.wav"; + description = AudioClose3d; + preload = true; +}; + +datablock AudioProfile(ZombieHOWL) { + filename = "fx/environment/Yeti_Howl1.wav"; + description = AudioBomb3d; + preload = true; +}; + +//********************************************** +// PARTICLE DATABLOCKS +//********************************************** +datablock ParticleData(NMMissileBaseParticle) { + dragCoeffiecient = 0.0; + gravityCoefficient = -0.2; + inheritedVelFactor = 0.0; + + lifetimeMS = 800; + lifetimeVarianceMS = 500; + + useInvAlpha = false; + spinRandomMin = -160.0; + spinRandomMax = 160.0; + + animateTexture = true; + framesPerSec = 15; + + textureName = "special/cloudflash"; + + colors[0] = "0.5 0.1 0.9 1.0"; + colors[1] = "0.5 0.1 0.9 1.0"; + colors[2] = "0.5 0.1 0.9 1.0"; + + sizes[0] = 2.5; + sizes[1] = 2.7; + sizes[2] = 3.0; + + times[0] = 0.0; + times[1] = 0.7; + times[2] = 1.0; +}; + +datablock ParticleData(ThrowerBaseParticle) { + dragCoeffiecient = 0.0; + gravityCoefficient = -0.2; + inheritedVelFactor = 0.0; + + lifetimeMS = 800; + lifetimeVarianceMS = 500; + + useInvAlpha = false; + spinRandomMin = -160.0; + spinRandomMax = 160.0; + + animateTexture = true; + framesPerSec = 15; + + textureName = "special/cloudflash"; + + colors[0] = "1.0 0.6 0.4 1.0"; + colors[1] = "1.0 0.5 0.2 1.0"; + colors[2] = "1.0 0.25 0.1 0.0"; + + sizes[0] = 0.5; + sizes[1] = 0.7; + sizes[2] = 1.0; + + times[0] = 0.0; + times[1] = 0.7; + times[2] = 1.0; +}; + +datablock ParticleData(DemonFBSmokeParticle) { + dragCoeffiecient = 0.0; + gravityCoefficient = 0.0; + inheritedVelFactor = 0.0; + + lifetimeMS = 2500; + lifetimeVarianceMS = 500; + + textureName = "particleTest"; + + useInvAlpha = true; + + spinRandomMin = -60.0; + spinRandomMax = 60.0; + + colors[0] = "0.5 0.5 0.5 0.5"; + colors[1] = "0.4 0.4 0.4 0.2"; + colors[2] = "0.3 0.3 0.3 0.0"; + + sizes[0] = 0.5; + sizes[1] = 1.75; + sizes[2] = 3.0; + + times[0] = 0.0; + times[1] = 0.5; + times[2] = 1.0; +}; + +datablock ParticleData(InflictionNightmareGlobeSmoke) { + dragCoefficient = 50;/////////----------------------- + gravityCoefficient = 0.0; + inheritedVelFactor = 1.0; + constantAcceleration = 0.0; + lifetimeMS = 5050; + lifetimeVarianceMS = 0; + useInvAlpha = true; + spinRandomMin = -360.0; + spinRandomMax = 360.0; + textureName = "particleTest"; + + colors[0] = "0.5 0.1 0.9 1.0"; + colors[1] = "0.5 0.1 0.9 1.0"; + colors[2] = "0.5 0.1 0.9 1.0"; + colors[3] = "0.5 0.1 0.9"; + + sizes[0] = 1.0; + sizes[1] = 1.0; + sizes[2] = 1.0; + sizes[3] = 1.0; + + times[0] = 0.0; + times[1] = 0.33; + times[2] = 0.66; + times[3] = 1.0; + + mass = 0.7; + elasticity = 0.2; + friction = 1; + computeCRC = true; + haslight = true; + lightType = "PulsingLight"; + lightColor = "0.2 0.0 0.5 1.0"; + lightTime = "200"; + lightRadius = "2.0"; +}; + +datablock ParticleData(NightmareGlobeSmoke) { + dragCoefficient = 50;/////////----------------------- + gravityCoefficient = 0.0; + inheritedVelFactor = 1.0; + constantAcceleration = 0.0; + lifetimeMS = 5050; + lifetimeVarianceMS = 0; + useInvAlpha = true; + spinRandomMin = -360.0; + spinRandomMax = 360.0; + textureName = "particleTest"; + + colors[0] = "0.1 0.1 0.1 1.0";// //////////////////// + colors[1] = "0.1 0.1 0.1 1.0";// //////////////////// + colors[2] = "0.1 0.1 0.1 1.0";// \\\\\\\\\\\\\\\\\\\\ + colors[3] = "0.1 0.1 0.1 1.0";// \\\\\\\\\\\\\\\\\\\\ + + sizes[0] = 1.0; + sizes[1] = 1.0; + sizes[2] = 1.0; + sizes[3] = 1.0; + + times[0] = 0.0; + times[1] = 0.33; + times[2] = 0.66; + times[3] = 1.0; + + mass = 0.7; + elasticity = 0.2; + friction = 1; + computeCRC = true; + haslight = true; + lightType = "PulsingLight"; + lightColor = "0.2 0.0 0.5 1.0"; + lightTime = "200"; + lightRadius = "2.0"; +}; + +datablock ParticleData(GreenEmitParticle) { + dragCoeffiecient = 1; + gravityCoefficient = -0.3; // rises slowly + inheritedVelFactor = 0; + + lifetimeMS = 300; + lifetimeVarianceMS = 0; + useInvAlpha = false; + spinRandomMin = 0.0; + spinRandomMax = 0.0; + + animateTexture = false; + + textureName = "flareBase"; // "special/Smoke/bigSmoke" + + colors[0] = "0 1 0"; + colors[1] = "0 1 0"; + colors[2] = "0 1 0"; + + sizes[0] = 0.8; + sizes[1] = 0.8; + sizes[2] = 0.8; + + times[0] = 0.0; + times[1] = 1.0; + times[2] = 5.0; +}; + +datablock ParticleData(PurpleNightmareEmitParticle) { + dragCoeffiecient = 1; + gravityCoefficient = -0.3; // rises slowly + inheritedVelFactor = 0; + + lifetimeMS = 300; + lifetimeVarianceMS = 0; + useInvAlpha = false; + spinRandomMin = 0.0; + spinRandomMax = 0.0; + + animateTexture = false; + + textureName = "flareBase"; // "special/Smoke/bigSmoke" + + colors[0] = "0.5 0.1 0.9 1.0"; + colors[1] = "0.5 0.1 0.9 1.0"; + colors[2] = "0.5 0.1 0.9"; + + sizes[0] = 0.4; + sizes[1] = 0.4; + sizes[2] = 0.4; + + times[0] = 0.0; + times[1] = 1.0; + times[2] = 5.0; + +}; + +//********************************************** +// PARTICLE EMITTER DATABLOCKS +//********************************************** +datablock ParticleEmitterData(NMMissileBaseEmitter) { + ejectionPeriodMS = 10; + periodVarianceMS = 0; + + ejectionVelocity = 1.5; + velocityVariance = 0.3; + + thetaMin = 0.0; + thetaMax = 30.0; + + particles = "NMMissileBaseParticle"; +}; + +datablock ParticleEmitterData(NightmareGlobeEmitter) { + ejectionPeriodMS = 0.1; + periodVarianceMS = 0; + + ejectionVelocity = 0.0; + velocityVariance = 0.0; + + ejectionOffset = 5; + thetaMin = 0; + thetaMax = 180; + + overrideAdvances = false; + particles = "NightmareGlobeSmoke"; +}; + +datablock ParticleEmitterData(InfNightmareGlobeEmitter) { + ejectionPeriodMS = 0.1; + periodVarianceMS = 0; + + ejectionVelocity = 0.0; + velocityVariance = 0.0; + + ejectionOffset = 5; + thetaMin = 0; + thetaMax = 180; + + overrideAdvances = false; + particles = "InflictionNightmareGlobeSmoke"; +}; + +datablock ParticleEmitterData(PulseGreenEmitter) { + ejectionPeriodMS = 2; + periodVarianceMS = 1; + + ejectionVelocity = 10; + velocityVariance = 0; + + thetaMin = 89.0; + thetaMax = 90.0; + + orientParticles = false; + + particles = "GreenEmitParticle"; +}; + +datablock ParticleEmitterData(YvexSniperEmitter) { + ejectionPeriodMS = 2; + periodVarianceMS = 1; + + ejectionVelocity = 10; + velocityVariance = 0; + + thetaMin = 89.0; + thetaMax = 90.0; + + orientParticles = false; + + particles = "PurpleNightmareEmitParticle"; +}; + +datablock ParticleEmitterData(DemonFBSmokeEmitter) { + ejectionPeriodMS = 7; + periodVarianceMS = 0; + + ejectionVelocity = 0.75; // A little oomph at the back end + velocityVariance = 0.2; + + thetaMin = 0.0; + thetaMax = 180.0; + + particles = "DemonFBSmokeParticle"; +}; + +datablock ParticleEmitterData(ThrowerBaseEmitter) { + ejectionPeriodMS = 10; + periodVarianceMS = 0; + + ejectionVelocity = 1.5; + velocityVariance = 0.3; + + thetaMin = 0.0; + thetaMax = 30.0; + + particles = "ThrowerBaseParticle"; +}; + +//********************************************** +// PROJECTILE DATABLOCKS +//********************************************** +datablock GrenadeProjectileData(DemonFireball) { + projectileShapeName = "plasmabolt.dts"; + emitterDelay = -1; + directDamage = 0.0; + hasDamageRadius = true; + indirectDamage = 0.4; + damageRadius = 5.0; // z0dd - ZOD, 8/13/02. Was 20.0 + radiusDamageType = $DamageType::zombie; + kickBackStrength = 1500; + + explosion = "PlasmaBoltExplosion"; + underwaterExplosion = "PlasmaBoltExplosion"; + velInheritFactor = 0; + splash = PlasmaSplash; + depthTolerance = 100.0; + + baseEmitter = DemonFBSmokeEmitter; + bubbleEmitter = DemonFBSmokeEmitter; + + grenadeElasticity = 0; + grenadeFriction = 0.4; + armingDelayMS = -1; // z0dd - ZOD, 4/14/02. Was 2000 + + gravityMod = 0.4; // z0dd - ZOD, 5/18/02. Make mortar projectile heavier, less floaty + muzzleVelocity = 50.0; // z0dd - ZOD, 8/13/02. More velocity to compensate for higher gravity. Was 63.7 + drag = 0; + sound = PlasmaProjectileSound; + + hasLight = true; + lightRadius = 10; + lightColor = "1 0.75 0.25"; + + hasLightUnderwaterColor = true; + underWaterLightColor = "1 0.75 0.25"; +}; + +datablock GrenadeProjectileData(DemonFlamingFireball) { + projectileShapeName = "plasmabolt.dts"; + emitterDelay = -1; + directDamage = 0.0; + hasDamageRadius = true; + indirectDamage = 0.4; + damageRadius = 5.0; // z0dd - ZOD, 8/13/02. Was 20.0 + radiusDamageType = $DamageType::Fire; + kickBackStrength = 1500; + + explosion = "PlasmaBoltExplosion"; + underwaterExplosion = "PlasmaBoltExplosion"; + velInheritFactor = 0; + splash = PlasmaSplash; + depthTolerance = 100.0; + + baseEmitter = ThrowerBaseEmitter; + bubbleEmitter = ThrowerBaseEmitter; + + grenadeElasticity = 0; + grenadeFriction = 0.4; + armingDelayMS = -1; // z0dd - ZOD, 4/14/02. Was 2000 + + gravityMod = 0.4; // z0dd - ZOD, 5/18/02. Make mortar projectile heavier, less floaty + muzzleVelocity = 50.0; // z0dd - ZOD, 8/13/02. More velocity to compensate for higher gravity. Was 63.7 + drag = 0; + sound = PlasmaProjectileSound; + + hasLight = true; + lightRadius = 10; + lightColor = "1 0.75 0.25"; + + hasLightUnderwaterColor = true; + underWaterLightColor = "1 0.75 0.25"; +}; + +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"; +}; + +datablock SeekerProjectileData(BossMissiles) { + casingShapeName = "weapon_missile_casement.dts"; + projectileShapeName = "weapon_missile_projectile.dts"; + hasDamageRadius = true; + indirectDamage = 0.1; + damageRadius = 6.0; + radiusDamageType = $DamageType::MissileTurret; + kickBackStrength = 500; + + flareDistance = 200; + flareAngle = 30; + minSeekHeat = 0.0; + + explosion = "MissileExplosion"; + velInheritFactor = 1.0; + + splash = MissileSplash; + baseEmitter = MortarSmokeEmitter; + delayEmitter = MissileFireEmitter; + puffEmitter = MissilePuffEmitter; + + lifetimeMS = 15000; // z0dd - ZOD, 4/14/02. Was 6000 + muzzleVelocity = 12.0; + maxVelocity = 225.0; // z0dd - ZOD, 4/14/02. Was 80.0 + turningSpeed = 50.0; + acceleration = 100.0; + + proximityRadius = 4; + + terrainAvoidanceSpeed = 100; + terrainScanAhead = 50; + terrainHeightFail = 50; + terrainAvoidanceRadius = 150; + + useFlechette = true; + flechetteDelayMs = 225; + casingDeb = FlechetteDebris; +}; + +//YvexNightmareMissile: OnExplode() function located in scripts/TWM2/Bosses/LordYvex.cs +datablock SeekerProjectileData(YvexNightmareMissile){ + casingShapeName = "weapon_missile_casement.dts"; + projectileShapeName = "weapon_missile_projectile.dts"; + hasDamageRadius = true; + indirectDamage = 0.8; + damageRadius = 8.0; + radiusDamageType = $DamageType::Missile; + 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 + + delayEmitter = MissileFireEmitter; + puffEmitter = MissilePuffEmitter; + bubbleEmitter = GrenadeBubbleEmitter; + bubbleEmitTime = 1.0; + + exhaustEmitter = MissileLauncherExhaustEmitter; + exhaustTimeMs = 300; + exhaustNodeName = "muzzlePoint1"; + + lifetimeMS = 30000; + muzzleVelocity = 10.0; + maxVelocity = 150.0; + turningSpeed = 110.0; + acceleration = 350.0; + + proximityRadius = 3; + + terrainAvoidanceSpeed = 180; + terrainScanAhead = 25; + terrainHeightFail = 12; + terrainAvoidanceRadius = 100; + + flareDistance = 200; + flareAngle = 30; + + sound = MissileProjectileSound; + + hasLight = true; + lightRadius = 5.0; + lightColor = "0.2 0.05 0"; + + useFlechette = true; + flechetteDelayMs = 550; + casingDeb = FlechetteDebris; + + explodeOnWaterImpact = false; + + baseEmitter = NMMissileBaseEmitter; +}; + +//YvexZombieMakerMissile: OnExplode() function located in scripts/TWM2/Bosses/LordYvex.cs +datablock SeekerProjectileData(YvexZombieMakerMissile) { + 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 = 30000; // z0dd - ZOD, 4/14/02. Was 6000 + muzzleVelocity = 30.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; +}; + + +//********************************************** +// MISC DATABLOCKS +//********************************************** +datablock StaticShapeData(SubBeacon) { + shapeFile = "turret_muzzlepoint.dts"; + targetNameTag = 'beacon'; + isInvincible = true; + + dynamicType = $TypeMasks::SensorObjectType; +}; \ No newline at end of file diff --git a/scripts/TWM2/Systems/MainControl.cs b/scripts/TWM2/Systems/MainControl.cs index e9b5df3..2473143 100644 --- a/scripts/TWM2/Systems/MainControl.cs +++ b/scripts/TWM2/Systems/MainControl.cs @@ -640,73 +640,114 @@ $ProjectileSeek["RapierShieldForwardProjectile", "ProjectileControls"] = "8 10 1 $ProjectileSeek["RapierShieldForwardProjectile", "CancelList"] = "FlareGrenadeProj"; function createSeekingProjectile(%projectile, %pType, %iPos, %iDir, %source, %target, %seekActivation) { - %proj = spawnprojectile(%projectile, %pTYpe, %iPos, %iDir, %source); - schedule(%seekActivation, 0, projectileSeeking, %proj, %target); - - return %proj; + %proj = spawnprojectile(%projectile, %pTYpe, %iPos, %iDir, %source); + schedule(%seekActivation, 0, projectileSeeking, %proj, %target); + + return %proj; } function projectileSeeking(%p, %target) { - %pName = %p.getDatablock().getName(); - %pArgs = $ProjectileSeek[%pName, "ProjectileControls"]; + %pName = %p.getDatablock().getName(); + %pArgs = $ProjectileSeek[%pName, "ProjectileControls"]; - %projpos = %p.position; - %projdir = %p.initialdirection; - %s = %p.sourceObject; - - if(!isobject(%p)) { - return; - } - if(isobject(%p)) { - %p.delete(); - } - if(!isobject(%target)) { - return; - } - if(%target.getClassName() $= "Player") { - if(%target.getState() $= "Dead") { - return; - } - } - - %iX = getWord(%projdir, 0); - %iY = getWord(%projdir, 1); - %iZ = getWord(%projdir, 2); + %projpos = %p.position; + %projdir = %p.initialdirection; + %s = %p.sourceObject; - %projdir = vectornormalize(vectorsub(%target.getPosition(), %projpos)); - %nDx = getWord(%projdir, 0); - %nDy = getWord(%projdir, 1); - %nDz = getWord(%projdir, 2); + if(!isobject(%p)) { + return; + } + if(isobject(%p)) { + %p.delete(); + } + if(!isobject(%target)) { + return; + } + if(%target.getClassName() $= "Player") { + if(%target.getState() $= "Dead") { + return; + } + } - %xCalc = %iX - %nDx; - %xCalc = ((%xCalc / getWord(%pArgs, 0)) * -1) + %iX; - %yCalc = %iY - %nDy; - %yCalc = ((%yCalc / getWord(%pArgs, 1)) * -1) + %iY; - %zCalc = %iZ - %nDz; - %zCalc = ((%zCalc / getWord(%pArgs, 2)) * -1) + %iZ; + %iX = getWord(%projdir, 0); + %iY = getWord(%projdir, 1); + %iZ = getWord(%projdir, 2); - %_newDir = %xCalc SPC %yCalc SPC %zCalc; - - %cnS = %pName.className; - %type = strReplace(%cnS, "Data", ""); - - %p = new (%type)() { - dataBlock = %pName; - initialDirection = %_newDir; - initialPosition = %projpos; - }; - %p.sourceobject = %s; - MissionCleanup.add(%p); - if(getWord(%pArgs, 3) == 1) { - %searchmask = $TypeMasks::ProjectileObjectType; - InitContainerRadiusSearch(%projpos, 12, %searchmask); - while ((%testTarget = containerSearchNext())) { - if(%testTarget.getdatablock().getname() $= $ProjectileSeek[%pName, "CancelList"]) { - %testTarget.delete(); - return; - } - } - } - - %p.seeksched = schedule( 80,0, "projectileSeeking", %p, %target); + %projdir = vectornormalize(vectorsub(%target.getPosition(), %projpos)); + %nDx = getWord(%projdir, 0); + %nDy = getWord(%projdir, 1); + %nDz = getWord(%projdir, 2); + + %xCalc = %iX - %nDx; + %xCalc = ((%xCalc / getWord(%pArgs, 0)) * -1) + %iX; + %yCalc = %iY - %nDy; + %yCalc = ((%yCalc / getWord(%pArgs, 1)) * -1) + %iY; + %zCalc = %iZ - %nDz; + %zCalc = ((%zCalc / getWord(%pArgs, 2)) * -1) + %iZ; + + %_newDir = %xCalc SPC %yCalc SPC %zCalc; + + %cnS = %pName.className; + %type = strReplace(%cnS, "Data", ""); + + %p = new (%type)() { + dataBlock = %pName; + initialDirection = %_newDir; + initialPosition = %projpos; + }; + %p.sourceobject = %s; + MissionCleanup.add(%p); + if(getWord(%pArgs, 3) == 1) { + %searchmask = $TypeMasks::ProjectileObjectType; + InitContainerRadiusSearch(%projpos, 12, %searchmask); + while ((%testTarget = containerSearchNext())) { + if(%testTarget.getdatablock().getname() $= $ProjectileSeek[%pName, "CancelList"]) { + %testTarget.delete(); + return; + } + } + } + + %p.seeksched = schedule(80,0, "projectileSeeking", %p, %target); } + +function createMissileSeekingProjectile(%datablockName, %targetObject, %sourceObject, %sourcePosition, %sourceVector, %sourceSlot, %updateDelay) { + if(!isObject(%targetObject)) { + return; + } + //Phantom139: Scheduling updates lower than 23ms is dangerous, let's enforce this as a minimum limit. + if(%updateDelay $= "" || %updateDelay < 23) { + error("* Warning: Call to createMissileSeekingProjectile() with an updateDelay undefined or lower than 23ms, check call stack and correct."); + %updateDelay = 100; + } + %missileProjectileInstance = new SeekerProjectile() { + dataBlock = %datablockName; + initialDirection = %sourceVector; + initialPosition = %sourcePosition; + sourceObject = %sourceObject; + sourceSlot = %sourceSlot; + }; + %beacon = new BeaconObject() { + dataBlock = "SubBeacon"; + beaconType = "vehicle"; + position = %targetObject.getWorldBoxCenter(); + }; + %beacon.team = 0; + %beacon.setTarget(0); + MissionCleanup.add(%beacon); + %missileProjectileInstance.setObjectTarget(%beacon); + %missileProjectileInstance.updateLoop = updateMissileSeekingProjectile(%missileProjectileInstance, %beacon, %targetObject, %updateDelay); +} + +function updateMissileSeekingProjectile(%missileProjectile, %beaconObject, %targetObject, %updateDelay) { + if(!isObject(%targetObject)){ + %beaconObject.delete(); + return; + } + if(!isObject(%missileProjectile)) { + %beaconObject.delete(); + return; + } + %beaconObject.setPosition(%targetObject.getWorldBoxCenter()); + %missileProjectile.updateLoop = schedule(updateDelay, 0, "updateMissileSeekingProjectile", %missileProjectile, %beaconObject, %targetObject, %updateDelay); +} \ No newline at end of file diff --git a/scripts/TWM2/Zombie/ZombieCore.cs b/scripts/TWM2/Zombie/ZombieCore.cs index ea90669..d048038 100644 --- a/scripts/TWM2/Zombie/ZombieCore.cs +++ b/scripts/TWM2/Zombie/ZombieCore.cs @@ -35,12 +35,14 @@ $Zombie::TypeDamage[15] = 0.6; $Zombie::TypeInfectedMultiplier[1] = 1.5; //$Zombie::BaseSpeed: The default speed setting on zombies, any zombie that does not have a TypeSpeed var. set will default to the BaseSpeed +// Be mindful of the $Zombie::SpeedUpdateTime[#] value when tuning, these two numbers augment closely so you need to be careful on tweaking $Zombie::BaseSpeed = 150; //$Zombie::TypeSpeed[#]: The speed of a specific zombie type instance, overrides BaseSpeed for that specific type $Zombie::TypeSpeed[2] = 300; $Zombie::TypeSpeed[3] = 4000; $Zombie::TypeSpeed[4] = 240; $Zombie::TypeSpeed[5] = 1500; +$Zombie::TypeSpeed[6] = 1200; //$Zombie::BaseJumpCooldown: The time zombies must elapse before jumping / lunging $Zombie::BaseJumpCooldown = 1500; @@ -55,6 +57,7 @@ $Zombie::BaseSpeedUpdateTime = 100; //$Zombie::SpeedUpdateTime[#]: An override to the base update type, use for specific types that need slower or faster processing between AI steps $Zombie::SpeedUpdateTime[3] = 500; $Zombie::SpeedUpdateTime[5] = 500; +$Zombie::SpeedUpdateTime[6] = 500; //$Zombie::LungeDistance: How far (m) a zombie must be to lunge at a target $Zombie::LungeDistance = 10; @@ -82,6 +85,9 @@ $Zombie::DemonZombieFireBombMaxRange = 250; //$Zombie::RapierUpwardScaling: How fast a rapier zombie will ascend when holding a player $Zombie::RapierUpwardScaling = 750; +//$Zombie::DemonLord_FirestormTrigger: How long in miliseconds between the firestorm charge up and the attack itself +$Zombie::DemonLord_FirestormTrigger = 1000; + //MISC Globals, Do not edit. $Zombie::killpoints = 5; $Zombie::RogThread = "cel1"; @@ -169,7 +175,7 @@ function TWM2Lib_Zombie_Core(%functionName, %arg1, %arg2, %arg3, %arg4) { } } - //infectloop(%player): Performs the infection loop. + //infectloop(%player, %infectSource): Performs the infection loop. case "infectloop": //Check for flags that disable this. if($TWM::PlayingHellJump || !$TWM::AllowZombieInfection) { @@ -189,6 +195,14 @@ function TWM2Lib_Zombie_Core(%functionName, %arg1, %arg2, %arg3, %arg4) { return; } } + // + if(%arg2 $= "impact") { + if(%arg1.usingPlasmasaber) { + %arg1.playShieldEffect("1 1 1"); + %arg1.infected = 0; + return; + } + } //Once we reach this point, we're good to go... if(%arg1.beats $= "") { TWM2Lib_Zombie_PlayerFunctions("zombieAttackImpulse", %arg1, 0); diff --git a/scripts/TWM2/Zombie/ZombieTypes/Demon.cs b/scripts/TWM2/Zombie/ZombieTypes/Demon.cs index 54ea9b9..f6c73ad 100644 --- a/scripts/TWM2/Zombie/ZombieTypes/Demon.cs +++ b/scripts/TWM2/Zombie/ZombieTypes/Demon.cs @@ -20,6 +20,7 @@ datablock PlayerData(DemonZombieArmor) : LightMaleHumanArmor { damageScale[$DamageType::SA2400] = 5.0; damageScale[$DamageType::Model1887] = 4.0; damageScale[$DamageType::plasma] = 0.001; + damageScale[$DamageType::Napalm] = 0.001; damageScale[$DamageType::Burn] = 0.001; damageScale[$DamageType::Fire] = 0.001; damageScale[$DamageType::CrimsonHawk] = 1.9; diff --git a/scripts/TWM2/Zombie/ZombieTypes/DemonLord.cs b/scripts/TWM2/Zombie/ZombieTypes/DemonLord.cs index ee7b65d..f6b1755 100644 --- a/scripts/TWM2/Zombie/ZombieTypes/DemonLord.cs +++ b/scripts/TWM2/Zombie/ZombieTypes/DemonLord.cs @@ -20,108 +20,49 @@ datablock PlayerData(DemonMotherZombieArmor) : LightMaleHumanArmor { damageScale[$DamageType::SA2400] = 5.0; damageScale[$DamageType::Model1887] = 4.0; damageScale[$DamageType::CrimsonHawk] = 1.9; + damageScale[$DamageType::plasma] = 0.001; + damageScale[$DamageType::Napalm] = 0.001; + damageScale[$DamageType::Burn] = 0.001; + damageScale[$DamageType::Fire] = 0.001; max[RepairKit] = 0; max[Mine] = 0; max[Grenade] = 0; }; -datablock StaticShapeData(SubBeacon) { - shapeFile = "turret_muzzlepoint.dts"; - targetNameTag = 'beacon'; - isInvincible = true; - - dynamicType = $TypeMasks::SensorObjectType; -}; - -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 DemonMotherZombieArmor::armorCollisionFunction(%datablock, %zombie, %colPlayer) { + if(!isObject(%zombie) || %zombie.getState() $= "dead") { + return; + } + if(!isObject(%colPlayer) || %colPlayer.getState() $= "dead") { + return; + } + //Check to make sure we're not hitting another zombie / boss + if(%colPlayer.isBoss || %colPlayer.isZombie || %colPlayer.rapierShield) { + return; + } + //Damage. + %causeInfect = %zombie.damage_infectOnTouch; + %baseDamage = %zombie.damage_amountOnTouch; + %multiplier = %zombie.damage_alreadyInfectedMultiplier; + + //Phantom139 (11/20): Demon Lords light players on fire, need to check for .onfire instead of the .infected flag. + %total = %colPlayer.onfire ? (%baseDamage * %multiplier) : %baseDamage; + + %pushVector = vectorscale(%colPlayer.getvelocity(), 1000); + %colPlayer.applyimpulse(%colPlayer.getposition(), %pushVector); + if(%causeInfect) { + //Phantom139: Demon Zombies now cause burns instead of infects + //%colPlayer.Infected = 1; + //%colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer); + %colPlayer.maxfirecount += (75 * (%total / 0.5)); + if(%colPlayer.onfire == 0 || %colPlayer.onfire $= ""){ + %colPlayer.onfire = 1; + schedule(10, %colPlayer, "burnloop", %colPlayer); + } + } + %colPlayer.damage(0, %colPlayer.getPosition(), %total, $DamageType::Zombie); +} function DemonMotherZombieArmor::AI(%datablock, %zombie) { //Fork off to both of the AI functions @@ -160,7 +101,7 @@ function DemonMotherZombieArmor::AIRoutine(%datablock, %zombie) { %closestClient = TWM2Lib_Zombie_Core("lookForTarget", %zombie); %closestDistance = getWord(%closestClient, 1); %closestClient = getWord(%closestClient, 0).Player; - if(%closestClient != -1){ + if(%closestClient != -1) { %searchobject = %closestclient; %dist = vectorDist(%pos, %searchobject.getPosition()); if(%dist <= 100) { @@ -175,25 +116,25 @@ function DemonMotherZombieArmor::AIRoutine(%datablock, %zombie) { %zombie.attackFunction = %datablock.AttackFunction(%zombie, "AcidStrike", %searchObject); } else { - DemonMotherFireRainAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "Firestorm", %searchObject); } } //damn, to close, ok lung at him else { - DemonMotherLungAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "FireLunge", %searchObject); } } else { //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. %rand = getRandom(1, 5); if(%rand == 1) { - DemonMotherPlasmaAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "PlasmaStrike", %searchObject); } else if(%rand <= 3) { - DemonMotherStrafeAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "StrafeMove", %searchObject); } else { - DemonMotherFlyAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "FlyAttack", %searchObject); } } } @@ -201,17 +142,17 @@ function DemonMotherZombieArmor::AIRoutine(%datablock, %zombie) { else { //humm we just attacked, ok, let charge him, get in close if(%zombie.justshot == 1) { - DemonMotherChargeIn(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "ChargeAttack", %searchObject); } //were good to fire, FIRE AWAY! else { //ok so theres 3 good possible attacks here, so lets get a random variable and decide what to do. %rand = getRandom(1, 5); if(%rand == 1) { - DemonMotherFireRainAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "Firestorm", %searchObject); } else if(%rand <= 3) { - DemonMotherMissileAttack(%zombie, %searchobject); + %zombie.attackFunction = %datablock.AttackFunction(%zombie, "MissileStrike", %searchObject); } else { %zombie.attackFunction = %datablock.AttackFunction(%zombie, "AcidStrike", %searchObject); @@ -223,23 +164,41 @@ function DemonMotherZombieArmor::AIRoutine(%datablock, %zombie) { %rand = getrandom(1,120); //please, dont ask why i choose this number, it just popped in my head if(%rand == 94) { - DemonMotherDemonSpawn(%zombie); + %datablock.AttackFunction(%zombie, "SpawnZombies"); } else { - DemonMotherMoveToTarget(%zombie,%searchobject); + %zombie.moveTarget = %searchObject; + %datablock.Move(%zombie); } } else { - DemonMotherMoveToTarget(%zombie,%searchobject); + %zombie.moveTarget = %searchObject; + %datablock.Move(%zombie); } %zombie.justshot = 0; %zombie.justmelee = 0; } else { - %zombie.aiRoutine = %datablock.schedule(500, 0, "AIRoutine", %zombie); + %zombie.aiRoutine = %datablock.schedule(%zombie.updateTimeFrequency, 0, "AIRoutine", %zombie); } } +function DemonMotherZombieArmor::Move(%datablock, %zombie) { + if(!isObject(%zombie) || %zombie.getState() $= "dead") { + return; + } + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %zombie.moveTarget.getPosition()); + %vector = vectorNormalize(vectorSub(%zombie.moveTarget.getPosition(), %zombie.getPosition())); + %vector = vectorscale(%vector, %zombie.speed); + %x = Getword(%vector, 0); + %y = Getword(%vector, 1); + %z = Getword(%vector, 2); + %vector = %x@" "@%y@" 150"; + %zombie.applyImpulse(%zombie.getPosition(), %vector); + + %zombie.aiRoutine = %datablock.schedule(%zombie.updateTimeFrequency, 0, "AIRoutine", %zombie); +} + function DemonMotherZombieArmor::AttackFunction(%datablock, %zombie, %attackFunction, %target) { if(!isObject(%zombie) || %zombie.getState() $= "dead") { return; @@ -284,301 +243,248 @@ function DemonMotherZombieArmor::AttackFunction(%datablock, %zombie, %attackFunc } case "FireLunge": + if(!isObject(%target) || %target.getState() $= "dead") { + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + return; + } + if(%zombie.chargeCount $= "") { + %zombie.chargeCount = 0; + } + if(%zombie.chargeCount == 0) { + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + %vector = vectorscale(%vector, 4000); + %x = Getword(%vector, 0); + %y = Getword(%vector, 1); + %z = Getword(%vector, 2); + %vector = %x@" "@%y@" 400"; + %zombie.applyImpulse(%zombie.getPosition(), %vector); + %zombie.justmelee = 1; + + %chargeEmitter = new ParticleEmissionDummy() { + datablock = "defaultEmissionDummy"; + emitter = "NapalmExplosionEmitter"; + position = %zombie.getMuzzlePoint(4); + }; + MissionCleanup.add(%chargeEmitter); + %chargeEmitter.schedule(100, "delete"); + + %zombie.attackFunction = %datablock.schedule(300, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else { + if(vectorDist(%zombie.getPosition(), %target.getPosition()) < 10) { + %p = new TracerProjectile() { + dataBlock = napalmSubExplosion; + initialDirection = "0 0 -10"; + initialPosition = %target.getPosition(); + sourceObject = %zombie; + sourceSlot = 4; + }; + %p.vector = "0 0 -10"; + %p.count = 1; + } + %zombie.chargecount = 0; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } case "StrafeMove": + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount <= 8) { + %zombie.setVelocity("0 0 0"); + //FaceTarget(%zombie, %target); + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + %vector = vectorscale(%vector, 3250); + %x = Getword(%vector, 0); + %y = Getword(%vector, 1); + %nv1 = %y; + %nv2 = (%x * -1); + %vector = %nv1@" "@%nv2@" 0"; + %zombie.applyImpulse(%zombie.getPosition(), %vector); + } + else if(%zombie.chargecount <= 11){ + %zombie.setvelocity("0 0 0"); + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %vector = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + %vector = vectorscale(%vector, 4500); + %x = Getword(%vector, 0); + %y = Getword(%vector, 1); + %z = Getword(%vector, 2); + %vector = %x@" "@%y@" 150"; + %zombie.applyImpulse(%zombie.getPosition(), %vector); + } + else{ + %zombie.chargecount = 0; + %zombie.justmelee = 1; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + return; + } + %zombie.attackFunction = %datablock.schedule(250, 0, "AttackFunction", %zombie, %attackFunction, %target); + %zombie.chargecount++; case "FlyAttack": + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount <= 9){ + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %zombie.setvelocity("0 0 10"); + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule(100, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else if(%zombie.chargecount == 10) { + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %zombie.setvelocity("0 0 5"); + %vector = vectorSub(%target.getPosition(), %zombie.getPosition()); + %nVec = vectorNormalize(%vector); + %vector = vectorAdd(%vector, vectorscale(%nvec,-4)); + %zombie.attackpos = vectorAdd(%zombie.getPosition(), %vector); + %zombie.attackdir = %nVec; + %zombie.startFade(400, 0, true); + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule(400, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else if(%zombie.chargecount >= 11){ + %zombie.startFade(500, 0, false); + %zombie.setPosition(%zombie.attackpos); + %zombie.setvelocity(vectorscale(%zombie.attackdir, 25)); + %zombie.justmelee = 1; + %zombie.chargecount = 0; + %zombie.attackpos = ""; + %zombie.attackdir = ""; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } case "Firestorm": + if(!isObject(%target) || %target.getState() $= "dead") { + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + return; + } + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount == 0) { + %vector = TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + for(%i = 0; %i < 10; %i++) { + %pos = %zombie.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, %zombie); + + %charge = new ParticleEmissionDummy() { + position = posFromRaycast(%searchresult); + dataBlock = "defaultEmissionDummy"; + emitter = "BurnEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(1500, "delete"); + } + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule($Zombie::DemonLord_FirestormTrigger, 0, "AttackFunction", %zombie, %attackFunction, %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 = %zombie; + sourceSlot = 4; + }; + } + %zombie.justshot = 1; + %zombie.chargecount = 0; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } case "MissileStrike": + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount == 0) { + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule(1000, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else { + %vec = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + createMissileSeekingProjectile("DMMissile", %target, %zombie, %zombie.getMuzzlePoint(4), %vec, 4, 100); + %zombie.justshot = 1; + %zombie.chargecount = 0; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } case "PlasmaStrike": + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount <= 9) { + %zombie.setVelocity("0 0 10"); + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule(100, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else{ + %zombie.setVelocity("0 0 3"); + %vec = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + %p = new LinearFlareProjectile() { + dataBlock = DMPlasma; + initialDirection = %vec; + initialPosition = %zombie.getMuzzlePoint(4); + sourceObject = %zombie; + sourceSlot = 4; + }; + %zombie.chargecount = 0; + %zombie.justshot = 1; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } case "ChargeAttack": + if(%zombie.chargecount $= "") { + %zombie.chargecount = 0; + } + if(%zombie.chargecount <= 4) { + TWM2Lib_Zombie_Core("zombieGetFacingDirection", %zombie, %target.getPosition()); + %vec = vectorNormalize(vectorSub(%target.getPosition(), %zombie.getPosition())); + %zombie.setvelocity(vectorScale(%vec, 50)); + %zombie.chargecount++; + %zombie.attackFunction = %datablock.schedule(500, 0, "AttackFunction", %zombie, %attackFunction, %target); + } + else{ + %zombie.justmelee = 1; + %zombie.chargecount = 0; + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); + } + + case "SpawnZombies": + if($TWM::PlayingHellJump || $TWM::PlayingHorde) { + return; + } + for(%i = 0; %i < 5; %i++) { + %pos = %zombie.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, %zombie); + + %charge = new ParticleEmissionDummy() { + position = posFromRaycast(%searchresult); + dataBlock = "defaultEmissionDummy"; + emitter = "BurnEmitter"; + }; + MissionCleanup.add(%charge); + %charge.schedule(1100, "delete"); + schedule(1000, 0, "TWM2Lib_Zombie_Core", "SpawnZombie", "zSpawnCommand", 4, posFromRaycast(%searchResult)); + } + %zombie.aiRoutine = %datablock.AIRoutine(%zombie); } -} - -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 = "BurnEmitter"; - }; - 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){ - if($TWM::PlayingHellJump || $TWM::PlayingHorde) { - return; - } - 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 = "BurnEmitter"; - }; - MissionCleanup.add(%charge); - %charge.schedule(1100, "delete"); - schedule(1000, 0, "TWM2Lib_Zombie_Core", "SpawnZombie", "zSpawnCommand", 4, posFromRaycast(%searchResult)); - } - schedule(1500, 0, "DemonMotherThink", %obj); -} +} \ No newline at end of file diff --git a/scripts/TWM2/Zombie/ZombieTypes/Normal.cs b/scripts/TWM2/Zombie/ZombieTypes/Normal.cs index bfe4ccc..8f7952d 100644 --- a/scripts/TWM2/Zombie/ZombieTypes/Normal.cs +++ b/scripts/TWM2/Zombie/ZombieTypes/Normal.cs @@ -58,7 +58,7 @@ function ZombieArmor::armorCollisionFunction(%datablock, %zombie, %colPlayer) { %colPlayer.applyimpulse(%colPlayer.getposition(), %pushVector); if(%causeInfect) { %colPlayer.Infected = 1; - %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer); + %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer, "impact"); } %colPlayer.damage(0, %colPlayer.getPosition(), %total, $DamageType::Zombie); } diff --git a/scripts/TWM2/Zombie/ZombieTypes/Rapier.cs b/scripts/TWM2/Zombie/ZombieTypes/Rapier.cs index fb2e75e..f358299 100644 --- a/scripts/TWM2/Zombie/ZombieTypes/Rapier.cs +++ b/scripts/TWM2/Zombie/ZombieTypes/Rapier.cs @@ -94,7 +94,7 @@ function RapierZombieArmor::armorCollisionFunction(%datablock, %zombie, %colPlay %colPlayer.damage(0, %colPlayer.getPosition(), %total, $DamageType::Zombie); if(%causeInfect) { %colPlayer.Infected = 1; - %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer); + %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer, "impact"); } } } diff --git a/scripts/TWM2/Zombie/ZombieTypes/Ravager.cs b/scripts/TWM2/Zombie/ZombieTypes/Ravager.cs index 88d08f0..9ccc13e 100644 --- a/scripts/TWM2/Zombie/ZombieTypes/Ravager.cs +++ b/scripts/TWM2/Zombie/ZombieTypes/Ravager.cs @@ -39,7 +39,7 @@ function RavagerZombieArmor::armorCollisionFunction(%datablock, %zombie, %colPla %colPlayer.applyimpulse(%colPlayer.getposition(), %pushVector); if(%causeInfect) { %colPlayer.Infected = 1; - %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer); + %colPlayer.InfectedLoop = schedule(10, %colPlayer, "TWM2Lib_Zombie_Core", "InfectLoop", %colPlayer, "impact"); } %colPlayer.damage(0, %colPlayer.getPosition(), %total, $DamageType::Zombie); } diff --git a/scripts/packs/ZSpawnpack.cs b/scripts/packs/ZSpawnpack.cs index c11fe98..7c8efb7 100644 --- a/scripts/packs/ZSpawnpack.cs +++ b/scripts/packs/ZSpawnpack.cs @@ -3,223 +3,6 @@ $TeamDeployableMax[ZSpawnDeployable] = 9999; // Zombie Spawn Point //--------------------------------------------------------- -datablock AudioProfile(ZombieMoan) -{ - filename = "fx/environment/growl3.wav"; - description = AudioClose3d; - preload = true; -}; - -datablock AudioProfile(ZombieHOWL) -{ - filename = "fx/environment/Yeti_Howl1.wav"; - description = AudioBomb3d; - preload = true; -}; - -//USED IN FLAMETHROWER / NMM -//DO NOT REMOVE: NEEDED HERE -datablock ParticleData(NMMissileBaseParticle) { - dragCoeffiecient = 0.0; - gravityCoefficient = -0.2; - inheritedVelFactor = 0.0; - - lifetimeMS = 800; - lifetimeVarianceMS = 500; - - useInvAlpha = false; - spinRandomMin = -160.0; - spinRandomMax = 160.0; - - animateTexture = true; - framesPerSec = 15; - - textureName = "special/cloudflash"; - - colors[0] = "0.5 0.1 0.9 1.0"; - colors[1] = "0.5 0.1 0.9 1.0"; - colors[2] = "0.5 0.1 0.9 1.0"; - - sizes[0] = 2.5; - sizes[1] = 2.7; - sizes[2] = 3.0; - - times[0] = 0.0; - times[1] = 0.7; - times[2] = 1.0; -}; - -datablock ParticleEmitterData(NMMissileBaseEmitter) { - ejectionPeriodMS = 10; - periodVarianceMS = 0; - - ejectionVelocity = 1.5; - velocityVariance = 0.3; - - thetaMin = 0.0; - thetaMax = 30.0; - - particles = "NMMissileBaseParticle"; -}; - -datablock ParticleData(ThrowerBaseParticle) { - dragCoeffiecient = 0.0; - gravityCoefficient = -0.2; - inheritedVelFactor = 0.0; - - lifetimeMS = 800; - lifetimeVarianceMS = 500; - - useInvAlpha = false; - spinRandomMin = -160.0; - spinRandomMax = 160.0; - - animateTexture = true; - framesPerSec = 15; - - textureName = "special/cloudflash"; - - colors[0] = "1.0 0.6 0.4 1.0"; - colors[1] = "1.0 0.5 0.2 1.0"; - colors[2] = "1.0 0.25 0.1 0.0"; - - sizes[0] = 0.5; - sizes[1] = 0.7; - sizes[2] = 1.0; - - times[0] = 0.0; - times[1] = 0.7; - times[2] = 1.0; -}; - -datablock ParticleEmitterData(ThrowerBaseEmitter) { - ejectionPeriodMS = 10; - periodVarianceMS = 0; - - ejectionVelocity = 1.5; - velocityVariance = 0.3; - - thetaMin = 0.0; - thetaMax = 30.0; - - particles = "ThrowerBaseParticle"; -}; -// - -datablock ParticleData(DemonFBSmokeParticle) -{ - dragCoeffiecient = 0.0; - gravityCoefficient = 0.0; - inheritedVelFactor = 0.0; - - lifetimeMS = 2500; - lifetimeVarianceMS = 500; - - textureName = "particleTest"; - - useInvAlpha = true; - - spinRandomMin = -60.0; - spinRandomMax = 60.0; - - colors[0] = "0.5 0.5 0.5 0.5"; - colors[1] = "0.4 0.4 0.4 0.2"; - colors[2] = "0.3 0.3 0.3 0.0"; - sizes[0] = 0.5; - sizes[1] = 1.75; - sizes[2] = 3.0; - times[0] = 0.0; - times[1] = 0.5; - times[2] = 1.0; -}; - -datablock ParticleEmitterData(DemonFBSmokeEmitter) -{ - ejectionPeriodMS = 7; - periodVarianceMS = 0; - - ejectionVelocity = 0.75; // A little oomph at the back end - velocityVariance = 0.2; - - thetaMin = 0.0; - thetaMax = 180.0; - - particles = "DemonFBSmokeParticle"; -}; - -datablock GrenadeProjectileData(DemonFireball) -{ - projectileShapeName = "plasmabolt.dts"; - emitterDelay = -1; - directDamage = 0.0; - hasDamageRadius = true; - indirectDamage = 0.4; - damageRadius = 5.0; // z0dd - ZOD, 8/13/02. Was 20.0 - radiusDamageType = $DamageType::zombie; - kickBackStrength = 1500; - - explosion = "PlasmaBoltExplosion"; - underwaterExplosion = "PlasmaBoltExplosion"; - velInheritFactor = 0; - splash = PlasmaSplash; - depthTolerance = 100.0; - - baseEmitter = DemonFBSmokeEmitter; - bubbleEmitter = DemonFBSmokeEmitter; - - grenadeElasticity = 0; - grenadeFriction = 0.4; - armingDelayMS = -1; // z0dd - ZOD, 4/14/02. Was 2000 - - gravityMod = 0.4; // z0dd - ZOD, 5/18/02. Make mortar projectile heavier, less floaty - muzzleVelocity = 50.0; // z0dd - ZOD, 8/13/02. More velocity to compensate for higher gravity. Was 63.7 - drag = 0; - sound = PlasmaProjectileSound; - - hasLight = true; - lightRadius = 10; - lightColor = "1 0.75 0.25"; - - hasLightUnderwaterColor = true; - underWaterLightColor = "1 0.75 0.25"; -}; - -datablock GrenadeProjectileData(DemonFlamingFireball) { - projectileShapeName = "plasmabolt.dts"; - emitterDelay = -1; - directDamage = 0.0; - hasDamageRadius = true; - indirectDamage = 0.4; - damageRadius = 5.0; // z0dd - ZOD, 8/13/02. Was 20.0 - radiusDamageType = $DamageType::Fire; - kickBackStrength = 1500; - - explosion = "PlasmaBoltExplosion"; - underwaterExplosion = "PlasmaBoltExplosion"; - velInheritFactor = 0; - splash = PlasmaSplash; - depthTolerance = 100.0; - - baseEmitter = ThrowerBaseEmitter; - bubbleEmitter = ThrowerBaseEmitter; - - grenadeElasticity = 0; - grenadeFriction = 0.4; - armingDelayMS = -1; // z0dd - ZOD, 4/14/02. Was 2000 - - gravityMod = 0.4; // z0dd - ZOD, 5/18/02. Make mortar projectile heavier, less floaty - muzzleVelocity = 50.0; // z0dd - ZOD, 8/13/02. More velocity to compensate for higher gravity. Was 63.7 - drag = 0; - sound = PlasmaProjectileSound; - - hasLight = true; - lightRadius = 10; - lightColor = "1 0.75 0.25"; - - hasLightUnderwaterColor = true; - underWaterLightColor = "1 0.75 0.25"; -}; - datablock StaticShapeData(DeployedZSpawnBase) : StaticShapeDamageProfile { className = "lightbase"; shapeFile = "pack_deploy_sensor_motion.dts"; @@ -292,7 +75,9 @@ datablock ItemData(ZSpawnDeployable) { function ZSpawnDeployableImage::testObjectTooClose(%item) { return ""; } + function ZSpawnDeployableImage::testNoTerrainFound(%item) {} + function ZSpawnDeployable::onPickup(%this, %obj, %shape, %amount) {} function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { @@ -300,10 +85,12 @@ function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { %playerVector = vectorNormalize(-1 * getWord(%plyr.getEyeVector(),1) SPC getWord(%plyr.getEyeVector(),0) SPC "0"); - if (vAbs(floorVec(%item.surfaceNrm,100)) $= "0 0 1") + if (vAbs(floorVec(%item.surfaceNrm,100)) $= "0 0 1") { %item.surfaceNrm2 = %playerVector; - else + } + else { %item.surfaceNrm2 = vectorNormalize(vectorCross(%item.surfaceNrm,"0 0 -1")); + } %rot = fullRot(%item.surfaceNrm,%item.surfaceNrm2); @@ -315,8 +102,9 @@ function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { %deplObj.setTransform(%item.surfacePt SPC %rot); // set the recharge rate right away - if (%deplObj.getDatablock().rechargeRate) + if (%deplObj.getDatablock().rechargeRate) { %deplObj.setRechargeRate(%deplObj.getDatablock().rechargeRate); + } // set team, owner, and handle %deplObj.team = %plyr.client.Team; @@ -324,8 +112,9 @@ function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { %deplObj.light.lightBase = %deplObj; // set the sensor group if it needs one - if (%deplObj.getTarget() != -1) + if (%deplObj.getTarget() != -1) { setTargetSensorGroup(%deplObj.getTarget(), %plyr.client.team); + } // place the deployable in the MissionCleanup/Deployables group (AI reasons) addToDeployGroup(%deplObj); @@ -345,10 +134,10 @@ function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { %deplObj.playThread($AmbientThread,"ambient"); // take the deployable off the player's back and out of inventory - if(!%plyr.client.isSuperAdmin) { - %plyr.unmountImage(%slot); - %plyr.decInventory(%item.item, 1); - } + if(!%plyr.client.isSuperAdmin) { + %plyr.unmountImage(%slot); + %plyr.decInventory(%item.item, 1); + } // set power frequency %deplObj.powerFreq = %plyr.powerFreq; @@ -356,84 +145,92 @@ function ZSpawnDeployableImage::onDeploy(%item, %plyr, %slot) { // Power object checkPowerObject(%deplObj); - switch(%plyr.packset) { - case 0: - %deplobj.ZType = 1; - case 1: - %deplobj.ZType = 2; - case 2: - %deplobj.ZType = 3; - %deplobj.numZ = 2; - case 3: - %deplobj.ZType = 4; - case 4: - %deplobj.ZType = 5; - case 5: - %deplobj.ZType = 6; - case 6: - %deplobj.ZType = 9; - case 7: - %deplobj.ZType = 11; - case 8: - %deplobj.ZType = 12; - case 9: - %deplobj.ZType = 13; - case 10: - %deplobj.ZType = 14; - case 11: - %deplobj.ZType = 15; - case 12: - %deplobj.ZType = 16; - case 13: - %deplobj.ZType = 17; - } + switch(%plyr.packset) { + case 0: + %deplobj.ZType = 1; + case 1: + %deplobj.ZType = 2; + case 2: + %deplobj.ZType = 3; + %deplobj.numZ = 2; + case 3: + %deplobj.ZType = 4; + case 4: + %deplobj.ZType = 5; + case 5: + %deplobj.ZType = 6; + case 6: + %deplobj.ZType = 9; + case 7: + %deplobj.ZType = 11; + case 8: + %deplobj.ZType = 12; + case 9: + %deplobj.ZType = 13; + case 10: + %deplobj.ZType = 14; + case 11: + %deplobj.ZType = 15; + case 12: + %deplobj.ZType = 16; + case 13: + %deplobj.ZType = 17; + } %deplobj.spawnTypeSet = %plyr.expertset; return %deplObj; } function DeployedZSpawnBase::onDestroyed(%this,%obj,%prevState) { - if (%obj.isRemoved) + if (%obj.isRemoved) { return; + } %obj.isRemoved = true; Parent::onDestroyed(%this,%obj,%prevState); $TeamDeployedCount[%obj.team, ZSpawnDeployable]--; remDSurface(%obj); %obj.schedule(500, "delete"); - if (%obj.ZCloop !$= "") - Cancel(%obj.ZCLoop); + if (%obj.ZCloop !$= "") { + Cancel(%obj.ZCLoop); + } } function DeployedZSpawnBase::disassemble(%data,%plyr,%obj) { - if (%obj.ZCloop !$= "") - Cancel(%obj.ZCLoop); + if (%obj.ZCloop !$= "") { + Cancel(%obj.ZCLoop); + } disassemble(%data,%plyr,%obj); } function ZSpawnDeployableImage::onMount(%data, %obj, %node) { - %obj.hasZSpawn = true; - %obj.expertset = 0; + %obj.hasZSpawn = true; + %obj.expertset = 0; } function ZSpawnDeployableImage::onUnmount(%data, %obj, %node) { - %obj.hasZSpawn = ""; + %obj.hasZSpawn = ""; } function DeployedZSpawnBase::onGainPowerEnabled(%data,%obj) { - if(%obj.spawnTypeSet == 1) - %obj.numz = 0; - if (%obj.ZCloop !$= "") - Cancel(%obj.ZCLoop); - %obj.ZCLoop = schedule(1000, 0, "ZcreateLoop", %obj); - Parent::onGainPowerEnabled(%data,%obj); + if(%obj.spawnTypeSet == 1) { + %obj.numz = 0; + } + if (%obj.ZCloop !$= "") { + Cancel(%obj.ZCLoop); + } + %obj.ZCLoop = schedule(1000, 0, "ZcreateLoop", %obj); + Parent::onGainPowerEnabled(%data,%obj); } function DeployedZSpawnBase::onLosePowerDisabled(%data,%obj) { - if (%obj.ZCloop !$= "") - Cancel(%obj.ZCLoop); - Parent::onLosePowerDisabled(%data,%obj); + if (%obj.ZCloop !$= "") { + Cancel(%obj.ZCLoop); + } + Parent::onLosePowerDisabled(%data,%obj); } +//Phantom139: Personal note, rework this at some point using a built in datablock function and +// a simtimer such that we can remove that eval statement. function ZcreateLoop(%obj) { if(isObject(%obj)) { if(%obj.timedout == 0){ diff --git a/scripts/server.cs b/scripts/server.cs index a6bf39d..9e1202c 100644 --- a/scripts/server.cs +++ b/scripts/server.cs @@ -58,6 +58,10 @@ function CreateServer(%mission, %missionType) exec("scripts/particleEmitter.cs"); // Must exist before item.cs and explosion.cs exec("scripts/particleDummies.cs"); exec("scripts/projectiles.cs"); // Must exits before item.cs + echo("*********************"); + echo("* LOADING TWM2 DATABLOCKS"); + exec("scripts/TWM2/MultiUseDatablocks.cs"); + echo("*********************"); exec("scripts/player.cs"); exec("scripts/gameBase.cs"); exec("scripts/staticShape.cs"); diff --git a/scripts/weapons/Melee/Plasmasabre.cs b/scripts/weapons/Melee/Plasmasabre.cs index 524f14c..70fda8c 100644 --- a/scripts/weapons/Melee/Plasmasabre.cs +++ b/scripts/weapons/Melee/Plasmasabre.cs @@ -110,7 +110,7 @@ datablock ShapeBaseImageData(PlasmasaberImage) { stateName[4] = "Reload"; stateTransitionOnTimeout[4] = "Ready"; - stateTimeoutValue[4] = 1.5; + stateTimeoutValue[4] = 0.8; stateAllowImageChange[4] = false; };