A_AttachLight and friends are too performance intensive. Fall back to just spawning light actors.
This commit is contained in:
parent
bd6c799988
commit
64ab1c6633
6 changed files with 130 additions and 77 deletions
|
|
@ -19,10 +19,30 @@ Class FlameAmmo : Ammo
|
|||
}
|
||||
}
|
||||
|
||||
Class OnFireLight : DynamicLight
|
||||
{
|
||||
OnFire of;
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !of || !of.victim )
|
||||
{
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
Args[0] = clamp(of.Amount*4,0,255);
|
||||
Args[1] = clamp(of.Amount*2,0,128);
|
||||
Args[3] = int(max(of.victim.radius,of.victim.height))+60+clamp(of.amount/8,0,80);
|
||||
SetOrigin(of.Victim.Vec3Offset(0,0,of.Victim.Height/2),true);
|
||||
}
|
||||
}
|
||||
|
||||
Class OnFire : Thinker
|
||||
{
|
||||
Actor victim, instigator;
|
||||
int amount, cnt;
|
||||
Actor victim, instigator, lite;
|
||||
int amount, cnt, delay;
|
||||
bool forcespread;
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
|
|
@ -33,16 +53,14 @@ Class OnFire : Thinker
|
|||
}
|
||||
if ( victim.waterlevel > 0 )
|
||||
{
|
||||
victim.A_RemoveLight('OnFireLight');
|
||||
amount -= victim.waterlevel**2;
|
||||
if ( lite ) lite.Destroy();
|
||||
amount -= int(victim.waterlevel**2);
|
||||
}
|
||||
else victim.A_AttachLight('OnFireLight',DynamicLight.RandomFlickerLight,Color(4,2,0)*clamp(amount,0,63),int(max(victim.radius,victim.height))+60+min(amount/4,40),int(max(victim.radius,victim.height))+60+min(amount/4,40)+8,DynamicLight.LF_ATTENUATE,(0,0,victim.height/2),0.1);
|
||||
if ( victim.Health <= 0 ) amount = min(amount,100);
|
||||
if ( !(level.maptime%3) )
|
||||
amount -= ((victim.Health>0)?1:2);
|
||||
if ( amount < -10 )
|
||||
{
|
||||
victim.A_RemoveLight('OnFireLight');
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
|
|
@ -52,13 +70,14 @@ Class OnFire : Thinker
|
|||
{
|
||||
cnt = 10;
|
||||
if ( victim.bSHOOTABLE && (victim.Health > 0) )
|
||||
victim.DamageMobj(instigator.FindInventory("UFlamethrower"),instigator,max(1,amount*(victim.bBOSS?0.05:0.15)),'Fire',DMG_THRUSTLESS);
|
||||
victim.DamageMobj(instigator.FindInventory("UFlamethrower"),instigator,max(1,int(amount*(victim.bBOSS?0.05:0.15))),'Fire',DMG_THRUSTLESS);
|
||||
if ( !victim )
|
||||
{
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
}
|
||||
if ( delay > 0 ) delay--;
|
||||
if ( level.maptime%5 ) return;
|
||||
int numpt = clamp(int(Random[FlameT](2,4)*amount*0.02),1,4);
|
||||
double mult = max(victim.radius,victim.height)/30.;
|
||||
|
|
@ -71,12 +90,21 @@ Class OnFire : Thinker
|
|||
let c = victim.Spawn("UFlameTrail",pos);
|
||||
c.scale *= max(1.,mult*0.35);
|
||||
c.vel = victim.vel*0.5+(cos(ang)*cos(pt),sin(ang)*cos(pt),-sin(pt))*FRandom[FlameT](.5,2);
|
||||
c.master = instigator;
|
||||
c.tracer = victim;
|
||||
}
|
||||
if ( !sting_flametspread && !forcespread ) return;
|
||||
// spread to nearby actors
|
||||
let bt = BlockThingsIterator.Create(victim);
|
||||
while ( bt.Next() )
|
||||
{
|
||||
let t = bt.Thing;
|
||||
if ( !t || !t.bSHOOTABLE || (t.Health <= 0) || (t == victim) || ((t == instigator) && (delay > 0)) || (victim.Distance3D(t) > victim.radius+t.radius+20) || !victim.CheckSight(t) ) continue;
|
||||
int amt = max(1,amount/10);
|
||||
if ( IsOnFire(t) ) amt = min(5,amt);
|
||||
Apply(t,instigator,amt);
|
||||
}
|
||||
}
|
||||
|
||||
static void Apply( Actor victim, Actor instigator, int amount )
|
||||
static void Apply( Actor victim, Actor instigator, int amount, bool forcespread = false, int delay = 0 )
|
||||
{
|
||||
if ( amount <= 0 ) return;
|
||||
if ( victim is 'ShredCorpseHitbox' ) return;
|
||||
|
|
@ -96,6 +124,11 @@ Class OnFire : Thinker
|
|||
t.instigator = instigator;
|
||||
t.amount = amount;
|
||||
t.cnt = 1;
|
||||
// for napalm gel
|
||||
t.forcespread = forcespread;
|
||||
t.delay = delay;
|
||||
t.lite = Actor.Spawn("OnFireLight",victim.pos);
|
||||
OnFireLight(t.lite).of = t;
|
||||
}
|
||||
|
||||
static bool IsOnFire( Actor victim )
|
||||
|
|
@ -134,58 +167,20 @@ Class UFlameLight : PaletteLight
|
|||
SetOrigin(target.pos,true);
|
||||
}
|
||||
}
|
||||
Class UFlameTrailLight : PaletteLight
|
||||
{
|
||||
Default
|
||||
{
|
||||
Tag "Ampd";
|
||||
Args 0,0,0,80;
|
||||
ReactionTime 20;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
Args[0] /= 9;
|
||||
Args[1] /= 9;
|
||||
Args[2] /= 9;
|
||||
if ( !target || (target.waterlevel > 0) )
|
||||
{
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
SetOrigin(target.pos,true);
|
||||
}
|
||||
}
|
||||
|
||||
Class UFlame : Actor
|
||||
{
|
||||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
let l = Spawn("UFlameLight",pos);
|
||||
l.target = self;
|
||||
if ( waterlevel <= 0 )
|
||||
{
|
||||
let l = Spawn("UFlameLight",pos);
|
||||
l.target = self;
|
||||
}
|
||||
Scale.x *= RandomPick[ExploS](-1,1);
|
||||
Scale.y *= RandomPick[ExploS](-1,1);
|
||||
}
|
||||
bool TraceCheck( Actor other )
|
||||
{
|
||||
Vector3 to;
|
||||
double len;
|
||||
FLineTraceData d;
|
||||
to = level.Vec3Diff(pos,other.pos);
|
||||
len = to.length();
|
||||
to /= len;
|
||||
if ( !LineTrace(atan2(to.y,to.x),len,asin(-to.z),TRF_THRUACTORS) ) return true;
|
||||
to = level.Vec3Diff(pos,other.Vec3Offset(0,0,other.height/2));
|
||||
len = to.length();
|
||||
to /= len;
|
||||
if ( !LineTrace(atan2(to.y,to.x),len,asin(-to.z),TRF_THRUACTORS) ) return true;
|
||||
to = level.Vec3Diff(pos,other.Vec3Offset(0,0,other.height));
|
||||
len = to.length();
|
||||
to /= len;
|
||||
if ( !LineTrace(atan2(to.y,to.x),len,asin(-to.z),TRF_THRUACTORS) ) return true;
|
||||
return false;
|
||||
}
|
||||
action void A_Flame()
|
||||
{
|
||||
if ( waterlevel > 0 )
|
||||
|
|
@ -204,17 +199,15 @@ Class UFlame : Actor
|
|||
s.alpha *= 0.4;
|
||||
s.scale *= 2.5;
|
||||
}
|
||||
if ( bAMBUSH && !sting_flametspread ) return;
|
||||
if ( Random[FlameT](0,int(12*(0.4-alpha))) ) return;
|
||||
double rad = bAMBUSH?10:60;
|
||||
if ( !bAMBUSH ) rad += 90*(0.4-alpha);
|
||||
let bt = BlockThingsIterator.Create(self,rad+200);
|
||||
if ( bAMBUSH ) return;
|
||||
if ( Random[FlameT](0,int(12*(0.5-alpha))) ) return;
|
||||
double rad = 60+80*int(0.4-alpha);
|
||||
let bt = BlockThingsIterator.Create(self,rad);
|
||||
while ( bt.Next() )
|
||||
{
|
||||
let t = bt.Thing;
|
||||
if ( !t || !t.bSHOOTABLE || (t.Health <= 0) || (t == tracer) || (!bAMBUSH && (t == master) && (GetAge() < 6)) || (Distance3D(t) > rad+t.radius) || !invoker.TraceCheck(t) ) continue;
|
||||
if ( !t || !t.bSHOOTABLE || (t.Health <= 0) || (t == tracer) || ((t == master) && (GetAge() < 6)) || (Distance3D(t) > rad+t.radius) ) continue;
|
||||
int amt = max(1,int(alpha*15));
|
||||
if ( bAMBUSH && OnFire.IsOnFire(t) ) amt /= 2;
|
||||
OnFire.Apply(t,master,amt);
|
||||
}
|
||||
}
|
||||
|
|
@ -293,6 +286,12 @@ Class UFlamethrower : UnrealWeapon
|
|||
Owner.A_PlaySound("flamet/down",CHAN_6,Dampener.Active(self)?.1:1.);
|
||||
return Super.CreateTossable(amt);
|
||||
}
|
||||
override void OwnerDied()
|
||||
{
|
||||
if ( Owner.player && (Owner.player.ReadyWeapon == self) )
|
||||
Owner.A_PlaySound("flamet/down",CHAN_6,Dampener.Active(self)?.1:1.);
|
||||
Super.OwnerDied();
|
||||
}
|
||||
override void DoEffect()
|
||||
{
|
||||
Super.DoEffect();
|
||||
|
|
@ -334,6 +333,7 @@ Class UFlamethrower : UnrealWeapon
|
|||
let weap = Weapon(invoker);
|
||||
weap.DepleteAmmo(weap.bAltFire,true,1);
|
||||
invoker.count = 0;
|
||||
invoker.special1 = 0;
|
||||
A_PlaySound("flamet/fire",CHAN_WEAPON,Dampener.Active(self)?.1:1.,true);
|
||||
A_Overlay(-9999,"Dummy2");
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,14 @@ Class PeaceAmmo : Ammo
|
|||
}
|
||||
}
|
||||
|
||||
Class PeaceLight : RocketLight
|
||||
{
|
||||
Default
|
||||
{
|
||||
Args 255,128,112,32;
|
||||
}
|
||||
}
|
||||
|
||||
Class PeaceTrail : Actor
|
||||
{
|
||||
Default
|
||||
|
|
@ -27,14 +35,14 @@ Class PeaceTrail : Actor
|
|||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
A_AttachLight('RocketLight',DynamicLight.PointLight,Color(255,128,112),32,32);
|
||||
let l = Spawn("PeaceLight",pos);
|
||||
l.target = self;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !target || !target.bMISSILE )
|
||||
{
|
||||
A_RemoveLight('RocketLight');
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -169,6 +169,26 @@ Class RazorBlade : Actor
|
|||
}
|
||||
}
|
||||
|
||||
Class RazorLight : DynamicLight
|
||||
{
|
||||
Default
|
||||
{
|
||||
Args 160, 0, 240, 40;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !target )
|
||||
{
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
Args[0] = int(160*target.alpha);
|
||||
Args[2] = int(240*target.alpha);
|
||||
SetOrigin(target.pos,true);
|
||||
}
|
||||
}
|
||||
|
||||
Class RazorBladeTrail : Actor
|
||||
{
|
||||
Default
|
||||
|
|
@ -181,11 +201,16 @@ Class RazorBladeTrail : Actor
|
|||
Radius 0.1;
|
||||
Height 0;
|
||||
}
|
||||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
let l = Spawn("RazorLight",pos);
|
||||
l.target = self;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
if ( !target || target.InStateSequence(target.CurState,target.ResolveState("Death")) )
|
||||
{
|
||||
A_RemoveLight('RazorLight');
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
|
|
@ -194,7 +219,6 @@ Class RazorBladeTrail : Actor
|
|||
pitch = target.pitch;
|
||||
roll = target.roll;
|
||||
alpha = min(target.vel.length()/target.speed,1.);
|
||||
A_AttachLight('RazorLight',DynamicLight.PointLight,Color(2,0,3)*int(80*alpha),80,80);
|
||||
}
|
||||
States
|
||||
{
|
||||
|
|
|
|||
|
|
@ -224,9 +224,29 @@ Class TarydiumExplosion : Actor
|
|||
}
|
||||
}
|
||||
|
||||
Class TDebuffLight : PointLightAttenuated
|
||||
{
|
||||
TarydiumDebuff dbf;
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !dbf || !dbf.victim )
|
||||
{
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
Args[0] = min(dbf.Amount,64);
|
||||
Args[1] = min(dbf.Amount*3,192);
|
||||
Args[2] = min(dbf.Amount*4,255);
|
||||
Args[3] = int(max(dbf.victim.radius,dbf.victim.height))+60+min(dbf.amount/4,40);
|
||||
SetOrigin(dbf.Victim.Vec3Offset(0,0,dbf.Victim.Height/2),true);
|
||||
}
|
||||
}
|
||||
|
||||
Class TarydiumDebuff : Thinker
|
||||
{
|
||||
Actor victim, instigator;
|
||||
Actor victim, instigator, lite;
|
||||
int amount; // accumulated damage for the explosion
|
||||
Vector3 oldvel;
|
||||
bool wasonair, reentrant;
|
||||
|
|
@ -238,7 +258,15 @@ Class TarydiumDebuff : Thinker
|
|||
BlowUp();
|
||||
return;
|
||||
}
|
||||
victim.A_AttachLight('TDEBUFFLIGHT',DynamicLight.PointLight,Color(1,3,4)*min(amount,63),int(max(victim.radius,victim.height))+60+min(amount/4,40),0,DynamicLight.LF_ATTENUATE,(0,0,victim.height/2));
|
||||
if ( !lite )
|
||||
{
|
||||
lite = Actor.Spawn("TDebuffLight",victim.pos);
|
||||
TDebuffLight(lite).dbf = self;
|
||||
lite.Args[0] = min(Amount,64);
|
||||
lite.Args[1] = min(Amount*3,192);
|
||||
lite.Args[2] = min(Amount*4,255);
|
||||
lite.Args[3] = int(max(victim.radius,victim.height))+60+min(amount/4,40);
|
||||
}
|
||||
if ( Random[Stinger](0,amount) > 100 )
|
||||
{
|
||||
amount += 30;
|
||||
|
|
@ -256,12 +284,6 @@ Class TarydiumDebuff : Thinker
|
|||
Destroy();
|
||||
}
|
||||
|
||||
override void OnDestroy()
|
||||
{
|
||||
Super.OnDestroy();
|
||||
if ( victim ) victim.A_RemoveLight('TDEBUFFLIGHT');
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
if ( !sting_stinger )
|
||||
|
|
|
|||
|
|
@ -69,7 +69,8 @@ Class UBioGel : Actor
|
|||
Super.PostBeginPlay();
|
||||
vel.z += 3;
|
||||
deadtimer = 105;
|
||||
A_AttachLight('BioLight',DynamicLight.PointLight,"40FF80",int(8*scale.x),int(8*scale.x));
|
||||
l = Spawn("BioLight",pos);
|
||||
l.target = self;
|
||||
rollvel = FRandom[GES](10,30)*RandomPick[GES](-1,1);
|
||||
pitchvel = FRandom[GES](10,30)*RandomPick[GES](-1,1);
|
||||
yawvel = FRandom[GES](10,30)*RandomPick[GES](-1,1);
|
||||
|
|
@ -430,7 +431,6 @@ Class UBioGel : Actor
|
|||
{
|
||||
A_NoGravity();
|
||||
A_Stop();
|
||||
A_RemoveLight('BioLight');
|
||||
A_SetRenderStyle(1.,STYLE_Add);
|
||||
if ( invoker.b ) invoker.b.Destroy();
|
||||
let s = Spawn("BioXLight",pos);
|
||||
|
|
@ -552,7 +552,6 @@ Class UBioGlob : UBioGel
|
|||
if ( numsplash-- <= 0 ) return;
|
||||
Vector3 dir = (ofs+(FRandom[GES](-.8,.8),FRandom[GES](-.8,.8),FRandom[GES](-.8,.8))).unit();
|
||||
A_SetScale(scale.x-0.15);
|
||||
A_AttachLight('BioLight',DynamicLight.PointLight,"40FF80",int(8*scale.x),int(8*scale.x));
|
||||
let d = Spawn("UBioSplash",pos+ofs*4);
|
||||
d.target = target;
|
||||
d.master = self;
|
||||
|
|
|
|||
|
|
@ -68,14 +68,14 @@ Class URocketTrail : Actor
|
|||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
A_AttachLight('RocketLight',DynamicLight.PointLight,Color(255,224,128),32,32);
|
||||
let l = Spawn("RocketLight",pos);
|
||||
l.target = self;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !target || !target.bMISSILE )
|
||||
{
|
||||
A_RemoveLight('RocketLight');
|
||||
Destroy();
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue