Added various screen shaders, plus a bunch of other changes.
Spreadgun rebalancing. Underwater sounds. Embiggener use sound. Other small things here and there.
This commit is contained in:
parent
191a9a5bb9
commit
42db2d3603
30 changed files with 754 additions and 194 deletions
|
|
@ -931,6 +931,7 @@ Class HammerspaceEmbiggener : Inventory
|
|||
{
|
||||
override Inventory CreateCopy( Actor other )
|
||||
{
|
||||
other.A_StartSound("powerup/embiggener",CHAN_ITEMEXTRA);
|
||||
// Find every unique type of ammoitem. Give it to the player if
|
||||
// he doesn't have it already, and increase its maximum capacity.
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
|
|
@ -996,6 +997,7 @@ Class HammerspaceEmbiggener : Inventory
|
|||
bool res = Super.HandlePickup(item);
|
||||
if ( item.GetClass() == GetClass() )
|
||||
{
|
||||
Owner.A_StartSound("powerup/embiggener",CHAN_ITEMEXTRA);
|
||||
// readjust ammo values to new capacity
|
||||
for ( Inventory i=Owner.Inv; i; i=i.Inv )
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,14 +1,15 @@
|
|||
// common code goes here
|
||||
enum ESWWMGZChannels
|
||||
{
|
||||
CHAN_YOUDONEFUCKEDUP = 63200,
|
||||
CHAN_DEMOVOICE = 63201,
|
||||
CHAN_FOOTSTEP = 63202,
|
||||
CHAN_WEAPONEXTRA = 63203,
|
||||
CHAN_POWERUP = 63204,
|
||||
CHAN_POWERUPEXTRA = 63205,
|
||||
CHAN_JETPACK = 63206,
|
||||
CHAN_ITEMEXTRA = 63207
|
||||
CHAN_YOUDONEFUCKEDUP = 63200, // exception handler
|
||||
CHAN_DEMOVOICE = 63201, // demolitionist voices
|
||||
CHAN_FOOTSTEP = 63202, // footstep sounds and others
|
||||
CHAN_WEAPONEXTRA = 63203, // additional weapon sounds (usually loops)
|
||||
CHAN_POWERUP = 63204, // powerup sounds
|
||||
CHAN_POWERUPEXTRA = 63205, // additional powerup sounds
|
||||
CHAN_JETPACK = 63206, // jetpack sound
|
||||
CHAN_ITEMEXTRA = 63207, // additional item sounds
|
||||
CHAN_AMBEXTRA = 63208 // player ambience when submerged
|
||||
};
|
||||
|
||||
// Misc. Utility code
|
||||
|
|
@ -367,6 +368,8 @@ Class SWWMScoreObj : Thinker
|
|||
int lifespan, initialspan;
|
||||
int starttic, seed, seed2;
|
||||
int ofs;
|
||||
SWWMScoreObj prev, next;
|
||||
bool damnum;
|
||||
|
||||
static SWWMScoreObj Spawn( int score, Vector3 pos, int tcolor = Font.CR_GOLD, String str = "", int ofs = 0 )
|
||||
{
|
||||
|
|
@ -381,9 +384,56 @@ Class SWWMScoreObj : Thinker
|
|||
o.seed = Random[ScoreBits]();
|
||||
o.seed2 = Random[ScoreBits]();
|
||||
o.ofs = ofs;
|
||||
o.damnum = (tcolor == Font.CR_RED) || (tcolor == Font.CR_GREEN);
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
if ( o.damnum )
|
||||
{
|
||||
o.next = hnd.damnums;
|
||||
if ( hnd.damnums ) hnd.damnums.prev = o;
|
||||
hnd.damnums = o;
|
||||
hnd.damnums_cnt++;
|
||||
}
|
||||
else
|
||||
{
|
||||
o.next = hnd.scorenums;
|
||||
if ( hnd.scorenums ) hnd.scorenums.prev = o;
|
||||
hnd.scorenums = o;
|
||||
hnd.scorenums_cnt++;
|
||||
}
|
||||
}
|
||||
return o;
|
||||
}
|
||||
|
||||
override void OnDestroy()
|
||||
{
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
if ( damnum )
|
||||
{
|
||||
hnd.damnums_cnt--;
|
||||
if ( !prev ) hnd.damnums = next;
|
||||
}
|
||||
else
|
||||
{
|
||||
hnd.scorenums_cnt--;
|
||||
if ( !prev ) hnd.scorenums = next;
|
||||
}
|
||||
if ( !prev )
|
||||
{
|
||||
if ( next ) next.prev = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
prev.next = next;
|
||||
if ( next ) next.prev = prev;
|
||||
}
|
||||
}
|
||||
Super.OnDestroy();
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
lifespan--;
|
||||
|
|
@ -403,6 +453,7 @@ Class SWWMInterest : Thinker
|
|||
Key trackedkey;
|
||||
Line trackedline;
|
||||
Vector3 pos;
|
||||
SWWMInterest prev, next;
|
||||
|
||||
static SWWMInterest Spawn( Vector3 pos = (0,0,0), Key thekey = null, Line theline = null )
|
||||
{
|
||||
|
|
@ -419,9 +470,37 @@ Class SWWMInterest : Thinker
|
|||
return null;
|
||||
}
|
||||
i.pos = thekey?thekey.Vec3Offset(0,0,thekey.height/2):pos;
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
i.next = hnd.intpoints;
|
||||
if ( hnd.intpoints ) hnd.intpoints.prev = i;
|
||||
hnd.intpoints = i;
|
||||
hnd.intpoints_cnt++;
|
||||
}
|
||||
return i;
|
||||
}
|
||||
|
||||
override void OnDestroy()
|
||||
{
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
hnd.intpoints_cnt--;
|
||||
if ( !prev )
|
||||
{
|
||||
hnd.intpoints = next;
|
||||
if ( next ) next.prev = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
prev.next = next;
|
||||
if ( next ) next.prev = prev;
|
||||
}
|
||||
}
|
||||
Super.OnDestroy();
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
// update
|
||||
|
|
@ -439,6 +518,7 @@ Class SWWMCombatTracker : Thinker
|
|||
DynamicValueInterpolator intp;
|
||||
Vector3 pos, prevpos;
|
||||
PlayerInfo myplayer;
|
||||
SWWMCombatTracker prev, next;
|
||||
|
||||
static SWWMCombatTracker Spawn( Actor target )
|
||||
{
|
||||
|
|
@ -461,9 +541,37 @@ Class SWWMCombatTracker : Thinker
|
|||
t.prevpos = level.Vec3Offset(target.prev,(0,0,target.default.height));
|
||||
t.intp = DynamicValueInterpolator.Create(t.lasthealth,.5,1,100);
|
||||
t.myplayer = target.player;
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
t.next = hnd.trackers;
|
||||
if ( hnd.trackers ) hnd.trackers.prev = t;
|
||||
hnd.trackers = t;
|
||||
hnd.trackers_cnt++;
|
||||
}
|
||||
return t;
|
||||
}
|
||||
|
||||
override void OnDestroy()
|
||||
{
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( hnd )
|
||||
{
|
||||
hnd.trackers_cnt--;
|
||||
if ( !prev )
|
||||
{
|
||||
hnd.trackers = next;
|
||||
if ( next ) next.prev = null;
|
||||
}
|
||||
else
|
||||
{
|
||||
prev.next = next;
|
||||
if ( next ) next.prev = prev;
|
||||
}
|
||||
}
|
||||
Super.OnDestroy();
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
// update
|
||||
|
|
@ -1217,6 +1325,10 @@ Class SWWMHandler : EventHandler
|
|||
transient int highesttic;
|
||||
transient Array<QueuedFlash> flashes;
|
||||
transient Array<LastLine> lastlines;
|
||||
SWWMCombatTracker trackers;
|
||||
SWWMScoreObj scorenums, damnums;
|
||||
SWWMInterest intpoints;
|
||||
int trackers_cnt, scorenums_cnt, damnums_cnt, intpoints_cnt;
|
||||
bool tookdamage[MAXPLAYERS];
|
||||
int spreecount[MAXPLAYERS];
|
||||
int lastkill[MAXPLAYERS];
|
||||
|
|
@ -1224,6 +1336,7 @@ Class SWWMHandler : EventHandler
|
|||
int lastitemcount[MAXPLAYERS];
|
||||
|
||||
transient CVar mutevoice;
|
||||
transient ui CVar useshaders;
|
||||
|
||||
static int AddOneliner( String type, int level, int delay = 5 )
|
||||
{
|
||||
|
|
@ -1420,10 +1533,16 @@ Class SWWMHandler : EventHandler
|
|||
else if ( e.IsSaveGame || e.IsReopen )
|
||||
{
|
||||
// clear all floating numbers
|
||||
let ti = ThinkerIterator.Create("SWWMScoreObj",Thinker.STAT_USER);
|
||||
Thinker t;
|
||||
while ( t = ti.Next() )
|
||||
t.Destroy();
|
||||
for ( SWWMScoreObj sc=scorenums; sc; sc=sc.Next )
|
||||
sc.lifespan = 0;
|
||||
for ( SWWMScoreObj sc=damnums; sc; sc=sc.Next )
|
||||
sc.lifespan = 0;
|
||||
// restore underwater sounds for players
|
||||
for ( int i=0; i<MAXPLAYERS; i++ )
|
||||
{
|
||||
if ( !playeringame[i] || (players[i].mo is 'Demolitionist') ) continue;
|
||||
Demolitionist(players[i].mo).CheckUnderwaterAmb(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1876,74 +1995,7 @@ Class SWWMHandler : EventHandler
|
|||
}
|
||||
else if ( e.Replacee is 'CWeaponPiece2' ) e.Replacement = 'CandyGun';
|
||||
else if ( e.Replacee is 'MWeaponPiece1' ) e.Replacement = 'Ynykron';
|
||||
else if ( e.Replacee is 'ArtiPoisonBag' )
|
||||
{
|
||||
switch( Random[Replacement](0,6) )
|
||||
{
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
e.Replacement = redpool[!Random[Replacement](0,2)];
|
||||
break;
|
||||
case 3:
|
||||
case 4:
|
||||
e.Replacement = greenpool[!Random[Replacement](0,2)];
|
||||
break;
|
||||
default:
|
||||
e.Replacement = 'SWWMNothing';
|
||||
}
|
||||
}
|
||||
else if ( (e.Replacee == 'Clip') || (e.Replacee == 'GoldWandAmmo') || (e.Replacee == 'GoldWandHefty') )
|
||||
{
|
||||
switch( Random[Replacement](0,6) )
|
||||
{
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
e.Replacement = redpool[Random[Replacement](0,2)];
|
||||
break;
|
||||
case 3:
|
||||
case 4:
|
||||
e.Replacement = greenpool[Random[Replacement](0,2)];
|
||||
break;
|
||||
case 5:
|
||||
e.Replacement = whitepool[Random[Replacement](0,1)];
|
||||
break;
|
||||
case 6:
|
||||
e.Replacement = purplepool[0];
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if ( (e.Replacee == 'Shell') || (e.Replacee is 'CrossbowAmmo') )
|
||||
{
|
||||
switch( Random[Replacement](0,10) )
|
||||
{
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
e.Replacement = redpool[Random[Replacement](2,3)];
|
||||
break;
|
||||
case 3:
|
||||
case 4:
|
||||
e.Replacement = greenpool[Random[Replacement](2,3)];
|
||||
break;
|
||||
case 5:
|
||||
case 6:
|
||||
e.Replacement = whitepool[Random[Replacement](1,2)];
|
||||
break;
|
||||
case 7:
|
||||
case 8:
|
||||
e.Replacement = purplepool[Random[Replacement](0,2)];
|
||||
break;
|
||||
case 9:
|
||||
e.Replacement = bluepool[Random[Replacement](0,2)];
|
||||
break;
|
||||
case 10:
|
||||
e.Replacement = blackpool[0];
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if ( (e.Replacee == 'ShellBox') || (e.Replacee is 'CrossbowHefty') )
|
||||
else if ( (e.Replacee == 'Clip') || (e.Replacee == 'GoldWandAmmo') || (e.Replacee == 'GoldWandHefty') || (e.Replacee is 'ArtiPoisonBag') )
|
||||
{
|
||||
switch( Random[Replacement](0,14) )
|
||||
{
|
||||
|
|
@ -1951,27 +2003,87 @@ Class SWWMHandler : EventHandler
|
|||
case 1:
|
||||
case 2:
|
||||
case 3:
|
||||
e.Replacement = redpool[Random[Replacement](3,5)];
|
||||
e.Replacement = redpool[Random[Replacement](0,1)];
|
||||
break;
|
||||
case 4:
|
||||
case 5:
|
||||
case 6:
|
||||
e.Replacement = greenpool[Random[Replacement](3,4)];
|
||||
e.Replacement = greenpool[Random[Replacement](0,1)];
|
||||
break;
|
||||
case 7:
|
||||
e.Replacement = purplepool[0];
|
||||
break;
|
||||
case 8:
|
||||
e.Replacement = purplepool[0];
|
||||
break;
|
||||
default:
|
||||
e.Replacement = 'SWWMNothing';
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if ( (e.Replacee == 'Shell') || (e.Replacee is 'CrossbowAmmo') )
|
||||
{
|
||||
switch( Random[Replacement](0,14) )
|
||||
{
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
case 3:
|
||||
e.Replacement = redpool[Random[Replacement](1,2)];
|
||||
break;
|
||||
case 4:
|
||||
case 5:
|
||||
case 6:
|
||||
e.Replacement = greenpool[Random[Replacement](1,2)];
|
||||
break;
|
||||
case 7:
|
||||
case 8:
|
||||
e.Replacement = whitepool[Random[Replacement](0,1)];
|
||||
break;
|
||||
case 9:
|
||||
case 10:
|
||||
case 11:
|
||||
e.Replacement = purplepool[Random[Replacement](0,1)];
|
||||
break;
|
||||
case 12:
|
||||
case 13:
|
||||
e.Replacement = bluepool[Random[Replacement](0,2)];
|
||||
break;
|
||||
case 14:
|
||||
e.Replacement = blackpool[0];
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if ( (e.Replacee == 'ShellBox') || (e.Replacee is 'CrossbowHefty') )
|
||||
{
|
||||
switch( Random[Replacement](0,15) )
|
||||
{
|
||||
case 0:
|
||||
case 1:
|
||||
case 2:
|
||||
case 3:
|
||||
e.Replacement = redpool[Random[Replacement](2,5)];
|
||||
break;
|
||||
case 4:
|
||||
case 5:
|
||||
case 6:
|
||||
e.Replacement = greenpool[Random[Replacement](2,4)];
|
||||
break;
|
||||
case 7:
|
||||
case 8:
|
||||
case 9:
|
||||
e.Replacement = whitepool[Random[Replacement](2,3)];
|
||||
e.Replacement = whitepool[Random[Replacement](1,3)];
|
||||
break;
|
||||
case 10:
|
||||
case 11:
|
||||
case 12:
|
||||
e.Replacement = purplepool[Random[Replacement](1,2)];
|
||||
break;
|
||||
case 12:
|
||||
case 13:
|
||||
case 14:
|
||||
e.Replacement = bluepool[Random[Replacement](2,3)];
|
||||
break;
|
||||
case 14:
|
||||
case 15:
|
||||
e.Replacement = blackpool[Random[Replacement](0,2)];
|
||||
break;
|
||||
}
|
||||
|
|
@ -2224,6 +2336,36 @@ Class SWWMHandler : EventHandler
|
|||
SWWMStatusBar(statusbar).viewrot = (e.viewangle,e.viewpitch,e.viewroll);
|
||||
}
|
||||
|
||||
// various shaders
|
||||
override void RenderOverlay( RenderEvent e )
|
||||
{
|
||||
PlayerInfo p = players[consoleplayer];
|
||||
if ( !useshaders ) useshaders = CVar.GetCVar('swwm_shaders',p);
|
||||
let mo = p.mo;
|
||||
if ( !mo ) return;
|
||||
bool pc = (p.camera == mo);
|
||||
let rage = RagekitPower(mo.FindInventory("RagekitPower"));
|
||||
if ( pc && rage && useshaders.GetBool() )
|
||||
{
|
||||
Shader.SetEnabled(p,"RagekitShader",true);
|
||||
Shader.SetUniform1f(p,"RagekitShader","timer",(gametic+e.FracTic)/Thinker.TICRATE);
|
||||
double xstrastr = 1.+max(0,rage.lastpulse-(gametic+e.Fractic))/35.;
|
||||
Shader.SetUniform1f(p,"RagekitShader","xtrastr",xstrastr**2.);
|
||||
}
|
||||
else Shader.SetEnabled(p,"RagekitShader",false);
|
||||
let ghost = GhostPower(mo.FindInventory("GhostPower"));
|
||||
if ( pc && ghost && useshaders.GetBool() ) Shader.SetEnabled(p,"GhostShader",true);
|
||||
else Shader.SetEnabled(p,"GhostShader",false);
|
||||
let sunny = InvinciballPower(mo.FindInventory("InvinciballPower"));
|
||||
if ( pc && sunny && useshaders.GetBool() )
|
||||
{
|
||||
Shader.SetEnabled(p,"InvinciShader",true);
|
||||
double str = max(0,sunny.lastpulse-(gametic+e.Fractic))/35.;
|
||||
Shader.SetUniform1f(p,"InvinciShader","str",str);
|
||||
}
|
||||
else Shader.SetEnabled(p,"InvinciShader",false);
|
||||
}
|
||||
|
||||
static void DoFlash( Actor camera, Color c, int duration )
|
||||
{
|
||||
// don't flash when paused
|
||||
|
|
|
|||
|
|
@ -16,9 +16,13 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
// this can be accessed from a section of the knowledge base
|
||||
Array<MsgLine> MainQueue, PickupQueue, FullHistory;
|
||||
|
||||
Array<SWWMCombatTracker> targets; // healthbars
|
||||
Array<SWWMScoreObj> scoreobjects; // floating scores
|
||||
Array<SWWMInterest> interesting; // points of interest for omnisight
|
||||
// sorted arrays of various elements
|
||||
Array<SWWMInterest> intpoints;
|
||||
Array<SWWMScoreObj> scoreobjs;
|
||||
Array<SWWMCombatTracker> trackers;
|
||||
|
||||
// the event handler, holding all sorts of stuff
|
||||
SWWMHandler hnd;
|
||||
|
||||
// client cvars
|
||||
transient CVar safezone, maxchat[2], maxpick, chatduration, msgduration, pickduration, chatcol, teamcol, obitcol, critcol, pickcol, targetter, healthnums, scorenums, scorebonus, targettag;
|
||||
|
|
@ -141,11 +145,13 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
|
||||
private bool CmpTarget( SWWMCombatTracker a, SWWMCombatTracker b )
|
||||
{
|
||||
if ( !a || !b ) return true;
|
||||
return (a.myplayer && !b.myplayer);
|
||||
}
|
||||
|
||||
private bool CmpScore( SWWMScoreObj a, SWWMScoreObj b )
|
||||
{
|
||||
if ( !a || !b ) return true;
|
||||
int srt[4] = { Font.CR_GOLD, Font.CR_FIRE, Font.CR_GREEN, Font.CR_RED };
|
||||
int s1 = 0, s2 = 0;
|
||||
for ( int i=0; i<3; i++ )
|
||||
|
|
@ -158,6 +164,7 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
|
||||
private bool CmpInterest( SWWMInterest a, SWWMInterest b )
|
||||
{
|
||||
if ( !a || !b ) return true;
|
||||
return a.type < b.type;
|
||||
}
|
||||
|
||||
|
|
@ -193,99 +200,9 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
MainQueue.Delete(i);
|
||||
i--;
|
||||
}
|
||||
// update omnisight stuff
|
||||
if ( CPlayer.mo.FindInventory("Omnisight") )
|
||||
{
|
||||
interesting.Clear();
|
||||
let ii = ThinkerIterator.Create("SWWMInterest",Thinker.STAT_USER);
|
||||
SWWMInterest poi; // :3
|
||||
while ( poi = SWWMInterest(ii.Next()) ) interesting.Push(poi);
|
||||
// sort by distance
|
||||
for ( int i=0; i<interesting.Size(); i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < interesting.Size() )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpInterest(interesting[k-1],interesting[k]) || CmpDist(interesting[k-1].pos,interesting[k].pos)) )
|
||||
{
|
||||
SWWMInterest tmp = interesting[k];
|
||||
interesting[k] = interesting[k-1];
|
||||
interesting[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
}
|
||||
// update target stuff
|
||||
targets.Clear();
|
||||
if ( targetter.GetBool() )
|
||||
{
|
||||
let ti = ThinkerIterator.Create("SWWMCombatTracker",Thinker.STAT_USER);
|
||||
SWWMCombatTracker ct;
|
||||
int extratime = 35;
|
||||
if ( CPlayer.mo.FindInventory("Omnisight") ) extratime += 105;
|
||||
while ( ct = SWWMCombatTracker(ti.Next()) )
|
||||
{
|
||||
// ignore player unless chasecamming
|
||||
if ( (ct.mytarget == players[consoleplayer].mo) && (players[consoleplayer].Camera == players[consoleplayer].mo) && !(players[consoleplayer].cheats&CF_CHASECAM) ) continue;
|
||||
if ( ct.myplayer && deathmatch ) continue; // no players in dm
|
||||
if ( level.maptime > ct.updated+extratime ) continue;
|
||||
targets.Push(ct);
|
||||
}
|
||||
// sort by distance (give priority to players)
|
||||
for ( int i=0; i<targets.Size(); i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < targets.Size() )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpTarget(targets[k-1],targets[k]) || CmpDist(targets[k-1].pos,targets[k].pos)) )
|
||||
{
|
||||
SWWMCombatTracker tmp = targets[k];
|
||||
targets[k] = targets[k-1];
|
||||
targets[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
// trim size, to unclutter
|
||||
if ( targets.Size() > 40 ) targets.Resize(40);
|
||||
}
|
||||
// update floating scores
|
||||
scoreobjects.Clear();
|
||||
let si = ThinkerIterator.Create("SWWMScoreObj",Thinker.STAT_USER);
|
||||
SWWMScoreObj so;
|
||||
while ( so = SWWMScoreObj(si.Next()) )
|
||||
{
|
||||
if ( ((so.tcolor == Font.CR_RED) || (so.tcolor == Font.CR_GREEN)) && (!healthnums.GetBool() || (level.Vec3Diff(viewpos,so.pos).length() > 2000)) ) continue;
|
||||
else if ( !scorenums.GetBool() || ((so.tcolor != Font.CR_GOLD) && !scorebonus.GetBool()) ) continue;
|
||||
scoreobjects.Push(so);
|
||||
// prevent slowdowns if hurting too many enemies at once
|
||||
if ( scoreobjects.Size() >= 100 ) break;
|
||||
}
|
||||
// sort by distance
|
||||
for ( int i=0; i<scoreobjects.Size(); i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < scoreobjects.Size() )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpScore(scoreobjects[k-1],scoreobjects[k]) || CmpDist(scoreobjects[k-1].pos,scoreobjects[k].pos)) )
|
||||
{
|
||||
SWWMScoreObj tmp = scoreobjects[k];
|
||||
scoreobjects[k] = scoreobjects[k-1];
|
||||
scoreobjects[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
// update interpolators
|
||||
HealthInter.Update(CPlayer.health);
|
||||
let hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
if ( !hnd ) hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
ScoreInter.Update(SWWMCredits.Get(CPlayer));
|
||||
let d = Demolitionist(CPlayer.mo);
|
||||
if ( d )
|
||||
|
|
@ -301,6 +218,98 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
// let weapons update their own interpolators
|
||||
if ( CPlayer.ReadyWeapon is 'SWWMWeapon' )
|
||||
SWWMWeapon(CPlayer.ReadyWeapon).HudTick();
|
||||
bool thesight = CPlayer.mo.FindInventory("Omnisight");
|
||||
if ( thesight )
|
||||
{
|
||||
// update omnisight stuff
|
||||
if ( intpoints.Size() != hnd.intpoints_cnt )
|
||||
intpoints.Resize(hnd.intpoints_cnt);
|
||||
int i = 0;
|
||||
for ( SWWMInterest poi=hnd.intpoints; poi; poi=poi.next )
|
||||
intpoints[i++] = poi;
|
||||
// sort by distance
|
||||
for ( int i=0; i<hnd.intpoints_cnt; i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < hnd.intpoints_cnt )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpInterest(intpoints[k-1],intpoints[k]) || CmpDist(intpoints[k-1].pos,intpoints[k].pos)) )
|
||||
{
|
||||
SWWMInterest tmp = intpoints[k];
|
||||
intpoints[k] = intpoints[k-1];
|
||||
intpoints[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
}
|
||||
if ( targetter.GetBool() )
|
||||
{
|
||||
// update target stuff
|
||||
if ( trackers.Size() != hnd.trackers_cnt )
|
||||
trackers.Resize(hnd.trackers_cnt);
|
||||
int i = 0, actual = 0;
|
||||
for ( SWWMCombatTracker trk=hnd.trackers; trk; trk=trk.next )
|
||||
{
|
||||
actual++;
|
||||
// ignore player unless chasecamming
|
||||
if ( (trk.mytarget == players[consoleplayer].mo) && (players[consoleplayer].Camera == players[consoleplayer].mo) && !(players[consoleplayer].cheats&CF_CHASECAM) ) continue;
|
||||
if ( trk.myplayer && deathmatch ) continue; // no players in dm
|
||||
int mtime = 35;
|
||||
if ( thesight && (trk.lasthealth > 0) ) mtime += 105;
|
||||
if ( level.maptime > trk.updated+mtime ) continue;
|
||||
trackers[i++] = trk;
|
||||
}
|
||||
// squeeze if some were discarded
|
||||
if ( i != hnd.trackers_cnt )
|
||||
trackers.Resize(i);
|
||||
// sort by distance (give priority to players)
|
||||
for ( int i=0; i<trackers.Size(); i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < trackers.Size() )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpTarget(trackers[k-1],trackers[k]) || CmpDist(trackers[k-1].pos,trackers[k].pos)) )
|
||||
{
|
||||
SWWMCombatTracker tmp = trackers[k];
|
||||
trackers[k] = trackers[k-1];
|
||||
trackers[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
}
|
||||
// update floating scores, adding the scorenums first, then the damnums
|
||||
int total_sz = hnd.scorenums_cnt;
|
||||
total_sz += min(100,hnd.damnums_cnt);
|
||||
if ( scoreobjs.Size() != total_sz )
|
||||
scoreobjs.Resize(total_sz);
|
||||
int i = 0;
|
||||
for ( SWWMScoreObj scr=hnd.scorenums; scr; scr=scr.next )
|
||||
scoreobjs[i++] = scr;
|
||||
for ( SWWMScoreObj scr=hnd.damnums; scr && (i<total_sz); scr=scr.next )
|
||||
scoreobjs[i++] = scr;
|
||||
// sort by distance
|
||||
for ( int i=0; i<total_sz; i++ )
|
||||
{
|
||||
int j = 1;
|
||||
while ( j < total_sz )
|
||||
{
|
||||
int k = j;
|
||||
while ( (k > 0) && (CmpScore(scoreobjs[k-1],scoreobjs[k]) || CmpDist(scoreobjs[k-1].pos,scoreobjs[k].pos)) )
|
||||
{
|
||||
SWWMScoreObj tmp = scoreobjs[k];
|
||||
scoreobjs[k] = scoreobjs[k-1];
|
||||
scoreobjs[k-1] = tmp;
|
||||
k--;
|
||||
}
|
||||
j++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override void Init()
|
||||
|
|
@ -339,6 +348,7 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
gl_proj = new("swwmLe__GLScreen");
|
||||
sw_proj = new("swwmLe__SWScreen");
|
||||
PrepareProjection();
|
||||
hnd = SWWMHandler(EventHandler.Find("SWWMHandler"));
|
||||
}
|
||||
|
||||
static private string FormatDist( double dist )
|
||||
|
|
@ -350,6 +360,8 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
|
||||
private void DrawTarget()
|
||||
{
|
||||
// don't draw when dead or with automap open
|
||||
if ( (CPlayer.health <= 0) || automapactive ) return;
|
||||
if ( !targettag ) targettag = CVar.GetCVar('swwm_targettags',players[consoleplayer]);
|
||||
viewport.FromHud();
|
||||
proj.CacheResolution();
|
||||
|
|
@ -362,17 +374,19 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
String tag;
|
||||
if ( thesight )
|
||||
{
|
||||
for ( int i=0; i<interesting.Size(); i++ )
|
||||
for ( int i=0; i<intpoints.Size(); i++ )
|
||||
{
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,interesting[i].pos);
|
||||
let poi = intpoints[i];
|
||||
if ( !poi ) continue;
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,poi.pos);
|
||||
proj.ProjectWorldPos(ViewPos+tdir);
|
||||
Vector2 npos = proj.ProjectToNormal();
|
||||
if ( !proj.IsInFront() ) continue;
|
||||
Vector2 vpos = viewport.SceneToWindow(npos);
|
||||
if ( interesting[i].type == INT_Key ) tag = String.Format("\cf%s\c-",StringTable.Localize(interesting[i].trackedkey.GetTag()));
|
||||
else if ( interesting[i].type == INT_Exit )
|
||||
if ( poi.type == INT_Key ) tag = String.Format("\cf%s\c-",StringTable.Localize(poi.trackedkey.GetTag()));
|
||||
else if ( poi.type == INT_Exit )
|
||||
{
|
||||
if ( interesting[i].trackedline.special == Exit_Secret )
|
||||
if ( poi.trackedline.special == Exit_Secret )
|
||||
tag = String.Format("\cx%s\c-",StringTable.Localize("$SWWM_SEXIT"));
|
||||
else tag = String.Format("\cy%s\c-",StringTable.Localize("$SWWM_NEXIT"));
|
||||
}
|
||||
|
|
@ -382,89 +396,96 @@ Class SWWMStatusBar : BaseStatusBar
|
|||
}
|
||||
}
|
||||
// targetting array
|
||||
for ( int i=0; i<targets.Size(); i++ )
|
||||
int displayed = 0;
|
||||
for ( int i=0; i<trackers.Size(); i++ )
|
||||
{
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,targets[i].prevpos*(1.-fractic)+targets[i].pos*fractic);
|
||||
let targ = trackers[i];
|
||||
if ( !targ ) continue;
|
||||
// cap to 40, so the screen isn't too cluttered
|
||||
if ( displayed++ > 40 ) break;
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,targ.prevpos*(1.-fractic)+targ.pos*fractic);
|
||||
proj.ProjectWorldPos(ViewPos+tdir);
|
||||
Vector2 npos = proj.ProjectToNormal();
|
||||
if ( !proj.IsInFront() ) continue;
|
||||
Vector2 vpos = viewport.SceneToWindow(npos);
|
||||
tag = targets[i].mytag;
|
||||
tag = targ.mytag;
|
||||
int mtime = 35;
|
||||
if ( thesight && (targets[i].lasthealth > 0) ) mtime += 105;
|
||||
double alph = clamp(((targets[i].updated+mtime)-level.maptime)/35.,0.,1.);
|
||||
if ( thesight && (targ.lasthealth > 0) ) mtime += 105;
|
||||
double alph = clamp(((targ.updated+mtime)-level.maptime)/35.,0.,1.);
|
||||
Vector2 barsiz = TexMan.GetScaledSize(EnemyBTex);
|
||||
barsiz.x *= hs.x;
|
||||
barsiz.y *= hs.y;
|
||||
Vector2 barpos = vpos-(barsiz/2.);
|
||||
barpos.y -= 16.;
|
||||
if ( targettag.GetBool() || targets[i].myplayer && (tag != "") )
|
||||
if ( targettag.GetBool() || targ.myplayer && (tag != "") )
|
||||
Screen.DrawText(mMiniwiFont.mFont,Font.CR_WHITE,(barpos.x+barsiz.x/2.-(mMiniwiFont.mFont.StringWidth(tag)*hs.x)/2.)/hs.x,(barpos.y-mMiniwiFont.mFont.GetHeight()*hs.y)/hs.y,tag,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph);
|
||||
Screen.DrawTexture(EnemyBTex,false,barpos.x/hs.x,barpos.y/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph);
|
||||
int ht = clamp(targets[i].intp.GetValue(),0,targets[i].maxhealth*10);
|
||||
int hw = int((min(ht,targets[i].maxhealth)*50.)/targets[i].maxhealth);
|
||||
if ( targets[i].mytarget && (targets[i].mytarget.bInvulnerable || (targets[i].myplayer && (targets[i].myplayer.cheats&(CF_GODMODE|CF_GODMODE2))) || targets[i].mytarget.FindInventory("InvinciballPower")) )
|
||||
int ht = clamp(targ.intp.GetValue(),0,targ.maxhealth*10);
|
||||
int hw = int((min(ht,targ.maxhealth)*50.)/targ.maxhealth);
|
||||
if ( targ.mytarget && (targ.mytarget.bInvulnerable || (targ.myplayer && (targ.myplayer.cheats&(CF_GODMODE|CF_GODMODE2))) || targ.mytarget.FindInventory("InvinciballPower")) )
|
||||
{
|
||||
Screen.DrawTexture(EnemyHTex[4],false,(barpos.x+2*hs.x)/hs.x,(barpos.y+2*hs.y)/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph,DTA_WindowRight,hw);
|
||||
continue;
|
||||
}
|
||||
Screen.DrawTexture(EnemyHTex[0],false,(barpos.x+2*hs.x)/hs.x,(barpos.y+2*hs.y)/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph,DTA_WindowRight,hw);
|
||||
if ( ht > targets[i].maxhealth )
|
||||
if ( ht > targ.maxhealth )
|
||||
{
|
||||
hw = int((min(ht-targets[i].maxhealth,targets[i].maxhealth)*50.)/targets[i].maxhealth);
|
||||
hw = int((min(ht-targ.maxhealth,targ.maxhealth)*50.)/targ.maxhealth);
|
||||
Screen.DrawTexture(EnemyHTex[1],false,(barpos.x+2*hs.x)/hs.x,(barpos.y+2*hs.y)/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph,DTA_WindowRight,hw);
|
||||
}
|
||||
if ( ht > targets[i].maxhealth*2 )
|
||||
if ( ht > targ.maxhealth*2 )
|
||||
{
|
||||
hw = int((min(ht-targets[i].maxhealth*2,targets[i].maxhealth*3)*50.)/(targets[i].maxhealth*3));
|
||||
hw = int((min(ht-targ.maxhealth*2,targ.maxhealth*3)*50.)/(targ.maxhealth*3));
|
||||
Screen.DrawTexture(EnemyHTex[2],false,(barpos.x+2*hs.x)/hs.x,(barpos.y+2*hs.y)/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph,DTA_WindowRight,hw);
|
||||
}
|
||||
if ( ht > targets[i].maxhealth*5 )
|
||||
if ( ht > targ.maxhealth*5 )
|
||||
{
|
||||
hw = int((min(ht-targets[i].maxhealth*5,targets[i].maxhealth*5)*50.)/(targets[i].maxhealth*5));
|
||||
hw = int((min(ht-targ.maxhealth*5,targ.maxhealth*5)*50.)/(targ.maxhealth*5));
|
||||
Screen.DrawTexture(EnemyHTex[3],false,(barpos.x+2*hs.x)/hs.x,(barpos.y+2*hs.y)/hs.y,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph,DTA_WindowRight,hw);
|
||||
}
|
||||
}
|
||||
// floating kill scores and others
|
||||
for ( int i=0; i<scoreobjects.Size(); i++ )
|
||||
for ( int i=0; i<scoreobjs.Size(); i++ )
|
||||
{
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,scoreobjects[i].pos);
|
||||
let snum = scoreobjs[i];
|
||||
if ( !snum ) continue;
|
||||
Vector3 tdir = Level.Vec3Diff(ViewPos,snum.pos);
|
||||
proj.ProjectWorldPos(ViewPos+tdir);
|
||||
Vector2 npos = proj.ProjectToNormal();
|
||||
if ( !proj.IsInFront() ) continue;
|
||||
Vector2 vpos = viewport.SceneToWindow(npos);
|
||||
if ( scoreobjects[i].str != "" )
|
||||
if ( snum.str != "" )
|
||||
{
|
||||
tag = StringTable.Localize(scoreobjects[i].str);
|
||||
if ( scoreobjects[i].score == int.max ) tag.AppendFormat(" %s",StringTable.Localize("$SWWM_MAX"));
|
||||
else if ( scoreobjects[i].score > 0 ) tag.AppendFormat(" x%d",scoreobjects[i].score);
|
||||
tag = StringTable.Localize(snum.str);
|
||||
if ( snum.score == int.max ) tag.AppendFormat(" %s",StringTable.Localize("$SWWM_MAX"));
|
||||
else if ( snum.score > 0 ) tag.AppendFormat(" x%d",snum.score);
|
||||
}
|
||||
else tag = String.Format("%+d",scoreobjects[i].score);
|
||||
double alph = clamp((scoreobjects[i].lifespan+fractic)/35.,0.,1.);
|
||||
else tag = String.Format("%+d",snum.score);
|
||||
double alph = clamp((snum.lifespan+fractic)/35.,0.,1.);
|
||||
Vector2 fo = (0,0);
|
||||
if ( scoreobjects[i].tcolor == Font.CR_RED )
|
||||
if ( snum.tcolor == Font.CR_RED )
|
||||
{
|
||||
// damage falls down
|
||||
int initspd = (128-scoreobjects[i].seed);
|
||||
int initspd = (128-snum.seed);
|
||||
if ( initspd >= 0 && initspd < 32 ) initspd = 32;
|
||||
if ( initspd < 0 && initspd > -32 ) initspd = -32;
|
||||
int boostup = 64+scoreobjects[i].seed2/2;
|
||||
fo.x = (.05*initspd)*((scoreobjects[i].initialspan-(scoreobjects[i].lifespan-fractic))**.8);
|
||||
fo.y = -((scoreobjects[i].initialspan-(scoreobjects[i].lifespan-fractic))**1.5)+boostup*sin((90./scoreobjects[i].initialspan)*(level.maptime+fractic-scoreobjects[i].starttic));
|
||||
int boostup = 64+snum.seed2/2;
|
||||
fo.x = (.05*initspd)*((snum.initialspan-(snum.lifespan-fractic))**.8);
|
||||
fo.y = -((snum.initialspan-(snum.lifespan-fractic))**1.5)+boostup*sin((90./snum.initialspan)*(level.maptime+fractic-snum.starttic));
|
||||
}
|
||||
else if ( scoreobjects[i].tcolor == Font.CR_GREEN )
|
||||
else if ( snum.tcolor == Font.CR_GREEN )
|
||||
{
|
||||
// health falls up (?)
|
||||
int initspd = (128-scoreobjects[i].seed);
|
||||
int initspd = (128-snum.seed);
|
||||
if ( initspd >= 0 && initspd < 32 ) initspd = 32;
|
||||
if ( initspd < 0 && initspd > -32 ) initspd = -32;
|
||||
int boostup = 16+scoreobjects[i].seed2/4;
|
||||
fo.x = (.15*initspd)*((scoreobjects[i].initialspan-(scoreobjects[i].lifespan-fractic))**.6);
|
||||
fo.y = ((scoreobjects[i].initialspan-(scoreobjects[i].lifespan-fractic))**1.2)-boostup*sin((90./scoreobjects[i].initialspan)*(level.maptime+fractic-scoreobjects[i].starttic));
|
||||
int boostup = 16+snum.seed2/4;
|
||||
fo.x = (.15*initspd)*((snum.initialspan-(snum.lifespan-fractic))**.6);
|
||||
fo.y = ((snum.initialspan-(snum.lifespan-fractic))**1.2)-boostup*sin((90./snum.initialspan)*(level.maptime+fractic-snum.starttic));
|
||||
}
|
||||
else fo.y = scoreobjects[i].initialspan-(scoreobjects[i].lifespan-fractic); // score rises linearly
|
||||
fo.y += scoreobjects[i].ofs*mMiniwiFont.mFont.GetHeight();
|
||||
Screen.DrawText(mMiniwiFont.mFont,scoreobjects[i].tcolor,(vpos.x-hs.x*(fo.x+mMiniwiFont.mFont.StringWidth(tag)/2.))/hs.x,(vpos.y-hs.y*(fo.y+(mMiniwiFont.mFont.GetHeight()/2.)))/hs.y,tag,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph);
|
||||
else fo.y = snum.initialspan-(snum.lifespan-fractic); // score rises linearly
|
||||
fo.y += snum.ofs*mMiniwiFont.mFont.GetHeight();
|
||||
Screen.DrawText(mMiniwiFont.mFont,snum.tcolor,(vpos.x-hs.x*(fo.x+mMiniwiFont.mFont.StringWidth(tag)/2.))/hs.x,(vpos.y-hs.y*(fo.y+(mMiniwiFont.mFont.GetHeight()/2.)))/hs.y,tag,DTA_VirtualWidthF,ss.x,DTA_VirtualHeightF,ss.y,DTA_KeepRatio,true,DTA_Alpha,alph);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -306,7 +306,7 @@ Class SWWMKnowledgeBaseMenu : GenericMenu
|
|||
}
|
||||
return true;
|
||||
case MKEY_ENTER:
|
||||
if ( (curtab == TAB_INVENTORY) && (invlist.Size() > 0) )
|
||||
if ( (curtab == TAB_INVENTORY) && (invlist.Size() > 0) && (sel0 < invlist.Size()) )
|
||||
{
|
||||
// can't use this
|
||||
if ( invlist[sel0] is 'Ammo' ) return true;
|
||||
|
|
@ -317,7 +317,7 @@ Class SWWMKnowledgeBaseMenu : GenericMenu
|
|||
checkuse = gametic+1;
|
||||
EventHandler.SendNetworkEvent(String.Format("swwmuseitem.%s",invlist[sel0].GetClassName()),consoleplayer);
|
||||
}
|
||||
else if ( (curtab == TAB_STORE) && (storelist.Size() > 0) )
|
||||
else if ( (curtab == TAB_STORE) && (storelist.Size() > 0) && (sel0 < storelist.Size()) )
|
||||
{
|
||||
int moni = SWWMCredits.Get(players[consoleplayer]);
|
||||
let itm = GetDefaultByType(storelist[sel0]);
|
||||
|
|
@ -359,7 +359,7 @@ Class SWWMKnowledgeBaseMenu : GenericMenu
|
|||
MenuSound("menu/democlose");
|
||||
sub = false;
|
||||
}
|
||||
else if ( lorelist.Size() > 0 )
|
||||
else if ( (lorelist.Size() > 0) && (sel0 < lorelist.Size()) )
|
||||
{
|
||||
// mark as read
|
||||
if ( !lorelist[sel0].read )
|
||||
|
|
@ -440,7 +440,7 @@ Class SWWMKnowledgeBaseMenu : GenericMenu
|
|||
// alphabetically sorted inventory
|
||||
for ( Inventory inv=players[consoleplayer].mo.Inv; inv; inv=inv.Inv )
|
||||
{
|
||||
if ( (inv.Amount <= 0) || !inv.SpawnState.ValidateSpriteFrame() || (inv is 'Key') || (inv is 'BasicArmor') || (inv is 'HexenArmor') || (inv is 'Powerup') || (inv is 'SWWMArmor') ) continue;
|
||||
if ( (inv.Amount <= 0) || !inv.SpawnState.ValidateSpriteFrame() || (inv is 'Key') || (inv is 'BasicArmor') || (inv is 'HexenArmor') || (inv is 'Powerup') || (inv is 'SWWMArmor') || (!(inv is 'Ammo') && !(inv is 'Weapon') && !inv.bINVBAR) ) continue;
|
||||
String tag = inv.GetTag();
|
||||
bool greater = false;
|
||||
for ( int i=0; i<invlist.Size(); i++ )
|
||||
|
|
|
|||
|
|
@ -19,12 +19,21 @@ Class Demolitionist : PlayerPawn
|
|||
|
||||
SWWMStats mystats;
|
||||
int cairtime;
|
||||
Vector3 oldpos;
|
||||
|
||||
int lastmpain;
|
||||
|
||||
double guideangle, guidepitch, guideroll;
|
||||
|
||||
enum EUnderType
|
||||
{
|
||||
UNDER_NONE,
|
||||
UNDER_WATER,
|
||||
UNDER_SLIME,
|
||||
UNDER_LAVA
|
||||
};
|
||||
|
||||
int lastunder;
|
||||
|
||||
Default
|
||||
{
|
||||
Speed 1;
|
||||
|
|
@ -246,7 +255,6 @@ Class Demolitionist : PlayerPawn
|
|||
{
|
||||
Super.PostBeginPlay();
|
||||
mystats = SWWMStats.Find(player);
|
||||
oldpos = pos;
|
||||
lastground = true;
|
||||
}
|
||||
void A_Dash()
|
||||
|
|
@ -290,12 +298,87 @@ Class Demolitionist : PlayerPawn
|
|||
}
|
||||
fuelcooldown = max(20,fuelcooldown);
|
||||
}
|
||||
void CheckUnderwaterAmb( bool restore = false )
|
||||
{
|
||||
Vector3 headpos = Vec3Offset(0,0,player.viewheight);
|
||||
Vector3 centerpos = Vec3Offset(0,0,height/2);
|
||||
Sector headregion = null;
|
||||
if ( CurSector.moreflags&Sector.SECMF_UNDERWATER ) // check underwater sector
|
||||
headregion = CurSector;
|
||||
else if ( CurSector.heightsec ) // check height transfer
|
||||
{
|
||||
let hsec = CurSector.heightsec;
|
||||
double fh = hsec.floorplane.ZAtPoint(pos.xy);
|
||||
if ( pos.z < fh )
|
||||
{
|
||||
if ( headpos.z <= fh )
|
||||
headregion = hsec;
|
||||
}
|
||||
else if ( !(hsec.moreflags&Sector.SECMF_FAKEFLOORONLY) && (headpos.z > hsec.ceilingplane.ZAtPoint(pos.xy)) )
|
||||
headregion = hsec;
|
||||
}
|
||||
else // check 3D floors
|
||||
{
|
||||
for ( int i=0; i<CurSector.Get3DFloorCount(); i++ )
|
||||
{
|
||||
let ff = CurSector.Get3DFloor(i);
|
||||
if ( !(ff.flags&F3DFloor.FF_EXISTS) || (ff.flags&F3DFloor.FF_SOLID) || (!(ff.flags&F3DFloor.FF_SWIMMABLE) && (ff.alpha == 0)) ) continue;
|
||||
double ff_bottom = ff.bottom.ZAtPoint(pos.xy);
|
||||
double ff_top = ff.top.ZAtPoint(pos.xy);
|
||||
if ( (ff_top <= pos.z) || (ff_bottom > centerpos.z) ) continue;
|
||||
if ( headpos.z <= ff_top )
|
||||
{
|
||||
headregion = ff.model;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
int curunder = UNDER_NONE;
|
||||
if ( headregion )
|
||||
{
|
||||
switch ( headregion.damagetype )
|
||||
{
|
||||
case 'Fire':
|
||||
case 'Lava':
|
||||
curunder = UNDER_LAVA;
|
||||
break;
|
||||
case 'Slime':
|
||||
case 'Poison':
|
||||
case 'PoisonCloud':
|
||||
curunder = UNDER_SLIME;
|
||||
break;
|
||||
case 'Ice':
|
||||
case 'Drowning':
|
||||
default:
|
||||
curunder = UNDER_WATER;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( (curunder != lastunder) || restore )
|
||||
{
|
||||
static const string undersnd[] = {"","misc/underwater","misc/underslime","misc/underlava"};
|
||||
static const string entersnd[] = {"","misc/waterenter","misc/slimeenter","misc/lavaenter"};
|
||||
static const string exitsnd[] = {"","misc/waterexit","misc/slimeexit","misc/lavaexit"};
|
||||
A_StopSound(CHAN_AMBEXTRA);
|
||||
if ( curunder > UNDER_NONE )
|
||||
{
|
||||
A_StartSound(undersnd[curunder],CHAN_AMBEXTRA,CHANF_LOOPING|CHANF_UI);
|
||||
if ( !restore && (players[consoleplayer].Camera == self) )
|
||||
A_StartSound(entersnd[curunder],CHAN_FOOTSTEP,CHANF_OVERLAP|CHANF_UI);
|
||||
}
|
||||
if ( !restore && (lastunder > UNDER_NONE) && (players[consoleplayer].Camera == self) )
|
||||
A_StartSound(exitsnd[lastunder],CHAN_FOOTSTEP,CHANF_OVERLAP|CHANF_UI);
|
||||
}
|
||||
if ( curunder > UNDER_NONE )
|
||||
A_SoundVolume(CHAN_AMBEXTRA,(players[consoleplayer].Camera==self)?1.:0.);
|
||||
lastunder = curunder;
|
||||
}
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !player ) return;
|
||||
double traveldist = level.Vec3Diff(oldpos,pos).length();
|
||||
if ( waterlevel < 3 )
|
||||
double traveldist = level.Vec3Diff(prev,pos).length();
|
||||
if ( waterlevel < 2 )
|
||||
{
|
||||
if ( !player.onground || bNoGravity )
|
||||
{
|
||||
|
|
@ -309,8 +392,8 @@ Class Demolitionist : PlayerPawn
|
|||
mystats.grounddist += traveldist;
|
||||
}
|
||||
}
|
||||
if ( traveldist > mystats.topspeed ) mystats.topspeed = traveldist;
|
||||
oldpos = pos;
|
||||
CheckUnderwaterAmb();
|
||||
if ( vel.length() > mystats.topspeed ) mystats.topspeed = vel.length();
|
||||
if ( !myvoice ) myvoice = CVar.GetCVar('swwm_voicetype',player);
|
||||
if ( !mute ) mute = CVar.GetCVar('swwm_mutevoice',player);
|
||||
if ( player.onground && !bNoGravity && !lastground && (waterlevel < 2) && (health > 0) )
|
||||
|
|
@ -334,7 +417,8 @@ Class Demolitionist : PlayerPawn
|
|||
if ( lastvelz < -10 ) A_StartSound("demolitionist/runstop",CHAN_FOOTSTEP,CHANF_OVERLAP);
|
||||
if ( (player == players[consoleplayer]) && (lastvelz < -gruntspeed) && (mute.GetInt() < 4) )
|
||||
A_StartSound(String.Format("voice/%s/grunt",myvoice.GetString()),CHAN_DEMOVOICE,CHANF_OVERLAP);
|
||||
A_Footstep(0,true,clamp(-lastvelz*0.05,0.01,1.0));
|
||||
if ( lastvelz < -1 )
|
||||
A_Footstep(0,true,clamp(-lastvelz*0.05,0.0,1.0));
|
||||
}
|
||||
lastground = player.onground;
|
||||
lastvelz = prevvelz;
|
||||
|
|
@ -381,7 +465,7 @@ Class Demolitionist : PlayerPawn
|
|||
double moveang = atan2(dir.y,dir.x);
|
||||
Vector3 sc = level.SphericalCoords(pos,a.pos,(moveang,0));
|
||||
if ( abs(sc.x) > 60 ) continue;
|
||||
// bosses and large monsters will stop the player
|
||||
// large monsters will stop the player
|
||||
A_QuakeEx(1,1,1,3,0,128,"",QF_RELATIVE|QF_SCALEDOWN);
|
||||
a.A_StartSound("demolitionist/bump",CHAN_FOOTSTEP,CHANF_OVERLAP);
|
||||
if ( a.bDONTTHRUST || (a.Mass >= Mass*5) )
|
||||
|
|
@ -715,6 +799,11 @@ Class Demolitionist : PlayerPawn
|
|||
last_jump_held = level.maptime+1;
|
||||
}
|
||||
}
|
||||
override void DeathThink()
|
||||
{
|
||||
// TODO reboot mechanic, death camera that doesn't move body
|
||||
Super.DeathThink();
|
||||
}
|
||||
override void PlayIdle()
|
||||
{
|
||||
if ( !player )
|
||||
|
|
|
|||
|
|
@ -136,6 +136,7 @@ Class GhostPower : PowerInvisibility
|
|||
{
|
||||
Super.InitEffect();
|
||||
if ( !Owner ) return;
|
||||
SWWMHandler.DoFlash(Owner,Color(96,224,192,255),20);
|
||||
DoEffect();
|
||||
}
|
||||
override void EndEffect()
|
||||
|
|
@ -144,6 +145,7 @@ Class GhostPower : PowerInvisibility
|
|||
if ( !Owner ) return;
|
||||
Owner.bNOTARGET = false;
|
||||
Owner.A_StartSound("powerup/ghostend",CHAN_ITEMEXTRA);
|
||||
SWWMHandler.DoFlash(Owner,Color(96,224,192,255),20);
|
||||
if ( (EffectTics <= 0) && Owner && Owner.CheckLocalView() ) Console.Printf(StringTable.Localize("$D_GHOSTARTI"));
|
||||
}
|
||||
|
||||
|
|
@ -334,6 +336,14 @@ Class GravityPower : Powerup
|
|||
|
||||
}
|
||||
|
||||
Class GravityX : GhostArtifactX
|
||||
{
|
||||
Default
|
||||
{
|
||||
RenderStyle "Normal";
|
||||
}
|
||||
}
|
||||
|
||||
Class GravitySuppressor : Inventory
|
||||
{
|
||||
Mixin SWWMAutoUseFix;
|
||||
|
|
@ -347,6 +357,15 @@ Class GravitySuppressor : Inventory
|
|||
else Owner.GiveInventory("GravityPower",1);
|
||||
return true;
|
||||
}
|
||||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
tracer = Spawn("GravityX",pos);
|
||||
tracer.angle = angle;
|
||||
tracer.target = self;
|
||||
tracer.FloatBobPhase = FloatBobPhase;
|
||||
}
|
||||
|
||||
Default
|
||||
{
|
||||
Tag "$T_GRAVITYS";
|
||||
|
|
@ -439,6 +458,7 @@ Class InvinciballPower : Powerup
|
|||
{
|
||||
Actor l, snd;
|
||||
int lasteffect;
|
||||
transient int lastpulse;
|
||||
|
||||
Default
|
||||
{
|
||||
|
|
@ -455,6 +475,8 @@ Class InvinciballPower : Powerup
|
|||
l = Spawn("InvinciballLight",Owner.pos);
|
||||
l.target = Owner;
|
||||
l.master = self;
|
||||
lastpulse = max(lastpulse,gametic+35);
|
||||
SWWMHandler.DoFlash(Owner,Color(96,255,64,0),20);
|
||||
}
|
||||
|
||||
override void DoEffect()
|
||||
|
|
@ -471,6 +493,7 @@ Class InvinciballPower : Powerup
|
|||
Super.EndEffect();
|
||||
if ( !Owner ) return;
|
||||
Owner.A_StartSound("powerup/invinciballend",CHAN_ITEMEXTRA);
|
||||
SWWMHandler.DoFlash(Owner,Color(96,255,64,0),20);
|
||||
if ( (EffectTics <= 0) && Owner && Owner.CheckLocalView() ) Console.Printf(StringTable.Localize("$D_INVINCIBALL"));
|
||||
}
|
||||
|
||||
|
|
@ -489,11 +512,20 @@ Class InvinciballPower : Powerup
|
|||
SWWMHandler.DoFlash(Owner,Color(64,255,64,0),15);
|
||||
Owner.A_StartSound("powerup/invinciballhit",CHAN_POWERUP);
|
||||
lasteffect = level.maptime;
|
||||
lastpulse = max(lastpulse,gametic+20);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Class InvinciballX : GhostArtifactX
|
||||
{
|
||||
Default
|
||||
{
|
||||
RenderStyle "Normal";
|
||||
}
|
||||
}
|
||||
|
||||
Class FuckingInvinciball : Inventory
|
||||
{
|
||||
Mixin SWWMAutoUseFix;
|
||||
|
|
@ -510,10 +542,24 @@ Class FuckingInvinciball : Inventory
|
|||
Owner.A_StartSound(UseSound,CHAN_ITEMEXTRA);
|
||||
Owner.A_StartSound("misc/sundowner",CHAN_POWERUPEXTRA);
|
||||
let i = InvinciballPower(Owner.FindInventory("InvinciballPower"));
|
||||
if ( i ) i.EffectTics = i.default.EffectTics;
|
||||
if ( i )
|
||||
{
|
||||
i.EffectTics = i.default.EffectTics;
|
||||
i.lastpulse = max(i.lastpulse,gametic+35);
|
||||
SWWMHandler.DoFlash(Owner,Color(96,255,64,0),20);
|
||||
}
|
||||
else Owner.GiveInventory("InvinciballPower",1);
|
||||
return true;
|
||||
}
|
||||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
tracer = Spawn("InvinciballX",pos);
|
||||
tracer.angle = angle;
|
||||
tracer.target = self;
|
||||
tracer.FloatBobPhase = FloatBobPhase;
|
||||
}
|
||||
|
||||
Default
|
||||
{
|
||||
Tag "$T_INVINCIBALL";
|
||||
|
|
@ -607,6 +653,7 @@ Class RagekitPower : Powerup
|
|||
{
|
||||
Actor l, snd;
|
||||
int lasteffect, lastrage;
|
||||
transient int lastpulse;
|
||||
|
||||
override double GetSpeedFactor()
|
||||
{
|
||||
|
|
@ -629,6 +676,7 @@ Class RagekitPower : Powerup
|
|||
SWWMHandler.DoFlash(Owner,Color(64,255,0,0),30);
|
||||
Owner.A_QuakeEx(8,8,8,20,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:1.);
|
||||
lasteffect = int.min;
|
||||
lastpulse = max(lastpulse,gametic+35);
|
||||
l = Spawn("RagekitLight",Owner.pos);
|
||||
l.target = Owner;
|
||||
l.master = self;
|
||||
|
|
@ -647,6 +695,7 @@ Class RagekitPower : Powerup
|
|||
if ( (Owner.player == players[consoleplayer]) && (gametic > lastrage) && (CVar.GetCVar('swwm_mutevoice',players[consoleplayer]).GetInt() < 2) )
|
||||
lastrage = SWWMHandler.AddOneliner("ragekit",2,5);
|
||||
Owner.A_QuakeEx(2,2,2,Random[Rage](1,2),0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:.5);
|
||||
lastpulse = max(lastpulse,gametic+10);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -655,6 +704,8 @@ Class RagekitPower : Powerup
|
|||
Super.EndEffect();
|
||||
if ( !Owner ) return;
|
||||
Owner.A_StartSound("powerup/ragekitend",CHAN_ITEMEXTRA);
|
||||
SWWMHandler.DoFlash(Owner,Color(128,255,0,0),30);
|
||||
Owner.A_QuakeEx(4,4,4,20,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:1.);
|
||||
if ( (EffectTics <= 0) && Owner && Owner.CheckLocalView() ) Console.Printf(StringTable.Localize("$D_RAGEKIT"));
|
||||
}
|
||||
|
||||
|
|
@ -671,6 +722,7 @@ Class RagekitPower : Powerup
|
|||
lastrage = SWWMHandler.AddOneliner("ragekit",2,5);
|
||||
Owner.A_StartSound("powerup/ragekithit",CHAN_POWERUP);
|
||||
lasteffect = level.maptime;
|
||||
lastpulse = max(lastpulse,gametic+35);
|
||||
}
|
||||
}
|
||||
else if ( passive )
|
||||
|
|
@ -678,6 +730,14 @@ Class RagekitPower : Powerup
|
|||
}
|
||||
}
|
||||
|
||||
Class RagekitX : GhostArtifactX
|
||||
{
|
||||
Default
|
||||
{
|
||||
RenderStyle "Normal";
|
||||
}
|
||||
}
|
||||
|
||||
Class Ragekit : Inventory
|
||||
{
|
||||
Mixin SWWMAutoUseFix;
|
||||
|
|
@ -687,10 +747,25 @@ Class Ragekit : Inventory
|
|||
if ( pickup && !deathmatch ) return false;
|
||||
Owner.A_StartSound(UseSound,CHAN_ITEMEXTRA);
|
||||
let r = RagekitPower(Owner.FindInventory("RagekitPower"));
|
||||
if ( r ) r.EffectTics = r.default.EffectTics;
|
||||
if ( r )
|
||||
{
|
||||
r.EffectTics = r.default.EffectTics;
|
||||
SWWMHandler.DoFlash(Owner,Color(64,255,0,0),30);
|
||||
Owner.A_QuakeEx(8,8,8,20,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:1.);
|
||||
r.lastpulse = max(r.lastpulse,gametic+35);
|
||||
}
|
||||
else Owner.GiveInventory("RagekitPower",1);
|
||||
return true;
|
||||
}
|
||||
override void PostBeginPlay()
|
||||
{
|
||||
Super.PostBeginPlay();
|
||||
tracer = Spawn("RagekitX",pos);
|
||||
tracer.angle = angle;
|
||||
tracer.target = self;
|
||||
tracer.FloatBobPhase = FloatBobPhase;
|
||||
}
|
||||
|
||||
Default
|
||||
{
|
||||
Tag "$T_RAGEKIT";
|
||||
|
|
|
|||
|
|
@ -525,7 +525,7 @@ Class SaltLight : PaletteLight
|
|||
{
|
||||
Tag "SaltTail";
|
||||
ReactionTime 30;
|
||||
Args 0,0,0,80;
|
||||
Args 0,0,0,120;
|
||||
}
|
||||
}
|
||||
Class SaltLight2 : PaletteLight
|
||||
|
|
@ -534,7 +534,7 @@ Class SaltLight2 : PaletteLight
|
|||
{
|
||||
Tag "SaltExpl";
|
||||
ReactionTime 30;
|
||||
Args 0,0,0,80;
|
||||
Args 0,0,0,70;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -543,7 +543,7 @@ Class SaltImpact : Actor
|
|||
Default
|
||||
{
|
||||
Obituary "$O_SPREADGUN_BLUE";
|
||||
DamageType "Salt";
|
||||
DamageType "Electricity";
|
||||
RenderStyle "Add";
|
||||
Radius 0.1;
|
||||
Height 0;
|
||||
|
|
@ -614,7 +614,7 @@ Class SaltBeam : Actor
|
|||
Default
|
||||
{
|
||||
Obituary "$O_SPREADGUN_BLUE";
|
||||
DamageType "Salt";
|
||||
DamageType "Electricity";
|
||||
RenderStyle "Add";
|
||||
Radius 0.1;
|
||||
Height 0;
|
||||
|
|
@ -645,7 +645,7 @@ Class SaltBeam : Actor
|
|||
let b = Actor.Spawn("InvisibleSplasher",t.WaterHitList[i].hitpos);
|
||||
b.A_CheckTerrain();
|
||||
}
|
||||
for ( int i=8; i<t.Results.Distance; i+=16 )
|
||||
for ( int i=16; i<t.Results.Distance; i+=32 )
|
||||
{
|
||||
if ( !Random[Spreadgun](0,Stamina) ) continue;
|
||||
let b = Actor.Spawn("SWWMSmoke",level.Vec3Offset(pos,x*i));
|
||||
|
|
@ -688,8 +688,16 @@ Class SaltBeam : Actor
|
|||
}
|
||||
return;
|
||||
}
|
||||
else if ( (args[0] > 20) && !Random[Spreadgun](0,800/args[0]) )
|
||||
{
|
||||
let i = Spawn("SaltImpact",level.Vec3Offset(pos,x*32));
|
||||
i.angle = atan2(x.y,x.x);
|
||||
i.pitch = asin(-x.z);
|
||||
i.target = target;
|
||||
return;
|
||||
}
|
||||
// next beam
|
||||
if ( !(special2%2) && !Random[Spreadgun](0,2) )
|
||||
if ( !(special2%2) && !Random[Spreadgun](0,4) )
|
||||
Spawn("SaltLight",level.Vec3Offset(pos,x*16));
|
||||
let next = Spawn("SaltBeam",level.Vec3Offset(pos,x*32));
|
||||
double a = FRandom[Spreadgun](0,360), s = FRandom[Spreadgun](0,.06);
|
||||
|
|
@ -698,6 +706,7 @@ Class SaltBeam : Actor
|
|||
next.pitch = asin(-dir.z);
|
||||
next.target = target;
|
||||
next.special2 = (special2+1)%10;
|
||||
next.args[0] = args[0]+1;
|
||||
next.SetStateLabel("TrailSpawn");
|
||||
}
|
||||
|
||||
|
|
@ -714,10 +723,10 @@ Class SaltBeam : Actor
|
|||
A_FadeOut(.04);
|
||||
if ( Random[Spreadgun](-2,GetAge()/10) == 0 )
|
||||
{
|
||||
SWWMHandler.DoBlast(self,48,5000,target);
|
||||
A_Explode(5,48,0);
|
||||
SWWMHandler.DoBlast(self,64,5000,target);
|
||||
A_Explode(5,64,0);
|
||||
}
|
||||
if ( (special2 || GetAge()) && !special1 ) SpreadOut();
|
||||
if ( ((special2%5) || GetAge()) && !special1 ) SpreadOut();
|
||||
}
|
||||
|
||||
States
|
||||
|
|
@ -1311,8 +1320,7 @@ Class Spreadgun : SWWMWeapon
|
|||
{
|
||||
Super.ModifyDropAmount(dropamount);
|
||||
// toss some ammo while we're at it
|
||||
let am = (Class<Ammo>)(GetReplacement("Shell"));
|
||||
A_DropItem(am,Random[Spreadgun](3,5));
|
||||
A_DropItem(Random[Spreadgun](0,2)?"RedShell":"GreenShell",Random[Spreadgun](1,3));
|
||||
}
|
||||
|
||||
Default
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue