Merge branch 'master' into utmovement

This commit is contained in:
Marisa the Magician 2018-08-17 21:12:58 +02:00
commit aa63ab7555
12 changed files with 98 additions and 47 deletions

View file

@ -21,3 +21,4 @@ user bool flak_footsteps = true;
server bool flak_translocator = false; server bool flak_translocator = false;
user bool flak_noswitchdeemer = true; // don't switch to redeemer when out of ammo user bool flak_noswitchdeemer = true; // don't switch to redeemer when out of ammo
user bool flak_deemershader = false; user bool flak_deemershader = false;
server bool flak_classicsshock = false; // classic enhanced shock rifle (no altfire, beams don't have splash damage)

View file

@ -25,6 +25,7 @@ OptionMenu "UTOptionMenu"
Option "Redeemer Target Visuals", "flak_redeemerreadout", "YesNo" Option "Redeemer Target Visuals", "flak_redeemerreadout", "YesNo"
Option "Redeemer View Shader", "flak_deemershader", "YesNo" Option "Redeemer View Shader", "flak_deemershader", "YesNo"
Option "No Redeemer Autoswitch", "flak_noswitchdeemer", "YesNo" Option "No Redeemer Autoswitch", "flak_noswitchdeemer", "YesNo"
Option "Classic Enh. Shock Rifle", "flak_classicsshock", "YesNo"
StaticText " " StaticText " "
Option "Enable Translocator", "flak_translocator", "YesNo" Option "Enable Translocator", "flak_translocator", "YesNo"
Command "Apply Changes", "event refreshtrans" Command "Apply Changes", "event refreshtrans"

View file

@ -411,7 +411,8 @@ Class BioGel : Actor
s.args[3] = int(s.args[3]*Scale.x); s.args[3] = int(s.args[3]*Scale.x);
invoker.deadtimer = -2; invoker.deadtimer = -2;
if ( invoker.atline ) invoker.atline.RemoteActivate(target,invoker.atside,SPAC_Impact,pos); if ( invoker.atline ) invoker.atline.RemoteActivate(target,invoker.atside,SPAC_Impact,pos);
A_Explode(int(Random[GES](10,15)*max(1,(Scale.x-1)**2)),Min(150,int(Scale.x*25))); UTMainHandler.DoBlast(self,Min(150,int(Scale.x*25)),20000*Scale.x);
A_Explode(int(Random[GES](18,22)*max(1,(Scale.x-1)**2)),Min(150,int(Scale.x*25)));
A_PlaySound("ges/explode",CHAN_VOICE); A_PlaySound("ges/explode",CHAN_VOICE);
int numpt = Min(300,int(Scale.x*30))+Random[GES](-10,10); int numpt = Min(300,int(Scale.x*30))+Random[GES](-10,10);
for ( int i=0; i<numpt; i++ ) for ( int i=0; i<numpt; i++ )
@ -437,13 +438,11 @@ Class BioGel : Actor
{ {
Obituary "%o drank a glass of %k's dripping green load."; Obituary "%o drank a glass of %k's dripping green load.";
DamageType 'Slime'; DamageType 'Slime';
DamageFunction int(Random[GES](10,15)*max(1,(Scale.x-1)**2));
RenderStyle "Add"; RenderStyle "Add";
Radius 3; Radius 3;
Height 3; Height 3;
Scale 2; Scale 2;
Speed 18; Speed 18;
ProjectileKickback 120;
Gravity 0.5; Gravity 0.5;
PROJECTILE; PROJECTILE;
-NOGRAVITY; -NOGRAVITY;
@ -452,6 +451,7 @@ Class BioGel : Actor
+FORCERADIUSDMG; +FORCERADIUSDMG;
+FORCEXYBILLBOARD; +FORCEXYBILLBOARD;
+MOVEWITHSECTOR; +MOVEWITHSECTOR;
+NODAMAGETHRUST;
} }
States States
{ {

View file

@ -105,16 +105,16 @@ Class UTRocket : Actor
Default Default
{ {
Obituary "%o was smacked down by %k's Rocket Launcher."; Obituary "%o was smacked down by %k's Rocket Launcher.";
DamageFunction Random[Eightball](90,115);
DamageType 'RocketDeath'; DamageType 'RocketDeath';
Radius 2; Radius 2;
Height 2; Height 2;
Speed 18; Speed 18;
ProjectileKickback 400;
PROJECTILE; PROJECTILE;
+SKYEXPLODE; +SKYEXPLODE;
+EXPLODEONWATER; +EXPLODEONWATER;
+SEEKERMISSILE; +SEEKERMISSILE;
+FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
override void PostBeginPlay() override void PostBeginPlay()
{ {
@ -123,15 +123,16 @@ Class UTRocket : Actor
l.target = self; l.target = self;
A_PlaySound("utrl/fly",CHAN_VOICE,1.0,true,2.5); A_PlaySound("utrl/fly",CHAN_VOICE,1.0,true,2.5);
} }
action void A_RocketExplode() action void A_RocketExplode( int dmg )
{ {
bFORCEXYBILLBOARD = true; bFORCEXYBILLBOARD = true;
A_SetRenderStyle(1.0,STYLE_Add); A_SetRenderStyle(1.0,STYLE_Add);
A_SprayDecal("RocketBlast",150); A_SprayDecal("RocketBlast",150);
A_NoGravity(); A_NoGravity();
A_SetScale(0.75); A_SetScale(0.75);
A_Explode(Random[Eightball](80,100),100); UTMainHandler.DoBlast(self,100,80000);
A_QuakeEx(3,3,3,8,0,250,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.2); A_Explode(dmg,100);
A_QuakeEx(3,3,3,8,0,250,"",QF_RELATIVE|QF_SCALEDOWN,falloff:100,rollIntensity:0.2);
A_PlaySound("utrl/explode",CHAN_VOICE); A_PlaySound("utrl/explode",CHAN_VOICE);
A_AlertMonsters(); A_AlertMonsters();
Spawn("RocketExplLight",pos); Spawn("RocketExplLight",pos);
@ -178,7 +179,7 @@ Class UTRocket : Actor
} }
Wait; Wait;
Death: Death:
TNT1 A 0 A_RocketExplode(); TNT1 A 0 A_RocketExplode(Random[Eightball](90,115));
SSMX ABCDEFGHIJ 2 Bright; SSMX ABCDEFGHIJ 2 Bright;
Stop; Stop;
} }
@ -190,7 +191,6 @@ Class UTGrenade : UTRocket
Default Default
{ {
DamageFunction Random[Eightball](90,120);
DamageType 'GrenadeDeath'; DamageType 'GrenadeDeath';
-NOGRAVITY; -NOGRAVITY;
+USEBOUNCESTATE; +USEBOUNCESTATE;
@ -231,6 +231,9 @@ Class UTGrenade : UTRocket
anglevel = FRandom[Eightball](-16,16); anglevel = FRandom[Eightball](-16,16);
} }
Goto Spawn; Goto Spawn;
Death:
TNT1 A 0 A_RocketExplode(Random[Eightball](90,120));
Goto Super::Death+1;
} }
} }

View file

@ -313,7 +313,8 @@ Class Enforcer : UTWeapon replaces Pistol
if ( d.HitType == TRACE_HitActor ) if ( d.HitType == TRACE_HitActor )
{ {
int dmg = Random[Enforcer](12,17); int dmg = Random[Enforcer](12,17);
dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE,atan2(d.HitDir.y,d.HitDir.x)); dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE|DMG_THRUSTLESS,atan2(d.HitDir.y,d.HitDir.x));
UTMainHandler.DoKnockback(d.HitActor,d.HitDir,3000);
if ( d.HitActor.bNOBLOOD ) if ( d.HitActor.bNOBLOOD )
{ {
let p = Spawn("BulletImpact",d.HitLocation); let p = Spawn("BulletImpact",d.HitLocation);

View file

@ -133,7 +133,6 @@ Class FlakChunk : Actor
double rollvel, pitchvel, yawvel; double rollvel, pitchvel, yawvel;
double lifetime, lifespeed; double lifetime, lifespeed;
int lifetics; int lifetics;
bool hasbounced;
Default Default
{ {
Obituary "%o was ripped to shreds by %k's Flak Cannon."; Obituary "%o was ripped to shreds by %k's Flak Cannon.";
@ -210,7 +209,6 @@ Class FlakChunk : Actor
} }
action void A_HandleBounce() action void A_HandleBounce()
{ {
invoker.hasbounced = true;
A_SprayDecal("WallCrack",-8); A_SprayDecal("WallCrack",-8);
int numpt = Random[Flak](2,3); int numpt = Random[Flak](2,3);
if ( frame < 10 ) if ( frame < 10 )
@ -359,16 +357,16 @@ Class FlakSlug : Actor
{ {
Obituary "%o was ripped to shreds by %k's Flak Cannon."; Obituary "%o was ripped to shreds by %k's Flak Cannon.";
DamageType 'FlakDeath'; DamageType 'FlakDeath';
DamageFunction Random[Flak](100,110);
Radius 2; Radius 2;
Height 2; Height 2;
Speed 40; Speed 40;
ProjectileKickback 320;
PROJECTILE; PROJECTILE;
-NOGRAVITY; -NOGRAVITY;
+SKYEXPLODE; +SKYEXPLODE;
+EXPLODEONWATER; +EXPLODEONWATER;
+HITTRACER; +HITTRACER;
+FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
override void PostBeginPlay() override void PostBeginPlay()
{ {
@ -387,8 +385,9 @@ Class FlakSlug : Actor
A_SprayDecal("RocketBlast",150); A_SprayDecal("RocketBlast",150);
A_NoGravity(); A_NoGravity();
A_SetScale(1.2); A_SetScale(1.2);
UTMainHandler.DoBlast(self,80,75000);
A_Explode(Random[Flak](70,80),80); A_Explode(Random[Flak](70,80),80);
A_QuakeEx(4,4,4,8,0,200,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.2); A_QuakeEx(4,4,4,8,0,200,"",QF_RELATIVE|QF_SCALEDOWN,falloff:80,rollIntensity:0.2);
A_PlaySound("flak/explode",CHAN_VOICE); A_PlaySound("flak/explode",CHAN_VOICE);
A_AlertMonsters(); A_AlertMonsters();
if ( !Tracer ) Spawn("SlugSmoke",pos); if ( !Tracer ) Spawn("SlugSmoke",pos);

View file

@ -124,7 +124,8 @@ Class Minigun : UTWeapon
if ( d.HitType == TRACE_HitActor ) if ( d.HitType == TRACE_HitActor )
{ {
int dmg = Random[Minigun](16,20); // fun fact: the Minigun is one of the few weapons that has actual RNG damage in UT int dmg = Random[Minigun](16,20); // fun fact: the Minigun is one of the few weapons that has actual RNG damage in UT
dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE,atan2(d.HitDir.y,d.HitDir.x)); dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE|DMG_THRUSTLESS,atan2(d.HitDir.y,d.HitDir.x));
UTMainHandler.DoKnockback(d.HitActor,d.HitDir,dmg*500);
if ( d.HitActor.bNOBLOOD ) if ( d.HitActor.bNOBLOOD )
{ {
let p = Spawn("BulletImpact",d.HitLocation); let p = Spawn("BulletImpact",d.HitLocation);

View file

@ -70,6 +70,7 @@ Class Razor2 : Actor
-BOUNCEAUTOOFF; -BOUNCEAUTOOFF;
+SKYEXPLODE; +SKYEXPLODE;
+CANBOUNCEWATER; +CANBOUNCEWATER;
+NODAMAGETHRUST;
} }
override void PostBeginPlay() override void PostBeginPlay()
{ {
@ -95,6 +96,7 @@ Class Razor2 : Actor
A_PlaySound("ripper/flesh"); A_PlaySound("ripper/flesh");
A_AlertMonsters(); A_AlertMonsters();
} }
UTMainHandler.DoKnockback(target,vel.unit(),15000);
return damage; return damage;
} }
action void A_RazorHit() action void A_RazorHit()
@ -183,12 +185,13 @@ Class Razor2Alt : Razor2
{ {
Default Default
{ {
DamageFunction Random[Ripper](40,60); DamageFunction 0;
DamageType 'RipperAltDealth'; DamageType 'RipperAltDealth';
BounceType "None"; BounceType "None";
ProjectileKickback 350;
-CANBOUNCEWATER; -CANBOUNCEWATER;
+EXPLODEONWATER; +EXPLODEONWATER;
+FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
action void A_RazorExplode() action void A_RazorExplode()
{ {
@ -200,8 +203,9 @@ Class Razor2Alt : Razor2
Spawn("Razor2AltLight",pos); Spawn("Razor2AltLight",pos);
A_AlertMonsters(); A_AlertMonsters();
A_SprayDecal("RazorBlast",20); A_SprayDecal("RazorBlast",20);
UTMainHandler.DoBlast(self,120,87000);
A_Explode(Random[Ripper](30,50),120); A_Explode(Random[Ripper](30,50),120);
A_QuakeEx(3,3,3,10,0,180,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.1); A_QuakeEx(3,3,3,10,0,180,"",QF_RELATIVE|QF_SCALEDOWN,falloff:120,rollIntensity:0.1);
int numpt = Random[Ripper](10,20); int numpt = Random[Ripper](10,20);
Vector3 x = (cos(angle)*cos(pitch),sin(angle)*cos(pitch),-sin(pitch)); Vector3 x = (cos(angle)*cos(pitch),sin(angle)*cos(pitch),-sin(pitch));
for ( int i=0; i<numpt; i++ ) for ( int i=0; i<numpt; i++ )

View file

@ -277,12 +277,12 @@ Class ShockBeam : Actor
Radius 0.1; Radius 0.1;
Height 0; Height 0;
Scale 0.4; Scale 0.4;
ProjectileKickback 250;
+NOGRAVITY; +NOGRAVITY;
+NOCLIP; +NOCLIP;
+DONTSPLASH; +DONTSPLASH;
+FORCEXYBILLBOARD; +FORCEXYBILLBOARD;
+FORCERADIUSDMG; +FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
override void PostBeginPlay() override void PostBeginPlay()
{ {
@ -336,9 +336,10 @@ Class ShockBeam : Actor
{ {
if ( target ) target.TakeInventory('ShockAmmo',2); if ( target ) target.TakeInventory('ShockAmmo',2);
let b = t.Results.HitActor.target; let b = t.Results.HitActor.target;
UTMainHandler.DoBlast(b,300,70000);
b.ExplodeMissile(null,self); b.ExplodeMissile(null,self);
b.A_Explode(Random[ASMD](150,160),300); b.A_Explode(Random[ASMD](150,160),300);
b.A_QuakeEx(6,6,6,60,0,1200,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.2); b.A_QuakeEx(6,6,6,60,0,1200,"",QF_RELATIVE|QF_SCALEDOWN,falloff:300,rollIntensity:0.2);
b.A_SprayDecal("BigShockMark1",100); b.A_SprayDecal("BigShockMark1",100);
b.A_SprayDecal("BigShockMark2",100); b.A_SprayDecal("BigShockMark2",100);
Spawn("ShockRifleWave",b.pos); Spawn("ShockRifleWave",b.pos);
@ -358,6 +359,7 @@ Class ShockBeam : Actor
else else
{ {
t.Results.HitActor.DamageMobj(self,target,Random[ASMD](35,50),'jolted',DMG_USEANGLE,atan2(t.Results.HitVector.y,t.Results.HitVector.x)); t.Results.HitActor.DamageMobj(self,target,Random[ASMD](35,50),'jolted',DMG_USEANGLE,atan2(t.Results.HitVector.y,t.Results.HitVector.x));
UTMainHandler.DoKnockback(t.Results.HitActor,t.Results.HitVector,60000);
let r = Spawn("ShockBeamRing",pos); let r = Spawn("ShockBeamRing",pos);
r.angle = atan2(t.Results.HitVector.y,t.Results.HitVector.x); r.angle = atan2(t.Results.HitVector.y,t.Results.HitVector.x);
r.pitch = asin(-t.Results.HitVector.z); r.pitch = asin(-t.Results.HitVector.z);
@ -391,7 +393,7 @@ Class ShockBeam : Actor
action void A_BeamExplode() action void A_BeamExplode()
{ {
Spawn("ShockBeamLight",pos); Spawn("ShockBeamLight",pos);
A_QuakeEx(2,2,2,5,0,120,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.1); A_QuakeEx(2,2,2,5,0,120,"",QF_RELATIVE|QF_SCALEDOWN,falloff:60,rollIntensity:0.1);
A_PlaySound("shock/hit",CHAN_VOICE); A_PlaySound("shock/hit",CHAN_VOICE);
A_AlertMonsters(); A_AlertMonsters();
int numpt = Random[ASMD](20,50); int numpt = Random[ASMD](20,50);
@ -503,6 +505,7 @@ Class SuperShockBeam : Actor
+FORCEXYBILLBOARD; +FORCEXYBILLBOARD;
+FORCERADIUSDMG; +FORCERADIUSDMG;
+EXTREMEDEATH; +EXTREMEDEATH;
+NODAMAGETHRUST;
} }
override void PostBeginPlay() override void PostBeginPlay()
{ {
@ -556,9 +559,10 @@ Class SuperShockBeam : Actor
{ {
if ( target ) target.TakeInventory('EnhancedShockAmmo',1); if ( target ) target.TakeInventory('EnhancedShockAmmo',1);
let b = t.Results.HitActor.target; let b = t.Results.HitActor.target;
UTMainHandler.DoBlast(b,400,70000);
b.ExplodeMissile(null,self); b.ExplodeMissile(null,self);
b.A_Explode(Random[ASMD](15000,16000),400); b.A_Explode(Random[ASMD](15000,16000),400);
b.A_QuakeEx(9,9,9,60,0,2400,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.4); b.A_QuakeEx(9,9,9,60,0,2400,"",QF_RELATIVE|QF_SCALEDOWN,falloff:400,rollIntensity:0.4);
b.A_SprayDecal("BigShockMark1",100); b.A_SprayDecal("BigShockMark1",100);
b.A_SprayDecal("SBigShockMark2",100); b.A_SprayDecal("SBigShockMark2",100);
Spawn("SuperShockRifleWave",b.pos); Spawn("SuperShockRifleWave",b.pos);
@ -578,7 +582,8 @@ Class SuperShockBeam : Actor
} }
else else
{ {
t.Results.HitActor.DamageMobj(self,target,Random[ASMD](3500,5000),'joltedX',DMG_USEANGLE,atan2(t.Results.HitVector.y,t.Results.HitVector.x)); t.Results.HitActor.DamageMobj(self,target,Random[ASMD](3500,5000),'joltedX',DMG_USEANGLE|DMG_THRUSTLESS,atan2(t.Results.HitVector.y,t.Results.HitVector.x));
UTMainHandler.DoKnockback(t.Results.HitActor,t.Results.HitVector,60000);
let r = Spawn("SuperShockBeamRing",pos); let r = Spawn("SuperShockBeamRing",pos);
r.angle = atan2(t.Results.HitVector.y,t.Results.HitVector.x); r.angle = atan2(t.Results.HitVector.y,t.Results.HitVector.x);
r.pitch = asin(-t.Results.HitVector.z); r.pitch = asin(-t.Results.HitVector.z);
@ -612,8 +617,12 @@ Class SuperShockBeam : Actor
action void A_BeamExplode() action void A_BeamExplode()
{ {
Spawn("SuperShockBeamLight",pos); Spawn("SuperShockBeamLight",pos);
A_Explode(Random[ASMD](500,800),90); if ( !CVar.GetCVar('flak_classicsshock').GetBool() )
A_QuakeEx(6,6,6,5,0,200,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.2); {
UTMainHandler.DoBlast(self,90,60000);
A_Explode(Random[ASMD](500,800),90);
}
A_QuakeEx(6,6,6,5,0,200,"",QF_RELATIVE|QF_SCALEDOWN,falloff:90,rollIntensity:0.2);
A_PlaySound("shock/hit",CHAN_VOICE,attenuation:0.5); A_PlaySound("shock/hit",CHAN_VOICE,attenuation:0.5);
A_PlaySound("sshock/blast",CHAN_6,attenuation:0.5); A_PlaySound("sshock/blast",CHAN_6,attenuation:0.5);
A_AlertMonsters(); A_AlertMonsters();
@ -819,6 +828,7 @@ Class ShockBall : Actor
} }
action void A_BallExplode() action void A_BallExplode()
{ {
UTMainHandler.DoBlast(self,70,70000);
A_Explode(Random[ASMD](40,50),70); A_Explode(Random[ASMD](40,50),70);
A_SprayDecal("ShockMarkBig",16); A_SprayDecal("ShockMarkBig",16);
Spawn("ShockExplLight",pos); Spawn("ShockExplLight",pos);
@ -829,7 +839,7 @@ Class ShockBall : Actor
r.scale *= 1.5; r.scale *= 1.5;
A_PlaySound("shock/hit",CHAN_VOICE); A_PlaySound("shock/hit",CHAN_VOICE);
A_PlaySound("shock/ball",CHAN_WEAPON); A_PlaySound("shock/ball",CHAN_WEAPON);
A_QuakeEx(4,4,4,30,0,200,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.15); A_QuakeEx(4,4,4,30,0,200,"",QF_RELATIVE|QF_SCALEDOWN,falloff:70,rollIntensity:0.15);
A_AlertMonsters(); A_AlertMonsters();
int numpt = Random[ASMD](50,100); int numpt = Random[ASMD](50,100);
for ( int i=0; i<numpt; i++ ) for ( int i=0; i<numpt; i++ )
@ -844,16 +854,16 @@ Class ShockBall : Actor
Obituary "%k inflicted mortal damage upon %o with the Shock Rifle"; Obituary "%k inflicted mortal damage upon %o with the Shock Rifle";
RenderStyle "Add"; RenderStyle "Add";
DamageType 'jolted'; DamageType 'jolted';
DamageFunction Random[ASMD](50,60);
Radius 2; Radius 2;
Height 2; Height 2;
Scale 0.4; Scale 0.4;
Speed 20; Speed 20;
ProjectileKickback 250;
PROJECTILE; PROJECTILE;
+FORCEXYBILLBOARD; +FORCEXYBILLBOARD;
+SKYEXPLODE; +SKYEXPLODE;
+EXPLODEONWATER; +EXPLODEONWATER;
+FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
States States
{ {
@ -882,6 +892,7 @@ Class SuperShockBall : Actor
} }
action void A_BallExplode() action void A_BallExplode()
{ {
UTMainHandler.DoBlast(self,120,70000);
A_Explode(Random[ASMD](4000,5000),120); A_Explode(Random[ASMD](4000,5000),120);
A_SprayDecal("ShockMarkBig",16); A_SprayDecal("ShockMarkBig",16);
Spawn("SuperShockExplLight",pos); Spawn("SuperShockExplLight",pos);
@ -893,7 +904,7 @@ Class SuperShockBall : Actor
A_PlaySound("shock/hit",CHAN_VOICE,attenuation:0.5); A_PlaySound("shock/hit",CHAN_VOICE,attenuation:0.5);
A_PlaySound("shock/ball",CHAN_WEAPON,attenuation:0.5); A_PlaySound("shock/ball",CHAN_WEAPON,attenuation:0.5);
A_PlaySound("sshock/blast",CHAN_6,attenuation:0.5); A_PlaySound("sshock/blast",CHAN_6,attenuation:0.5);
A_QuakeEx(8,8,8,30,0,300,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.25); A_QuakeEx(8,8,8,30,0,300,"",QF_RELATIVE|QF_SCALEDOWN,falloff:120,rollIntensity:0.25);
A_AlertMonsters(); A_AlertMonsters();
int numpt = Random[ASMD](50,100); int numpt = Random[ASMD](50,100);
for ( int i=0; i<numpt; i++ ) for ( int i=0; i<numpt; i++ )
@ -908,7 +919,6 @@ Class SuperShockBall : Actor
Obituary "%k electrified %o with the Enhanced Shock Rifle."; Obituary "%k electrified %o with the Enhanced Shock Rifle.";
RenderStyle "Add"; RenderStyle "Add";
DamageType 'joltedX'; DamageType 'joltedX';
DamageFunction Random[ASMD](5000,6000);
Radius 2; Radius 2;
Height 2; Height 2;
Scale 0.5; Scale 0.5;
@ -919,6 +929,8 @@ Class SuperShockBall : Actor
+FORCERADIUSDMG; +FORCERADIUSDMG;
+EXTREMEDEATH; +EXTREMEDEATH;
+EXPLODEONWATER; +EXPLODEONWATER;
+FORCERADIUSDMG;
+NODAMAGETHRUST;
} }
States States
{ {
@ -1101,6 +1113,17 @@ Class ShockRifle : UTWeapon
Class EnhancedShockAmmo : Ammo Class EnhancedShockAmmo : Ammo
{ {
int ticcnt;
override void Tick()
{
Super.Tick();
if ( !Owner ) return;
ticcnt++;
if ( ticcnt < 105 ) return;
ticcnt = 0;
if ( Amount > 0 ) Amount--;
}
Default Default
{ {
Tag "Enhanced Shock Core"; Tag "Enhanced Shock Core";
@ -1132,17 +1155,6 @@ Class ViewSuperShockSpark : ViewShockSpark
Class EnhancedShockRifle : UTWeapon replaces InvulnerabilitySphere Class EnhancedShockRifle : UTWeapon replaces InvulnerabilitySphere
{ {
int ticcnt;
override void Tick()
{
Super.Tick();
if ( !Owner ) return;
ticcnt++;
if ( ticcnt < 105 ) return;
ticcnt = 0;
DepleteAmmo(false,true,1);
}
action void A_SShockFire() action void A_SShockFire()
{ {
Weapon weap = Weapon(invoker); Weapon weap = Weapon(invoker);
@ -1259,6 +1271,7 @@ Class EnhancedShockRifle : UTWeapon replaces InvulnerabilitySphere
ASMF BCDEFGHIJJ 2; ASMF BCDEFGHIJJ 2;
Goto Idle; Goto Idle;
AltFire: AltFire:
ASMI A 0 A_JumpIf(CVar.GetCVar('flak_classicsshock').GetBool(),"Fire");
ASMI A 0 A_JumpIfNoAmmo("DryFire"); ASMI A 0 A_JumpIfNoAmmo("DryFire");
ASMA A 1 A_SShockAlt(); ASMA A 1 A_SShockAlt();
ASMA BCDFGHIJ 2; ASMA BCDFGHIJ 2;

View file

@ -96,8 +96,15 @@ Class SniperRifle : UTWeapon
{ {
int dmg = Random[Sniper](45,60); int dmg = Random[Sniper](45,60);
if ( d.HitLocation.z >= (d.HitActor.pos.z+d.HitActor.height*0.8) ) if ( d.HitLocation.z >= (d.HitActor.pos.z+d.HitActor.height*0.8) )
dmg = d.HitActor.DamageMobj(invoker,self,dmg+70,'Decapitated',DMG_USEANGLE,atan2(d.HitDir.y,d.HitDir.x)); {
else dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE,atan2(d.HitDir.y,d.HitDir.x)); dmg = d.HitActor.DamageMobj(invoker,self,dmg+70,'Decapitated',DMG_USEANGLE|DMG_THRUSTLESS,atan2(d.HitDir.y,d.HitDir.x));
UTMainHandler.DoKnockback(d.HitActor,d.HitDir,35000);
}
else
{
dmg = d.HitActor.DamageMobj(invoker,self,dmg,'shot',DMG_USEANGLE|DMG_THRUSTLESS,atan2(d.HitDir.y,d.HitDir.x));
UTMainHandler.DoKnockback(d.HitActor,d.HitDir,30000);
}
if ( d.HitActor.bNOBLOOD ) if ( d.HitActor.bNOBLOOD )
{ {
let p = Spawn("BulletImpact",d.HitLocation); let p = Spawn("BulletImpact",d.HitLocation);

View file

@ -1012,4 +1012,25 @@ Class UTMainHandler : StaticEventHandler
let hnd = UTMainHandler(StaticEventHandler.Find("UTMainHandler")); let hnd = UTMainHandler(StaticEventHandler.Find("UTMainHandler"));
hnd.flashes.push(qf); hnd.flashes.push(qf);
} }
// Doom's explosions aren't fully 3D
static void DoBlast( Actor Source, double ExplosionRadius, double MomentumTransfer )
{
BlockThingsIterator bi = BlockThingsIterator.Create(Source,ExplosionRadius);
while ( bi.Next() )
{
Actor a = bi.Thing;
if ( !a || !a.bSHOOTABLE || !Source.CheckSight(a,0xf) || (a == Source) || (Source.Distance3D(a) > ExplosionRadius) )
continue;
Vector3 midpoint = a.Vec3Offset(0,0,a.height*0.5);
a.vel += Level.Vec3Diff(Source.pos,midpoint).unit()*(MomentumTransfer/(Thinker.TICRATE*a.mass));
}
}
// Same for this
static void DoKnockback( Actor Victim, Vector3 HitDirection, double MomentumTransfer )
{
if ( !Victim ) return;
Victim.vel += HitDirection*(MomentumTransfer/(Thinker.TICRATE*Victim.Mass));
}
} }

View file

@ -42,7 +42,7 @@ Class ShockWave : Actor
{ {
lifespan = ReactionTime; lifespan = ReactionTime;
A_PlaySound("warhead/explode",CHAN_VOICE,attenuation:ATTN_NONE); A_PlaySound("warhead/explode",CHAN_VOICE,attenuation:ATTN_NONE);
A_QuakeEx(9,9,9,100,0,12000,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.5); A_QuakeEx(9,9,9,100,0,12000,"",QF_RELATIVE|QF_SCALEDOWN,falloff:1200,rollIntensity:0.5);
} }
override void Tick() override void Tick()
{ {
@ -61,7 +61,7 @@ Class ShockWave : Actor
t.Reinit(); t.Reinit();
while ( a = Actor(t.Next()) ) while ( a = Actor(t.Next()) )
{ {
if ( !a.bShootable || !CheckSight(a) || (Distance3D(a) > dmgradius) ) continue; if ( !a.bShootable || !CheckSight(a,0xf) || (Distance3D(a) > dmgradius) ) continue;
Vector3 dir = Vec3To(a); Vector3 dir = Vec3To(a);
double dist = max(1,dir.length()); double dist = max(1,dir.length());
dir = dir/dist+(0,0,0.3); dir = dir/dist+(0,0,0.3);