mirror of
https://github.com/fabiangreffrath/woof.git
synced 2025-09-25 22:05:20 -04:00
implement SDL-native sound looping for moving walls (#803)
* implement SDL-native sound looping for moving walls * add an extra check that new and oldlooping sound are same * stop looping sounds during menus and pause * stop looping sounds on level exit * stop looping sounds if P_Ticker() didn't run through * do not iterate through sound channels more than necessary * correctly count looping sounds
This commit is contained in:
parent
49f2ec0ac4
commit
e1274e6481
@ -2356,6 +2356,10 @@ void G_Ticker(void)
|
|||||||
gamestate == GS_INTERMISSION ? WI_Ticker() :
|
gamestate == GS_INTERMISSION ? WI_Ticker() :
|
||||||
gamestate == GS_FINALE ? F_Ticker() :
|
gamestate == GS_FINALE ? F_Ticker() :
|
||||||
gamestate == GS_DEMOSCREEN ? D_PageTicker() : (void) 0;
|
gamestate == GS_DEMOSCREEN ? D_PageTicker() : (void) 0;
|
||||||
|
|
||||||
|
// [FG] stop looping sounds if P_Ticker() didn't run through
|
||||||
|
if (leveltime == oldleveltime)
|
||||||
|
S_StopLoopSounds();
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
|
@ -519,7 +519,7 @@ int I_GetSfxLumpNum(sfxinfo_t *sfx)
|
|||||||
// active sounds, which is maintained as a given number
|
// active sounds, which is maintained as a given number
|
||||||
// of internal channels. Returns a handle.
|
// of internal channels. Returns a handle.
|
||||||
//
|
//
|
||||||
int I_StartSound(sfxinfo_t *sound, int cnum, int vol, int sep, int pitch, int pri)
|
int I_StartSound(sfxinfo_t *sound, int cnum, int vol, int sep, int pitch, int pri, boolean loop)
|
||||||
{
|
{
|
||||||
static unsigned int id = 0;
|
static unsigned int id = 0;
|
||||||
int handle;
|
int handle;
|
||||||
@ -549,7 +549,7 @@ int I_StartSound(sfxinfo_t *sound, int cnum, int vol, int sep, int pitch, int pr
|
|||||||
if(addsfx(sound, handle, pitch))
|
if(addsfx(sound, handle, pitch))
|
||||||
{
|
{
|
||||||
channelinfo[handle].idnum = id++; // give the sound a unique id
|
channelinfo[handle].idnum = id++; // give the sound a unique id
|
||||||
Mix_PlayChannelTimed(handle, &channelinfo[handle].chunk, 0, -1);
|
Mix_PlayChannelTimed(handle, &channelinfo[handle].chunk, loop ? -1 : 0, -1);
|
||||||
updateSoundParams(handle, vol, sep, pitch);
|
updateSoundParams(handle, vol, sep, pitch);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -75,7 +75,7 @@ int I_GetSfxLumpNum(sfxinfo_t *sfxinfo);
|
|||||||
|
|
||||||
// Starts a sound in a particular sound channel.
|
// Starts a sound in a particular sound channel.
|
||||||
int I_StartSound(sfxinfo_t *sound, int cnum, int vol, int sep, int pitch,
|
int I_StartSound(sfxinfo_t *sound, int cnum, int vol, int sep, int pitch,
|
||||||
int pri);
|
int pri, boolean loop);
|
||||||
|
|
||||||
// Stops a sound channel.
|
// Stops a sound channel.
|
||||||
void I_StopSound(int handle);
|
void I_StopSound(int handle);
|
||||||
|
@ -84,7 +84,7 @@ void T_MoveCeiling (ceiling_t* ceiling)
|
|||||||
case genSilentCrusher:
|
case genSilentCrusher:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
S_StartSound((mobj_t *)&ceiling->sector->soundorg,sfx_stnmov);
|
S_LoopSound((mobj_t *)&ceiling->sector->soundorg,sfx_stnmov);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -148,7 +148,7 @@ void T_MoveCeiling (ceiling_t* ceiling)
|
|||||||
case genSilentCrusher:
|
case genSilentCrusher:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
S_StartSound((mobj_t *)&ceiling->sector->soundorg,sfx_stnmov);
|
S_LoopSound((mobj_t *)&ceiling->sector->soundorg,sfx_stnmov);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -254,7 +254,7 @@ void T_MoveFloor(floormove_t* floor)
|
|||||||
);
|
);
|
||||||
|
|
||||||
if (!(leveltime&7)) // make the floormove sound
|
if (!(leveltime&7)) // make the floormove sound
|
||||||
S_StartSound((mobj_t *)&floor->sector->soundorg, sfx_stnmov);
|
S_LoopSound((mobj_t *)&floor->sector->soundorg, sfx_stnmov);
|
||||||
|
|
||||||
if (res == pastdest) // if destination height is reached
|
if (res == pastdest) // if destination height is reached
|
||||||
{
|
{
|
||||||
@ -401,7 +401,7 @@ void T_MoveElevator(elevator_t* elevator)
|
|||||||
|
|
||||||
// make floor move sound
|
// make floor move sound
|
||||||
if (!(leveltime&7))
|
if (!(leveltime&7))
|
||||||
S_StartSound((mobj_t *)&elevator->sector->soundorg, sfx_stnmov);
|
S_LoopSound((mobj_t *)&elevator->sector->soundorg, sfx_stnmov);
|
||||||
|
|
||||||
if (res == pastdest) // if destination height acheived
|
if (res == pastdest) // if destination height acheived
|
||||||
{
|
{
|
||||||
|
@ -62,7 +62,7 @@ void T_PlatRaise(plat_t* plat)
|
|||||||
|| plat->type == raiseToNearestAndChange)
|
|| plat->type == raiseToNearestAndChange)
|
||||||
{
|
{
|
||||||
if (!(leveltime&7))
|
if (!(leveltime&7))
|
||||||
S_StartSound((mobj_t *)&plat->sector->soundorg, sfx_stnmov);
|
S_LoopSound((mobj_t *)&plat->sector->soundorg, sfx_stnmov);
|
||||||
}
|
}
|
||||||
|
|
||||||
// if encountered an obstacle, and not a crush type, reverse direction
|
// if encountered an obstacle, and not a crush type, reverse direction
|
||||||
@ -240,7 +240,7 @@ int EV_DoPlat
|
|||||||
//jff 3/14/98 clear old field as well
|
//jff 3/14/98 clear old field as well
|
||||||
sec->oldspecial = 0;
|
sec->oldspecial = 0;
|
||||||
|
|
||||||
S_StartSound((mobj_t *)&sec->soundorg,sfx_stnmov);
|
S_LoopSound((mobj_t *)&sec->soundorg,sfx_stnmov);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case raiseAndChange:
|
case raiseAndChange:
|
||||||
@ -250,7 +250,7 @@ int EV_DoPlat
|
|||||||
plat->wait = 0;
|
plat->wait = 0;
|
||||||
plat->status = up;
|
plat->status = up;
|
||||||
|
|
||||||
S_StartSound((mobj_t *)&sec->soundorg,sfx_stnmov);
|
S_LoopSound((mobj_t *)&sec->soundorg,sfx_stnmov);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case downWaitUpStay:
|
case downWaitUpStay:
|
||||||
|
@ -67,6 +67,7 @@ typedef struct channel_s
|
|||||||
int priority; // current priority value
|
int priority; // current priority value
|
||||||
int singularity; // haleyjd 09/27/06: stored singularity value
|
int singularity; // haleyjd 09/27/06: stored singularity value
|
||||||
int idnum; // haleyjd 09/30/06: unique id num for sound event
|
int idnum; // haleyjd 09/30/06: unique id num for sound event
|
||||||
|
boolean loop;
|
||||||
} channel_t;
|
} channel_t;
|
||||||
|
|
||||||
// the set of channels available
|
// the set of channels available
|
||||||
@ -74,6 +75,8 @@ static channel_t channels[MAX_CHANNELS];
|
|||||||
// [FG] removed map objects may finish their sounds
|
// [FG] removed map objects may finish their sounds
|
||||||
static degenmobj_t sobjs[MAX_CHANNELS];
|
static degenmobj_t sobjs[MAX_CHANNELS];
|
||||||
|
|
||||||
|
static int looping_sounds;
|
||||||
|
|
||||||
// These are not used, but should be (menu).
|
// These are not used, but should be (menu).
|
||||||
// Maximum volume of a sound effect.
|
// Maximum volume of a sound effect.
|
||||||
// Internal default is max out of 0-15.
|
// Internal default is max out of 0-15.
|
||||||
@ -117,12 +120,34 @@ static void S_StopChannel(int cnum)
|
|||||||
{
|
{
|
||||||
if(I_SoundIsPlaying(channels[cnum].handle))
|
if(I_SoundIsPlaying(channels[cnum].handle))
|
||||||
I_StopSound(channels[cnum].handle); // stop the sound playing
|
I_StopSound(channels[cnum].handle); // stop the sound playing
|
||||||
|
|
||||||
|
if (channels[cnum].loop)
|
||||||
|
looping_sounds--;
|
||||||
|
|
||||||
// haleyjd 09/27/06: clear the entire channel
|
// haleyjd 09/27/06: clear the entire channel
|
||||||
memset(&channels[cnum], 0, sizeof(channel_t));
|
memset(&channels[cnum], 0, sizeof(channel_t));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void S_StopLoopSounds (void)
|
||||||
|
{
|
||||||
|
int cnum;
|
||||||
|
|
||||||
|
if (looping_sounds == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!nosfxparm)
|
||||||
|
{
|
||||||
|
for (cnum = 0; cnum < numChannels; ++cnum)
|
||||||
|
{
|
||||||
|
if (channels[cnum].sfxinfo && channels[cnum].loop)
|
||||||
|
S_StopChannel(cnum);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
looping_sounds = 0;
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// S_AdjustSoundParams
|
// S_AdjustSoundParams
|
||||||
//
|
//
|
||||||
@ -211,7 +236,7 @@ static int S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source,
|
|||||||
// Note that a higher priority number means lower priority!
|
// Note that a higher priority number means lower priority!
|
||||||
//
|
//
|
||||||
static int S_getChannel(const mobj_t *origin, sfxinfo_t *sfxinfo,
|
static int S_getChannel(const mobj_t *origin, sfxinfo_t *sfxinfo,
|
||||||
int priority, int singularity)
|
int priority, int singularity, boolean loop)
|
||||||
{
|
{
|
||||||
// channel number to use
|
// channel number to use
|
||||||
int cnum;
|
int cnum;
|
||||||
@ -231,6 +256,10 @@ static int S_getChannel(const mobj_t *origin, sfxinfo_t *sfxinfo,
|
|||||||
channels[cnum].singularity == singularity &&
|
channels[cnum].singularity == singularity &&
|
||||||
channels[cnum].origin == origin)
|
channels[cnum].origin == origin)
|
||||||
{
|
{
|
||||||
|
// [FG] looping sounds don't interrupt each other
|
||||||
|
if (channels[cnum].sfxinfo == sfxinfo && channels[cnum].loop && loop)
|
||||||
|
return -1;
|
||||||
|
|
||||||
S_StopChannel(cnum);
|
S_StopChannel(cnum);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -298,7 +327,7 @@ static boolean BlockSFX(sfxinfo_t *sfx)
|
|||||||
return sfx->parallel_count > parallel_sfx_limit;
|
return sfx->parallel_count > parallel_sfx_limit;
|
||||||
}
|
}
|
||||||
|
|
||||||
void S_StartSound(const mobj_t *origin, int sfx_id)
|
static void S_StartSoundEx(const mobj_t *origin, int sfx_id, boolean loop)
|
||||||
{
|
{
|
||||||
int sep, pitch, o_priority, priority, singularity, cnum, handle;
|
int sep, pitch, o_priority, priority, singularity, cnum, handle;
|
||||||
int volumeScale = 127;
|
int volumeScale = 127;
|
||||||
@ -383,7 +412,7 @@ void S_StartSound(const mobj_t *origin, int sfx_id)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// try to find a channel
|
// try to find a channel
|
||||||
if((cnum = S_getChannel(origin, sfx, priority, singularity)) < 0)
|
if((cnum = S_getChannel(origin, sfx, priority, singularity, loop)) < 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
#ifdef RANGECHECK
|
#ifdef RANGECHECK
|
||||||
@ -398,7 +427,7 @@ void S_StartSound(const mobj_t *origin, int sfx_id)
|
|||||||
sfx = sfx->link; // sf: skip thru link(s)
|
sfx = sfx->link; // sf: skip thru link(s)
|
||||||
|
|
||||||
// Assigns the handle to one of the channels in the mix/output buffer.
|
// Assigns the handle to one of the channels in the mix/output buffer.
|
||||||
handle = I_StartSound(sfx, cnum, volume, sep, pitch, priority);
|
handle = I_StartSound(sfx, cnum, volume, sep, pitch, priority, loop);
|
||||||
|
|
||||||
// haleyjd: check to see if the sound was started
|
// haleyjd: check to see if the sound was started
|
||||||
if(handle >= 0)
|
if(handle >= 0)
|
||||||
@ -414,12 +443,25 @@ void S_StartSound(const mobj_t *origin, int sfx_id)
|
|||||||
channels[cnum].priority = priority; // scaled priority
|
channels[cnum].priority = priority; // scaled priority
|
||||||
channels[cnum].singularity = singularity;
|
channels[cnum].singularity = singularity;
|
||||||
channels[cnum].idnum = I_SoundID(handle); // unique instance id
|
channels[cnum].idnum = I_SoundID(handle); // unique instance id
|
||||||
|
channels[cnum].loop = loop;
|
||||||
|
if (loop)
|
||||||
|
looping_sounds++;
|
||||||
}
|
}
|
||||||
else // haleyjd: the sound didn't start, so clear the channel info
|
else // haleyjd: the sound didn't start, so clear the channel info
|
||||||
memset(&channels[cnum], 0, sizeof(channel_t));
|
memset(&channels[cnum], 0, sizeof(channel_t));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void S_StartSound(const mobj_t *origin, int sfx_id)
|
||||||
|
{
|
||||||
|
S_StartSoundEx(origin, sfx_id, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
void S_LoopSound(const mobj_t *origin, int sfx_id)
|
||||||
|
{
|
||||||
|
S_StartSoundEx(origin, sfx_id, true);
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// S_StopSound
|
// S_StopSound
|
||||||
//
|
//
|
||||||
@ -760,6 +802,7 @@ void S_Start(void)
|
|||||||
if(channels[cnum].sfxinfo)
|
if(channels[cnum].sfxinfo)
|
||||||
S_StopChannel(cnum);
|
S_StopChannel(cnum);
|
||||||
}
|
}
|
||||||
|
looping_sounds = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// start new music for the level
|
// start new music for the level
|
||||||
|
@ -50,9 +50,11 @@ void S_Start(void);
|
|||||||
// using <sound_id> from sounds.h
|
// using <sound_id> from sounds.h
|
||||||
//
|
//
|
||||||
void S_StartSound(const mobj_t *origin, int sound_id);
|
void S_StartSound(const mobj_t *origin, int sound_id);
|
||||||
|
void S_LoopSound(const mobj_t *origin, int sound_id);
|
||||||
|
|
||||||
// Stop sound for thing at <origin>
|
// Stop sound for thing at <origin>
|
||||||
void S_StopSound(const mobj_t *origin);
|
void S_StopSound(const mobj_t *origin);
|
||||||
|
void S_StopLoopSounds(void);
|
||||||
|
|
||||||
// [FG] play sounds in full length
|
// [FG] play sounds in full length
|
||||||
extern boolean full_sounds;
|
extern boolean full_sounds;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user