From 5f8e65e09941c9c5d48e2277a8b1be1e35f04a9a Mon Sep 17 00:00:00 2001 From: Chris Robinson Date: Fri, 28 Dec 2007 22:41:14 -0800 Subject: [PATCH] Implement AL_EXT_FLOAT32 --- Alc/ALc.c | 2 +- Alc/ALu.c | 6 ++++++ OpenAL32/Include/alMain.h | 3 +++ OpenAL32/alBuffer.c | 28 ++++++++++++++++++++++++++++ OpenAL32/alSource.c | 9 +++++++++ 5 files changed, 47 insertions(+), 1 deletion(-) diff --git a/Alc/ALc.c b/Alc/ALc.c index 8c75b32c..0db68efe 100644 --- a/Alc/ALc.c +++ b/Alc/ALc.c @@ -357,7 +357,7 @@ static ALvoid InitContext(ALCcontext *pContext) pContext->lNumStereoSources = 1; pContext->lNumMonoSources = pContext->Device->MaxNoOfSources - pContext->lNumStereoSources; - strcpy(pContext->ExtensionList, "AL_EXT_EXPONENT_DISTANCE AL_EXT_IMA4 AL_EXT_LINEAR_DISTANCE AL_EXT_OFFSET"); + strcpy(pContext->ExtensionList, "AL_EXT_EXPONENT_DISTANCE AL_EXT_FLOAT32 AL_EXT_IMA4 AL_EXT_LINEAR_DISTANCE AL_EXT_OFFSET"); } diff --git a/Alc/ALu.c b/Alc/ALu.c index b5af500b..f77990a7 100644 --- a/Alc/ALu.c +++ b/Alc/ALu.c @@ -68,6 +68,10 @@ __inline ALuint aluBytesFromFormat(ALenum format) case AL_FORMAT_51CHN16: return 2; + case AL_FORMAT_MONO_FLOAT32: + case AL_FORMAT_STEREO_FLOAT32: + return 4; + default: return 0; } @@ -79,10 +83,12 @@ __inline ALuint aluChannelsFromFormat(ALenum format) { case AL_FORMAT_MONO8: case AL_FORMAT_MONO16: + case AL_FORMAT_MONO_FLOAT32: return 1; case AL_FORMAT_STEREO8: case AL_FORMAT_STEREO16: + case AL_FORMAT_STEREO_FLOAT32: return 2; case AL_FORMAT_QUAD8: diff --git a/OpenAL32/Include/alMain.h b/OpenAL32/Include/alMain.h index 30dd068f..f11f8fd9 100644 --- a/OpenAL32/Include/alMain.h +++ b/OpenAL32/Include/alMain.h @@ -89,6 +89,9 @@ extern char _alDebug[256]; } while(0) +#define AL_FORMAT_MONO_FLOAT32 0x10010 +#define AL_FORMAT_STEREO_FLOAT32 0x10011 + #define AL_FORMAT_MONO_IMA4 0x1300 #define AL_FORMAT_STEREO_IMA4 0x1301 // These are from AL_EXT_MCFORMATS, which we don't support yet but the mixer diff --git a/OpenAL32/alBuffer.c b/OpenAL32/alBuffer.c index ab5b60d8..d1a8c359 100644 --- a/OpenAL32/alBuffer.c +++ b/OpenAL32/alBuffer.c @@ -282,6 +282,10 @@ ALAPI ALvoid ALAPIENTRY alBufferData(ALuint buffer,ALenum format,const ALvoid *d LoadData(ALBuf, data, size, freq, format, AL_FORMAT_MONO16); break; + case AL_FORMAT_MONO_FLOAT32: + LoadData(ALBuf, data, size, freq, format, AL_FORMAT_MONO16); + break; + case AL_FORMAT_STEREO8: LoadData(ALBuf, data, size, freq, format, AL_FORMAT_STEREO16); break; @@ -290,6 +294,10 @@ ALAPI ALvoid ALAPIENTRY alBufferData(ALuint buffer,ALenum format,const ALvoid *d LoadData(ALBuf, data, size, freq, format, AL_FORMAT_STEREO16); break; + case AL_FORMAT_STEREO_FLOAT32: + LoadData(ALBuf, data, size, freq, format, AL_FORMAT_STEREO16); + break; + case AL_FORMAT_MONO_IMA4: // Here is where things vary: // nVidia and Apple use 64+1 samples per block => block_size=36 bytes @@ -913,6 +921,26 @@ static void LoadData(ALbuffer *ALBuf, const ALubyte *data, ALsizei size, ALuint alSetError(AL_OUT_OF_MEMORY); break; + case 4: + size /= sizeof(ALfloat); + + // Allocate 8 extra samples + ALBuf->data = realloc(ALBuf->data, (8*NewChannels + size) * (1*sizeof(ALshort))); + if (ALBuf->data) + { + for (i = 0;i < size;i++) + ALBuf->data[i] = (ALshort)(((ALfloat*)data)[i] * 32767.5f - 0.5); + memset(&(ALBuf->data[size]), 0, 16*NewChannels); + + ALBuf->format = NewFormat; + ALBuf->eOriginalFormat = OrigFormat; + ALBuf->size = size*1*sizeof(ALshort); + ALBuf->frequency = freq; + } + else + alSetError(AL_OUT_OF_MEMORY); + break; + default: assert(0); } diff --git a/OpenAL32/alSource.c b/OpenAL32/alSource.c index a06c6060..7c022e6c 100644 --- a/OpenAL32/alSource.c +++ b/OpenAL32/alSource.c @@ -1910,6 +1910,10 @@ static ALboolean GetSourceOffset(ALsource *pSource, ALenum eName, ALfloat *pflOf { *pflOffset = (ALfloat)(lBytesPlayed >> 1); } + else if (aluBytesFromFormat(eOriginalFormat) == 4) + { + *pflOffset = (ALfloat)(lBytesPlayed << 1); + } else if ((eOriginalFormat == AL_FORMAT_MONO_IMA4) || (eOriginalFormat == AL_FORMAT_STEREO_IMA4)) { @@ -2061,6 +2065,11 @@ static ALint GetByteOffset(ALsource *pSource) lByteOffset = pSource->lOffset * 2; lByteOffset -= (lByteOffset % (lChannels * 2)); } + else if (aluBytesFromFormat(pBuffer->eOriginalFormat) == 4) + { + lByteOffset = pSource->lOffset / 2; + lByteOffset -= (lByteOffset % (lChannels * 2)); + } else if ((pBuffer->eOriginalFormat == AL_FORMAT_MONO_IMA4) || (pBuffer->eOriginalFormat == AL_FORMAT_STEREO_IMA4)) { -- 2.11.4.GIT