diff --git a/source/common/utility/tarray.h b/source/common/utility/tarray.h index dbd63002b..1df7e5d39 100644 --- a/source/common/utility/tarray.h +++ b/source/common/utility/tarray.h @@ -316,9 +316,16 @@ public: // Returns a reference to the last element T &Last() const { + assert(Count > 0); return Array[Count-1]; } + T SafeGet (size_t index, const T& defaultval) const + { + if (index <= Count) return Array[index]; + else return defaultval; + } + // returns address of first element T *Data() const { diff --git a/source/games/duke/src/gameexec.cpp b/source/games/duke/src/gameexec.cpp index 8d4617d55..d1399d991 100644 --- a/source/games/duke/src/gameexec.cpp +++ b/source/games/duke/src/gameexec.cpp @@ -1760,23 +1760,23 @@ int ParseState::parse(void) break; case concmd_ifsoundid: insptr++; - parseifelse((short)*insptr == ambienttags[g_ac->spr.detail].lo); + parseifelse((short)*insptr == ambienttags.SafeGet(g_ac->spr.detail, {}).lo); break; case concmd_ifsounddist: insptr++; if (*insptr == 0) - parseifelse(ambienttags[g_ac->spr.detail].hi > g_x); + parseifelse(ambienttags.SafeGet(g_ac->spr.detail, {}).hi > g_x); else if (*insptr == 1) - parseifelse(ambienttags[g_ac->spr.detail].hi < g_x); + parseifelse(ambienttags.SafeGet(g_ac->spr.detail, {}).hi < g_x); break; case concmd_soundtag: insptr++; - S_PlayActorSound(ambienttags[g_ac->spr.detail].lo, g_ac); + S_PlayActorSound(ambienttags.SafeGet(g_ac->spr.detail, {}).lo, g_ac); break; case concmd_soundtagonce: insptr++; - if (!S_CheckActorSoundPlaying(g_ac, ambienttags[g_ac->spr.detail].lo)) - S_PlayActorSound(ambienttags[g_ac->spr.detail].lo, g_ac); + if (!S_CheckActorSoundPlaying(g_ac, ambienttags.SafeGet(g_ac->spr.detail, {}).lo)) + S_PlayActorSound(ambienttags.SafeGet(g_ac->spr.detail, {}).lo, g_ac); break; case concmd_soundonce: insptr++; diff --git a/source/games/duke/src/spawn_r.cpp b/source/games/duke/src/spawn_r.cpp index 00d5dda1b..51bae9900 100644 --- a/source/games/duke/src/spawn_r.cpp +++ b/source/games/duke/src/spawn_r.cpp @@ -563,12 +563,6 @@ DDukeActor* spawninit_r(DDukeActor* actj, DDukeActor* act, TArray* case SHOTGUNSHELL: initshell(actj, act, act->spr.picnum == SHELL); break; - case SOUNDFX: - { - act->spr.cstat |= CSTAT_SPRITE_INVISIBLE; - ChangeActorStat(act, STAT_ZOMBIEACTOR); - } - break; case EXPLOSION2: case EXPLOSION3: case BURNING: diff --git a/wadsrc/static/zscript/games/duke/actors/controllers.zs b/wadsrc/static/zscript/games/duke/actors/controllers.zs index eb236d5e9..8ba1ed9a0 100644 --- a/wadsrc/static/zscript/games/duke/actors/controllers.zs +++ b/wadsrc/static/zscript/games/duke/actors/controllers.zs @@ -164,16 +164,17 @@ class DukeDummyCtrl : DukeActor class DukeSoundFX : DukeActor { - default - { - statnum STAT_ZOMBIEACTOR; - } - override void StaticSetup() { self.cstat = CSTAT_SPRITE_INVISIBLE; self.detail = dlevel.addambient(self.hitag, self.lotag); self.lotag = self.hitag = 0; } + + // this actor needs to start on STAT_DEFAULT. + override void Initialize() + { + self.ChangeStat(STAT_ZOMBIEACTOR); + } }