Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Heretic: Dynamic ambient sound sequences
In addition to the built-in sequences, this allows defining additional ones and also dynamically overriding the built-in sequences.
  • Loading branch information
skyjake committed Nov 10, 2020
1 parent b31dced commit 0065406
Show file tree
Hide file tree
Showing 3 changed files with 67 additions and 9 deletions.
2 changes: 2 additions & 0 deletions doomsday/apps/plugins/heretic/include/p_spec.h
Expand Up @@ -61,6 +61,8 @@ void P_SpawnAllSpecialThinkers(void);

void P_InitAmbientSound(void);

void P_DefineAmbientSfx(int sequence, const int *seq, size_t count);

/**
* Called by spawnMapThing during @ref P_SetupMap()
*/
Expand Down
2 changes: 1 addition & 1 deletion doomsday/apps/plugins/heretic/src/h_main.cpp
Expand Up @@ -26,7 +26,7 @@
#include <de/App>
#include <de/CommandLine>
#include <de/Function>
#include <de/NumberValue>>
#include <de/NumberValue>
#include "d_netsv.h"
#include "g_defs.h"
#include "gamesession.h"
Expand Down
72 changes: 64 additions & 8 deletions doomsday/apps/plugins/heretic/src/p_spec.cpp
Expand Up @@ -40,6 +40,9 @@
#include "p_user.h"
#include "player.h"

#include <map>
#include <vector>

#define MAX_AMBIENT_SFX 8 ///< Per level

enum afxcmd_t
Expand All @@ -59,6 +62,7 @@ ThinkerT<mobj_t> LavaInflictor;

static const int *LevelAmbientSfx[MAX_AMBIENT_SFX];
static const int *AmbSfxPtr;
static int AmbSfxCurrentSeq; // corresponds to AmbSfxPtr
static int AmbSfxCount;
static int AmbSfxTics;
static int AmbSfxVolume;
Expand Down Expand Up @@ -197,6 +201,10 @@ static const int *AmbientSfx[] = {
AmbSndSeq10 // FastFootsteps
};

static constexpr int NUM_BUILTIN_AMBIENT_SFX = int(sizeof(AmbientSfx) / sizeof(AmbientSfx[0]));

static std::map<int, std::vector<int>> AmbDynamicSndSeq;

dd_bool P_ActivateLine(Line *ld, mobj_t *mo, int side, int actType)
{
// Clients do not activate lines.
Expand Down Expand Up @@ -857,19 +865,67 @@ void P_PlayerInWindSector(player_t *player)

void P_InitAmbientSound()
{
AmbSfxCount = 0;
AmbSfxVolume = 0;
AmbSfxTics = 10 * TICSPERSEC;
AmbSfxPtr = AmbSndSeqInit;
AmbSfxCount = 0;
AmbSfxVolume = 0;
AmbSfxTics = 10 * TICSPERSEC;
AmbSfxPtr = AmbSndSeqInit;
AmbSfxCurrentSeq = -1;
}

static const int *ambientSeqPtr(int sequence)
{
if (AmbDynamicSndSeq.find(sequence) != AmbDynamicSndSeq.end())
{
return AmbDynamicSndSeq[sequence].data();
}
else if (sequence < NUM_BUILTIN_AMBIENT_SFX)
{
return AmbientSfx[sequence];
}
return nullptr;
}

void P_DefineAmbientSfx(int sequence, const int *seq, size_t count)
{
const int *oldSeq = ambientSeqPtr(sequence); // Becomes obsolete.

AmbDynamicSndSeq[sequence] = {seq, seq + count};

// If this is a previously existing sequence, it may need to be reset if active in the level.
if (oldSeq)
{
for (auto &ptr : LevelAmbientSfx)
{
if (ptr == oldSeq)
{
ptr = ambientSeqPtr(sequence);
}
}
}

// Restart if this was the current sequence.
if (AmbSfxCurrentSeq == sequence)
{
AmbSfxPtr = ambientSeqPtr(sequence);
}
}

void P_AddAmbientSfx(int sequence)
{
if(AmbSfxCount == MAX_AMBIENT_SFX)
if (AmbSfxCount == MAX_AMBIENT_SFX)
{
LOG_MAP_ERROR("Too many ambient sound sequences per level (max: %d)") << MAX_AMBIENT_SFX;
return;
}

if (const int *seqPtr = ambientSeqPtr(sequence))
{
LevelAmbientSfx[AmbSfxCount++] = seqPtr;
}
else
{
Con_Error("Too many ambient sound sequences");
LOG_MAP_WARNING("Ambient sound sequence %d does not exist") << sequence;
}
LevelAmbientSfx[AmbSfxCount++] = AmbientSfx[sequence];
}

void P_AmbientSound()
Expand Down Expand Up @@ -923,7 +979,7 @@ void P_AmbientSound()

case afxcmd_end:
AmbSfxTics = 6 * TICSPERSEC + P_Random();
AmbSfxPtr = LevelAmbientSfx[P_Random() % AmbSfxCount];
AmbSfxPtr = LevelAmbientSfx[AmbSfxCurrentSeq = P_Random() % AmbSfxCount];
return;

default:
Expand Down

0 comments on commit 0065406

Please sign in to comment.