flak_m/zscript/minigun.zsc

409 lines
9.5 KiB
Text

Class Tier6Ammo : RandomSpawner2 replaces Cell
{
Default
{
DropItem "EClip", 255, 1;
DropItem "RifleAmmo2", 255, 1;
}
}
Class Tier6Ammo2 : RandomSpawner2 replaces CellPack
{
Default
{
DropItem "MiniAmmo", 255, 6;
DropItem "RifleAmmo", 255, 6;
DropItem "WarheadAmmo", 255, 1;
}
}
Class Tier6Weapon : RandomSpawner2 replaces PlasmaRifle
{
Default
{
DropItem "Minigun", 255, 1;
DropItem "SniperRifle", 255, 1;
}
}
Class MiniAmmo : Ammo
{
Default
{
Tag "Large Bullets";
Inventory.PickupMessage "You picked up %d bullets.";
Inventory.Amount 50;
Inventory.MaxAmount 200;
Ammo.BackpackAmount 100;
Ammo.BackpackMaxAmount 400;
Ammo.DropAmount 20;
}
override String PickupMessage()
{
return String.Format(pickupmsg,Amount);
}
States
{
Spawn:
MAMO A -1;
Stop;
}
}
Class MinigunLight : EnforcerLight
{
override void PostBeginPlay()
{
Super.PostBeginPlay();
args[LIGHT_INTENSITY] = Random[Minigun](120,180);
}
}
Class MinigunTracer : Actor
{
Vector3 dest;
Default
{
RenderStyle "Add";
Radius 0.1;
Height 0;
+NOCLIP;
+NOGRAVITY;
+DONTSPLASH;
}
override void Tick()
{
Super.Tick();
if ( level.frozen || globalfreeze ) return;
Vector3 dir = level.Vec3Diff(pos,dest);
if ( dir.length() < 160 )
{
Destroy();
return;
}
dir = dir.unit();
SetOrigin(Vec3Offset(dir.x*160,dir.y*160,dir.z*160),true);
A_SetAngle(atan2(dir.y,dir.x),SPF_INTERPOLATE);
A_SetPitch(asin(-dir.z),SPF_INTERPOLATE);
A_SetRoll(roll+60,SPF_INTERPOLATE);
}
States
{
Spawn:
TRAC A -1 Bright;
Stop;
}
}
Class Minigun : UTWeapon
{
int bcnt;
action void A_FireBullet( bool alt = false )
{
Weapon weap = Weapon(invoker);
if ( !weap ) return;
if ( weap.Ammo1.Amount <= 0 ) return;
A_Overlay(-2,"MuzzleFlash",true);
A_OverlayFlags(-2,PSPF_RENDERSTYLE|PSPF_FORCESTYLE,true);
A_OverlayRenderstyle(-2,STYLE_Add);
if ( (alt && (invoker.bcnt++ < 2)) || (invoker.bcnt++ < 4) ) return;
invoker.bcnt = 0;
if ( !weap.DepleteAmmo(weap.bAltFire,true,1) ) return;
invoker.FireEffect();
UTMainHandler.DoFlash(self,Color(32,255,255,0),1);
A_AlertMonsters();
if ( alt ) A_QuakeEx(2,2,2,8,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.12);
else A_QuakeEx(1,1,1,8,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.08);
let l = Spawn("MinigunLight",pos);
l.target = self;
if ( !alt ) MinigunLight(l).cnt--;
Vector3 x, y, z, x2, y2, z2;
[x, y, z] = Matrix4.GetAxes(pitch,angle,roll);
Vector3 origin = pos+(0,0,player.viewheight)+10.0*x+y*2.0-z*2.0;
double a = FRandom[Minigun](0,360), s = FRandom[Minigun](0,alt?0.05:0.02);
[x2, y2, z2] = Matrix4.GetAxes(BulletSlope(),angle,roll);
Vector3 dir = (x2+y2*cos(a)*s+z2*sin(a)*s).unit();
FLineTraceData d;
LineTrace(atan2(dir.y,dir.x),10000,asin(-dir.z),TRF_ABSPOSITION,origin.z,origin.x,origin.y,d);
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
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 )
{
let p = Spawn("BulletImpact",d.HitLocation);
p.scale *= 0.75;
p.angle = atan2(d.HitDir.y,d.HitDir.x)+180;
p.pitch = asin(d.HitDir.z);
}
else
{
d.HitActor.TraceBleed(dmg,self);
d.HitActor.SpawnBlood(d.HitLocation,atan2(d.HitDir.y,d.HitDir.x)+180,dmg);
}
}
else if ( d.HitType != TRACE_HitNone )
{
Vector3 hitnormal = -d.HitDir;
if ( d.HitType == TRACE_HitFloor ) hitnormal = d.HitSector.floorplane.Normal;
else if ( d.HitType == TRACE_HitCeiling ) hitnormal = d.HitSector.ceilingplane.Normal;
else if ( d.HitType == TRACE_HitWall )
{
hitnormal = (-d.HitLine.delta.y,d.HitLine.delta.x,0).unit();
if ( !d.LineSide ) hitnormal *= -1;
}
let p = Spawn("BulletImpact",d.HitLocation+hitnormal*0.01);
p.scale *= 0.75;
p.angle = atan2(hitnormal.y,hitnormal.x);
p.pitch = asin(-hitnormal.z);
if ( d.HitLine ) d.HitLine.RemoteActivate(self,d.LineSide,SPAC_Impact,d.HitLocation);
}
if ( !Random[Minigun](0,1) )
{
let t = Spawn("MinigunTracer",origin+x*20.0);
t.angle = atan2(dir.y,dir.x);
t.pitch = asin(-dir.z);
MinigunTracer(t).dest = d.HitLocation;
}
for ( int i=0; i<4; i++ )
{
let s = Spawn("UTViewSmoke",origin);
UTViewSmoke(s).ofs = (10,2,-2);
s.scale *= 1.5;
s.alpha *= 0.6;
UTViewSmoke(s).vvel += (FRandom[Minigun](0.2,0.8),FRandom[Minigun](-0.3,0.3),FRandom[Minigun](-0.3,0.3));
s.target = self;
}
origin += x*8.0+y*5.0-z*5.0;
let c = Spawn("UTCasing",origin);
c.vel = x*FRandom[Junk](-2,2)+y*FRandom[Junk](3,6)+z*FRandom[Junk](3,5);
c.Scale *= 0.5;
}
action void A_MinigunRefire( statelabel flash = null, bool nounwind = false )
{
Weapon weap = Weapon(invoker);
if ( !weap || !player ) return;
if ( weap.Ammo1.Amount <= 0 )
{
if ( nounwind ) return;
A_ClearRefire();
player.setpsprite(PSP_WEAPON,weap.FindState("Unwind"));
return;
}
if ( nounwind )
{
if ( player.cmd.buttons&BT_ALTATTACK )
{
weap.bAltFire = true;
flash = "AltFire";
}
else
{
weap.bAltFire = false;
flash = "Fire";
}
}
A_Refire(flash);
}
Default
{
Tag "Minigun";
Obituary "%k's Minigun turned %o into a leaky piece of meat.";
Inventory.PickupMessage "You got the Minigun.";
Weapon.UpSound "minigun/select";
Weapon.SlotNumber 7;
Weapon.SelectionOrder 3;
Weapon.AmmoType "MiniAmmo";
Weapon.AmmoUse 1;
Weapon.AmmoType2 "MiniAmmo";
Weapon.AmmoUse2 1;
Weapon.AmmoGive 50;
Weapon.Kickback 180;
UTWeapon.DropAmmo 20;
}
States
{
Spawn:
MGNP A -1;
Stop;
MGNP B -1;
Stop;
Select:
MGNS A 1 A_Raise(int.max);
Wait;
Ready:
MGNS ABCDEFGHIJKLMNOPQRST 1 A_WeaponReady(WRF_NOFIRE);
Idle:
MGNI ABCDEFGHIJKLMNOPQRS 5
{
A_CheckReload();
A_WeaponReady();
}
Loop;
Fire:
AltFire:
MGNI A 3 { invoker.bcnt = 5; }
Hold:
MGNF A 1
{
A_PlaySound("minigun/fire",CHAN_WEAPON,1.0,true);
A_FireBullet();
}
MGNF B 0 A_MinigunRefire(1);
Goto Unwind;
MGNF B 1 A_FireBullet();
MGNF C 0 A_MinigunRefire(1);
Goto Unwind;
MGNF C 1 A_FireBullet();
MGNF D 0 A_MinigunRefire(1);
Goto Unwind;
MGNF D 1 A_FireBullet();
MGNF E 0 A_MinigunRefire(1);
Goto Unwind;
MGNF E 1 A_FireBullet();
MGNF F 0 A_MinigunRefire(1);
Goto Unwind;
MGNF F 1 A_FireBullet();
MGNF G 0 A_MinigunRefire(1);
Goto Unwind;
MGNF G 1 A_FireBullet();
MGNF H 0 A_MinigunRefire(1);
Goto Unwind;
MGNF H 1 A_FireBullet();
MGNF I 0 A_MinigunRefire(1);
Goto Unwind;
MGNF I 1 A_FireBullet();
MGNF J 0 A_MinigunRefire(1);
Goto Unwind;
MGNF J 1 A_FireBullet();
MGNF K 0 A_MinigunRefire(1);
Goto Unwind;
MGNF K 1 A_FireBullet();
MGNF L 0 A_MinigunRefire(1);
Goto Unwind;
MGNF L 1 A_FireBullet();
MGNF M 0 A_MinigunRefire(1);
Goto Unwind;
MGNF M 1 A_FireBullet();
MGNF N 0 A_MinigunRefire(1);
Goto Unwind;
MGNF N 1 A_FireBullet();
MGNF O 0 A_MinigunRefire(1);
Goto Unwind;
MGNF O 1 A_FireBullet();
MGNF P 0 A_MinigunRefire(1);
Goto Unwind;
MGNF P 1 A_FireBullet();
MGNF Q 0 A_MinigunRefire(1);
Goto Unwind;
MGNF Q 1 A_FireBullet();
MGNF R 0 A_MinigunRefire(1);
Goto Unwind;
MGNF R 1 A_FireBullet();
MGNF S 0 A_MinigunRefire(1);
Goto Unwind;
MGNF S 1 A_FireBullet();
MGNF A 0
{
if ( invoker.bAltFire ) A_MinigunRefire(1);
else A_MinigunRefire("Hold");
}
Goto Unwind;
AltHold:
MGNF A 1
{
A_PlaySound("minigun/altfire",CHAN_WEAPON,1.0,true);
A_FireBullet(true);
}
MGNF D 0 A_MinigunRefire(1);
Goto Unwind;
MGNF D 1 A_FireBullet(true);
MGNF G 0 A_MinigunRefire(1);
Goto Unwind;
MGNF G 1 A_FireBullet(true);
MGNF J 0 A_MinigunRefire(1);
Goto Unwind;
MGNF J 1 A_FireBullet(true);
MGNF M 0 A_MinigunRefire(1);
Goto Unwind;
MGNF M 1 A_FireBullet(true);
MGNF P 0 A_MinigunRefire(1);
Goto Unwind;
MGNF P 1 A_FireBullet(true);
MGNF S 0 A_MinigunRefire(1);
Goto Unwind;
MGNF S 1 A_FireBullet(true);
MGNF C 0 A_MinigunRefire(1);
Goto Unwind;
MGNF C 1 A_FireBullet(true);
MGNF F 0 A_MinigunRefire(1);
Goto Unwind;
MGNF F 1 A_FireBullet(true);
MGNF I 0 A_MinigunRefire(1);
Goto Unwind;
MGNF I 1 A_FireBullet(true);
MGNF L 0 A_MinigunRefire(1);
Goto Unwind;
MGNF L 1 A_FireBullet(true);
MGNF O 0 A_MinigunRefire(1);
Goto Unwind;
MGNF O 1 A_FireBullet(true);
MGNF R 0 A_MinigunRefire(1);
Goto Unwind;
MGNF R 1 A_FireBullet(true);
MGNF B 0 A_MinigunRefire(1);
Goto Unwind;
MGNF B 1 A_FireBullet(true);
MGNF E 0 A_MinigunRefire(1);
Goto Unwind;
MGNF E 1 A_FireBullet(true);
MGNF H 0 A_MinigunRefire(1);
Goto Unwind;
MGNF H 1 A_FireBullet(true);
MGNF K 0 A_MinigunRefire(1);
Goto Unwind;
MGNF K 1 A_FireBullet(true);
MGNF N 0 A_MinigunRefire(1);
Goto Unwind;
MGNF N 1 A_FireBullet(true);
MGNF Q 0 A_MinigunRefire(1);
Goto Unwind;
MGNF Q 1 A_FireBullet(true);
MGNF A 0 A_MinigunRefire("AltHold");
Goto Unwind;
Unwind:
MGNU A 0 A_PlaySound("minigun/unwind",CHAN_WEAPON);
MGNU ABCDEFGHIJKLMNOPQRSTUVWXYZ 1 A_MinigunRefire(null,true);
MGU2 ABCDEFGHIJKLM 1 A_MinigunRefire(null,true);
Goto Idle;
Deselect:
MGND A 1 A_StopSound(CHAN_WEAPON);
MGND BCDEFGHIJ 1;
MGND J 1 A_Lower(int.max);
Wait;
MuzzleFlash:
TNT1 A 0 A_Jump(256,1,2,3,4,5,6,7,8,9);
Stop;
MMUZ A 2 Bright;
Stop;
MMUZ B 2 Bright;
Stop;
MMUZ C 2 Bright;
Stop;
MMUZ D 2 Bright;
Stop;
MMUZ E 2 Bright;
Stop;
MMUZ F 2 Bright;
Stop;
MMUZ G 2 Bright;
Stop;
MMUZ H 2 Bright;
Stop;
MMUZ I 2 Bright;
Stop;
}
}