Fixes some sound <-> mixsdl interactions, in particular, same buffer getting queued on 2 sources (bug #146)
git-svn-id: svn://svn.code.sf.net/p/sc2/code/trunk@730 8092fc87-c524-0410-9efc-e669fe64eaf9
This commit is contained in:
@@ -490,10 +490,15 @@ mixSDL_Sourcei (mixSDL_Object srcobj, mixSDL_SourceProp pname,
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case MIX_SOURCE_STATE:
|
case MIX_SOURCE_STATE:
|
||||||
#ifdef DEBUG
|
if (value == MIX_INITIAL)
|
||||||
fprintf (stderr, "mixSDL_Sourcei() called "
|
{
|
||||||
"with MIX_SOURCE_STATE. call ignored\n");
|
mixSDL_SourceRewind_internal (src);
|
||||||
#endif
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
fprintf (stderr, "mixSDL_Sourcei(MIX_SOURCE_STATE): "
|
||||||
|
"unsupported state, call ignored\n");
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
mixSDL_SetError (MIX_INVALID_ENUM);
|
mixSDL_SetError (MIX_INVALID_ENUM);
|
||||||
@@ -700,26 +705,7 @@ mixSDL_SourceRewind (mixSDL_Object srcobj)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
/* should change the processed buffers to queued */
|
mixSDL_SourceRewind_internal (src);
|
||||||
mixSDL_Buffer *buf;
|
|
||||||
|
|
||||||
if (src->state >= MIX_PLAYING)
|
|
||||||
mixSDL_SourceDeactivate (src);
|
|
||||||
|
|
||||||
mixSDL_LockMutex (buf_mutex);
|
|
||||||
|
|
||||||
for (buf = src->firstqueued;
|
|
||||||
buf && buf->state != MIX_BUF_QUEUED;
|
|
||||||
buf = buf->next)
|
|
||||||
{
|
|
||||||
buf->state = MIX_BUF_QUEUED;
|
|
||||||
}
|
|
||||||
|
|
||||||
mixSDL_UnlockMutex (buf_mutex);
|
|
||||||
|
|
||||||
src->curbufofs = 0;
|
|
||||||
src->cprocessed = 0;
|
|
||||||
src->state = MIX_INITIAL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
mixSDL_UnlockMutex (src_mutex);
|
mixSDL_UnlockMutex (src_mutex);
|
||||||
@@ -1104,6 +1090,32 @@ mixSDL_SourceStop_internal (mixSDL_Source *src)
|
|||||||
mixSDL_UnlockMutex (buf_mutex);
|
mixSDL_UnlockMutex (buf_mutex);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
mixSDL_SourceRewind_internal (mixSDL_Source *src)
|
||||||
|
{
|
||||||
|
/* should change the processed buffers to queued */
|
||||||
|
mixSDL_Buffer *buf;
|
||||||
|
|
||||||
|
if (src->state >= MIX_PLAYING)
|
||||||
|
mixSDL_SourceDeactivate (src);
|
||||||
|
|
||||||
|
mixSDL_LockMutex (buf_mutex);
|
||||||
|
|
||||||
|
for (buf = src->firstqueued;
|
||||||
|
buf && buf->state != MIX_BUF_QUEUED;
|
||||||
|
buf = buf->next)
|
||||||
|
{
|
||||||
|
buf->state = MIX_BUF_QUEUED;
|
||||||
|
}
|
||||||
|
|
||||||
|
mixSDL_UnlockMutex (buf_mutex);
|
||||||
|
|
||||||
|
src->curbufofs = 0;
|
||||||
|
src->cprocessed = 0;
|
||||||
|
src->nextqueued = src->firstqueued;
|
||||||
|
src->state = MIX_INITIAL;
|
||||||
|
}
|
||||||
|
|
||||||
/* get the sample next in queue in internal format */
|
/* get the sample next in queue in internal format */
|
||||||
static __inline__ bool
|
static __inline__ bool
|
||||||
mixSDL_SourceGetNextSample (mixSDL_Source *src, sint32* psamp)
|
mixSDL_SourceGetNextSample (mixSDL_Source *src, sint32* psamp)
|
||||||
|
|||||||
@@ -76,6 +76,7 @@ static __inline__ void mixSDL_PutSampleExt (void *dst, uint32 bpc,
|
|||||||
/* Source manipulation */
|
/* Source manipulation */
|
||||||
static void mixSDL_SourceUnqueueAll (mixSDL_Source *src);
|
static void mixSDL_SourceUnqueueAll (mixSDL_Source *src);
|
||||||
static void mixSDL_SourceStop_internal (mixSDL_Source *src);
|
static void mixSDL_SourceStop_internal (mixSDL_Source *src);
|
||||||
|
static void mixSDL_SourceRewind_internal (mixSDL_Source *src);
|
||||||
static void mixSDL_SourceActivate (mixSDL_Source* src);
|
static void mixSDL_SourceActivate (mixSDL_Source* src);
|
||||||
static void mixSDL_SourceDeactivate (mixSDL_Source* src);
|
static void mixSDL_SourceDeactivate (mixSDL_Source* src);
|
||||||
|
|
||||||
|
|||||||
@@ -61,6 +61,7 @@
|
|||||||
#define TFBSOUND_SOURCE_STATE MIX_SOURCE_STATE
|
#define TFBSOUND_SOURCE_STATE MIX_SOURCE_STATE
|
||||||
#define TFBSOUND_PLAYING MIX_PLAYING
|
#define TFBSOUND_PLAYING MIX_PLAYING
|
||||||
#define TFBSOUND_PAUSED MIX_PAUSED
|
#define TFBSOUND_PAUSED MIX_PAUSED
|
||||||
|
#define TFBSOUND_STOPPED MIX_STOPPED
|
||||||
#define TFBSOUND_FORMAT_MONO16 MIX_FORMAT_MONO16
|
#define TFBSOUND_FORMAT_MONO16 MIX_FORMAT_MONO16
|
||||||
#define TFBSOUND_FORMAT_STEREO16 MIX_FORMAT_STEREO16
|
#define TFBSOUND_FORMAT_STEREO16 MIX_FORMAT_STEREO16
|
||||||
#define TFBSOUND_FORMAT_STEREO8 MIX_FORMAT_STEREO8
|
#define TFBSOUND_FORMAT_STEREO8 MIX_FORMAT_STEREO8
|
||||||
|
|||||||
@@ -21,14 +21,19 @@
|
|||||||
|
|
||||||
#include "sound.h"
|
#include "sound.h"
|
||||||
|
|
||||||
|
static void CheckFinishedChannels ();
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
PlayChannel (COUNT channel, PVOID sample, COUNT sample_length, COUNT loop_begin,
|
PlayChannel (COUNT channel, PVOID sample, COUNT sample_length, COUNT loop_begin,
|
||||||
COUNT loop_length, unsigned char priority)
|
COUNT loop_length, unsigned char priority)
|
||||||
{
|
{
|
||||||
TFB_SoundSample *tfb_sample = *(TFB_SoundSample**) sample;
|
TFB_SoundSample *tfb_sample = *(TFB_SoundSample**) sample;
|
||||||
|
StopSource (channel);
|
||||||
|
// all finished (stopped) channels can be cleaned up at this point
|
||||||
|
// since this is the only func that can initiate an sfx sound
|
||||||
|
CheckFinishedChannels ();
|
||||||
soundSource[channel].sample = tfb_sample;
|
soundSource[channel].sample = tfb_sample;
|
||||||
TFBSound_SourceStop (soundSource[channel].handle);
|
|
||||||
TFBSound_Sourcei (soundSource[channel].handle, TFBSOUND_BUFFER,
|
TFBSound_Sourcei (soundSource[channel].handle, TFBSOUND_BUFFER,
|
||||||
tfb_sample->buffer[0]);
|
tfb_sample->buffer[0]);
|
||||||
TFBSound_SourcePlay (soundSource[channel].handle);
|
TFBSound_SourcePlay (soundSource[channel].handle);
|
||||||
@@ -40,6 +45,26 @@ StopChannel (COUNT channel, unsigned char Priority)
|
|||||||
StopSource (channel);
|
StopSource (channel);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
CheckFinishedChannels ()
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = FIRST_SFX_SOURCE; i <= LAST_SFX_SOURCE; ++i)
|
||||||
|
{
|
||||||
|
TFBSound_IntVal state;
|
||||||
|
|
||||||
|
TFBSound_GetSourcei (soundSource[i].handle, TFBSOUND_SOURCE_STATE,
|
||||||
|
&state);
|
||||||
|
if (state == TFBSOUND_STOPPED)
|
||||||
|
{
|
||||||
|
CleanSource (i);
|
||||||
|
// and if it failed... we still dont care
|
||||||
|
TFBSound_GetError();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
ChannelPlaying (COUNT WhichChannel)
|
ChannelPlaying (COUNT WhichChannel)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -34,22 +34,39 @@ StopSound (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
StopSource (int iSource)
|
CleanSource (int iSource)
|
||||||
{
|
{
|
||||||
|
#define MAX_STACK_BUFFERS 64
|
||||||
TFBSound_IntVal processed;
|
TFBSound_IntVal processed;
|
||||||
|
|
||||||
TFBSound_SourceStop (soundSource[iSource].handle);
|
|
||||||
TFBSound_GetSourcei (soundSource[iSource].handle,
|
TFBSound_GetSourcei (soundSource[iSource].handle,
|
||||||
TFBSOUND_BUFFERS_PROCESSED, &processed);
|
TFBSOUND_BUFFERS_PROCESSED, &processed);
|
||||||
|
|
||||||
if (processed != 0)
|
if (processed != 0)
|
||||||
{
|
{
|
||||||
TFBSound_Object *buffer = (TFBSound_Object *)
|
TFBSound_Object stack_bufs[MAX_STACK_BUFFERS];
|
||||||
HMalloc (sizeof (TFBSound_Object) * processed);
|
TFBSound_Object *bufs;
|
||||||
|
|
||||||
|
if (processed > MAX_STACK_BUFFERS)
|
||||||
|
bufs = (TFBSound_Object *) HMalloc (
|
||||||
|
sizeof (TFBSound_Object) * processed);
|
||||||
|
else
|
||||||
|
bufs = stack_bufs;
|
||||||
|
|
||||||
TFBSound_SourceUnqueueBuffers (soundSource[iSource].handle,
|
TFBSound_SourceUnqueueBuffers (soundSource[iSource].handle,
|
||||||
processed, buffer);
|
processed, bufs);
|
||||||
HFree (buffer);
|
|
||||||
|
if (processed > MAX_STACK_BUFFERS)
|
||||||
|
HFree (bufs);
|
||||||
}
|
}
|
||||||
|
// set the source state to 'initial'
|
||||||
|
TFBSound_SourceRewind (soundSource[iSource].handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
StopSource (int iSource)
|
||||||
|
{
|
||||||
|
TFBSound_SourceStop (soundSource[iSource].handle);
|
||||||
|
CleanSource (iSource);
|
||||||
}
|
}
|
||||||
|
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
@@ -82,6 +99,18 @@ SoundPlaying (void)
|
|||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// for now just spin in a sleep() loop
|
||||||
|
// perhaps later change to condvar implementation
|
||||||
|
void
|
||||||
|
WaitForSoundEnd (COUNT Channel)
|
||||||
|
{
|
||||||
|
while (Channel == TFBSOUND_WAIT_ALL ?
|
||||||
|
SoundPlaying () : ChannelPlaying (Channel))
|
||||||
|
{
|
||||||
|
SleepThread (ONE_SECOND / 20);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
TFB_SoundChain *
|
TFB_SoundChain *
|
||||||
create_soundchain (TFB_SoundDecoder *decoder, float startTime)
|
create_soundchain (TFB_SoundDecoder *decoder, float startTime)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -90,6 +90,7 @@ typedef struct tfb_soundsource
|
|||||||
extern TFB_SoundSource soundSource[];
|
extern TFB_SoundSource soundSource[];
|
||||||
|
|
||||||
void StopSource (int iSource);
|
void StopSource (int iSource);
|
||||||
|
void CleanSource (int iSource);
|
||||||
|
|
||||||
void SetSFXVolume (float volume);
|
void SetSFXVolume (float volume);
|
||||||
void SetSpeechVolume (float volume);
|
void SetSpeechVolume (float volume);
|
||||||
|
|||||||
@@ -27,6 +27,7 @@ static unsigned int tfb_enum_lookup[TFBSOUND_ENUMSIZE];
|
|||||||
unsigned int TFBSOUND_NO_ERROR;
|
unsigned int TFBSOUND_NO_ERROR;
|
||||||
int TFBSOUND_PAUSED;
|
int TFBSOUND_PAUSED;
|
||||||
int TFBSOUND_PLAYING;
|
int TFBSOUND_PLAYING;
|
||||||
|
int TFBSOUND_STOPPED;
|
||||||
unsigned int TFBSOUND_FORMAT_MONO16;
|
unsigned int TFBSOUND_FORMAT_MONO16;
|
||||||
unsigned int TFBSOUND_FORMAT_STEREO16;
|
unsigned int TFBSOUND_FORMAT_STEREO16;
|
||||||
unsigned int TFBSOUND_FORMAT_STEREO8;
|
unsigned int TFBSOUND_FORMAT_STEREO8;
|
||||||
@@ -262,6 +263,7 @@ TFB_choose_InitSound (int driver, int flags)
|
|||||||
TFBSOUND_NO_ERROR = AL_NO_ERROR;
|
TFBSOUND_NO_ERROR = AL_NO_ERROR;
|
||||||
TFBSOUND_PAUSED = AL_PAUSED;
|
TFBSOUND_PAUSED = AL_PAUSED;
|
||||||
TFBSOUND_PLAYING = AL_PLAYING;
|
TFBSOUND_PLAYING = AL_PLAYING;
|
||||||
|
TFBSOUND_STOPPED = AL_STOPPED;
|
||||||
TFBSOUND_FORMAT_MONO16 = AL_FORMAT_MONO16;
|
TFBSOUND_FORMAT_MONO16 = AL_FORMAT_MONO16;
|
||||||
TFBSOUND_FORMAT_STEREO16 = AL_FORMAT_STEREO16;
|
TFBSOUND_FORMAT_STEREO16 = AL_FORMAT_STEREO16;
|
||||||
TFBSOUND_FORMAT_MONO8 = AL_FORMAT_MONO8;
|
TFBSOUND_FORMAT_MONO8 = AL_FORMAT_MONO8;
|
||||||
@@ -281,6 +283,7 @@ TFB_choose_InitSound (int driver, int flags)
|
|||||||
TFBSOUND_NO_ERROR = MIX_NO_ERROR;
|
TFBSOUND_NO_ERROR = MIX_NO_ERROR;
|
||||||
TFBSOUND_PAUSED = MIX_PAUSED;
|
TFBSOUND_PAUSED = MIX_PAUSED;
|
||||||
TFBSOUND_PLAYING = MIX_PLAYING;
|
TFBSOUND_PLAYING = MIX_PLAYING;
|
||||||
|
TFBSOUND_STOPPED = MIX_STOPPED;
|
||||||
TFBSOUND_FORMAT_MONO16 = MIX_FORMAT_MONO16;
|
TFBSOUND_FORMAT_MONO16 = MIX_FORMAT_MONO16;
|
||||||
TFBSOUND_FORMAT_STEREO16 = MIX_FORMAT_STEREO16;
|
TFBSOUND_FORMAT_STEREO16 = MIX_FORMAT_STEREO16;
|
||||||
TFBSOUND_FORMAT_MONO8 = MIX_FORMAT_MONO8;
|
TFBSOUND_FORMAT_MONO8 = MIX_FORMAT_MONO8;
|
||||||
|
|||||||
@@ -101,6 +101,7 @@ enum
|
|||||||
|
|
||||||
extern int TFBSOUND_PAUSED;
|
extern int TFBSOUND_PAUSED;
|
||||||
extern int TFBSOUND_PLAYING;
|
extern int TFBSOUND_PLAYING;
|
||||||
|
extern int TFBSOUND_STOPPED;
|
||||||
extern unsigned int TFBSOUND_NO_ERROR;
|
extern unsigned int TFBSOUND_NO_ERROR;
|
||||||
extern unsigned int TFBSOUND_FORMAT_MONO16;
|
extern unsigned int TFBSOUND_FORMAT_MONO16;
|
||||||
extern unsigned int TFBSOUND_FORMAT_STEREO16;
|
extern unsigned int TFBSOUND_FORMAT_STEREO16;
|
||||||
|
|||||||
Reference in New Issue
Block a user