diff options
-rw-r--r-- | Alc/ALc.c | 2 | ||||
-rw-r--r-- | Alc/ALu.c | 64 | ||||
-rw-r--r-- | OpenAL32/Include/alMain.h | 5 | ||||
-rw-r--r-- | OpenAL32/Include/alSource.h | 1 | ||||
-rw-r--r-- | OpenAL32/alExtension.c | 1 | ||||
-rw-r--r-- | OpenAL32/alSource.c | 17 |
6 files changed, 72 insertions, 18 deletions
@@ -389,7 +389,7 @@ static const ALchar alExtList[] = "AL_EXT_LINEAR_DISTANCE AL_EXT_MCFORMATS AL_EXT_MULAW " "AL_EXT_MULAW_MCFORMATS AL_EXT_OFFSET AL_EXT_source_distance_model " "AL_LOKI_quadriphonic AL_SOFTX_buffer_samples AL_SOFT_buffer_sub_data " - "AL_SOFT_loop_points"; + "AL_SOFT_loop_points AL_SOFTX_non_virtual_channels"; // Mixing Priority Level static ALint RTPrioLevel; @@ -89,6 +89,22 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) static const ALfloat angles_X71[8] = { -30.0f, 30.0f, 0.0f, 0.0f, -110.0f, 110.0f, -90.0f, 90.0f }; + static const Channel chans_Mono[1] = { FRONT_CENTER }; + static const Channel chans_Stereo[2] = { FRONT_LEFT, FRONT_RIGHT }; + static const Channel chans_Rear[2] = { BACK_LEFT, BACK_RIGHT }; + static const Channel chans_Quad[4] = { FRONT_LEFT, FRONT_RIGHT, + BACK_LEFT, BACK_RIGHT }; + static const Channel chans_X51[6] = { FRONT_LEFT, FRONT_RIGHT, + FRONT_CENTER, LFE, + BACK_LEFT, BACK_RIGHT }; + static const Channel chans_X61[7] = { FRONT_LEFT, FRONT_RIGHT, + FRONT_CENTER, LFE, BACK_CENTER, + SIDE_LEFT, SIDE_RIGHT }; + static const Channel chans_X71[8] = { FRONT_LEFT, FRONT_RIGHT, + FRONT_CENTER, LFE, + BACK_LEFT, BACK_RIGHT, + SIDE_LEFT, SIDE_RIGHT }; + ALCdevice *Device = ALContext->Device; ALfloat SourceVolume,ListenerGain,MinVolume,MaxVolume; ALbufferlistitem *BufferListItem; @@ -101,8 +117,9 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) ALint NumSends, Frequency; const ALfloat *SpeakerGain; const ALfloat *angles = NULL; + const Channel *chans = NULL; ALint num_channels = 0; - ALint lfe_chan = -1; + ALboolean VirtualChannels; ALfloat Pitch; ALfloat cw; ALuint pos; @@ -117,10 +134,11 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) ListenerGain = ALContext->Listener.Gain; /* Get source properties */ - SourceVolume = ALSource->flGain; - MinVolume = ALSource->flMinGain; - MaxVolume = ALSource->flMaxGain; - Pitch = ALSource->flPitch; + SourceVolume = ALSource->flGain; + MinVolume = ALSource->flMinGain; + MaxVolume = ALSource->flMaxGain; + Pitch = ALSource->flPitch; + VirtualChannels = ALSource->VirtualChannels; /* Calculate the stepping value */ Channels = FmtMono; @@ -148,11 +166,14 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) Channels = ALBuffer->FmtChannels; - ALSource->Params.DoMix = ((Device->Flags&DEVICE_USE_HRTF) ? - SelectHrtfMixer(ALBuffer, (ALSource->Params.Step==FRACTIONONE) ? - POINT_RESAMPLER : ALSource->Resampler) : - SelectMixer(ALBuffer, (ALSource->Params.Step==FRACTIONONE) ? - POINT_RESAMPLER : ALSource->Resampler)); + if(ALSource->VirtualChannels && (Device->Flags&DEVICE_USE_HRTF)) + ALSource->Params.DoMix = SelectHrtfMixer(ALBuffer, + (ALSource->Params.Step==FRACTIONONE) ? POINT_RESAMPLER : + ALSource->Resampler); + else + ALSource->Params.DoMix = SelectMixer(ALBuffer, + (ALSource->Params.Step==FRACTIONONE) ? POINT_RESAMPLER : + ALSource->Resampler); break; } BufferListItem = BufferListItem->next; @@ -182,10 +203,11 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) { case FmtMono: angles = angles_Mono; + chans = chans_Mono; num_channels = 1; break; case FmtStereo: - if((ALContext->Device->Flags&DEVICE_DUPLICATE_STEREO)) + if(VirtualChannels && (ALContext->Device->Flags&DEVICE_DUPLICATE_STEREO)) { DryGain *= aluSqrt(2.0f/4.0f); for(c = 0;c < 2;c++) @@ -203,45 +225,53 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) } } angles = angles_Stereo; + chans = chans_Stereo; num_channels = 2; break; case FmtRear: angles = angles_Rear; + chans = chans_Rear; num_channels = 2; break; case FmtQuad: angles = angles_Quad; + chans = chans_Quad; num_channels = 4; break; case FmtX51: angles = angles_X51; + chans = chans_X51; num_channels = 6; - lfe_chan = 3; break; case FmtX61: angles = angles_X61; + chans = chans_X61; num_channels = 7; - lfe_chan = 3; break; case FmtX71: angles = angles_X71; + chans = chans_X71; num_channels = 8; - lfe_chan = 3; break; } - if((Device->Flags&DEVICE_USE_HRTF)) + if(VirtualChannels == AL_FALSE) + { + for(c = 0;c < num_channels;c++) + SrcMatrix[c][chans[c]] += DryGain * ListenerGain; + } + else if((Device->Flags&DEVICE_USE_HRTF)) { for(c = 0;c < num_channels;c++) { const ALshort *hrtf_left, *hrtf_right; - if(c == lfe_chan) + if(chans[c] == LFE) { /* Skip LFE */ ALSource->Params.HrtfDelay[c][0] = 0; @@ -271,7 +301,7 @@ ALvoid CalcNonAttnSourceParams(ALsource *ALSource, const ALCcontext *ALContext) { for(c = 0;c < num_channels;c++) { - if(c == lfe_chan) /* Special-case LFE */ + if(chans[c] == LFE) /* Special-case LFE */ { SrcMatrix[c][LFE] += DryGain * ListenerGain; continue; diff --git a/OpenAL32/Include/alMain.h b/OpenAL32/Include/alMain.h index 3264d5ed..ebf1b20e 100644 --- a/OpenAL32/Include/alMain.h +++ b/OpenAL32/Include/alMain.h @@ -93,6 +93,11 @@ AL_API ALboolean AL_APIENTRY alIsBufferFormatSupportedSOFT(ALenum format); #endif #endif +#ifndef AL_SOFT_non_virtual_channels +#define AL_SOFT_non_virtual_channels 1 +#define AL_VIRTUAL_CHANNELS_SOFT 0x1033 +#endif + #if defined(HAVE_STDINT_H) #include <stdint.h> diff --git a/OpenAL32/Include/alSource.h b/OpenAL32/Include/alSource.h index 9cbd7f54..8afe8281 100644 --- a/OpenAL32/Include/alSource.h +++ b/OpenAL32/Include/alSource.h @@ -46,6 +46,7 @@ typedef struct ALsource ALboolean bHeadRelative; ALboolean bLooping; ALenum DistanceModel; + ALboolean VirtualChannels; resampler_t Resampler; diff --git a/OpenAL32/alExtension.c b/OpenAL32/alExtension.c index eb0f46a8..ebb2e252 100644 --- a/OpenAL32/alExtension.c +++ b/OpenAL32/alExtension.c @@ -75,6 +75,7 @@ static const ALenums enumeration[] = { { "AL_STREAMING", AL_STREAMING }, { "AL_UNDETERMINED", AL_UNDETERMINED }, { "AL_METERS_PER_UNIT", AL_METERS_PER_UNIT }, + { "AL_VIRTUAL_CHANNELS_SOFT", AL_VIRTUAL_CHANNELS_SOFT }, // Source EFX Properties { "AL_DIRECT_FILTER", AL_DIRECT_FILTER }, diff --git a/OpenAL32/alSource.c b/OpenAL32/alSource.c index e91206eb..a1319005 100644 --- a/OpenAL32/alSource.c +++ b/OpenAL32/alSource.c @@ -680,6 +680,16 @@ AL_API ALvoid AL_APIENTRY alSourcei(ALuint source,ALenum eParam,ALint lValue) alSetError(pContext, AL_INVALID_VALUE); break; + case AL_VIRTUAL_CHANNELS_SOFT: + if(lValue == AL_TRUE || lValue == AL_FALSE) + { + Source->VirtualChannels = lValue; + Source->NeedsUpdate = AL_TRUE; + } + else + alSetError(pContext, AL_INVALID_VALUE); + break; + case AL_DISTANCE_MODEL: if(lValue == AL_NONE || lValue == AL_INVERSE_DISTANCE || @@ -801,6 +811,7 @@ AL_API void AL_APIENTRY alSourceiv(ALuint source, ALenum eParam, const ALint* pl case AL_AUXILIARY_SEND_FILTER_GAIN_AUTO: case AL_AUXILIARY_SEND_FILTER_GAINHF_AUTO: case AL_DISTANCE_MODEL: + case AL_VIRTUAL_CHANNELS_SOFT: alSourcei(source, eParam, plValues[0]); return; @@ -1149,6 +1160,10 @@ AL_API ALvoid AL_APIENTRY alGetSourcei(ALuint source, ALenum eParam, ALint *plVa *plValue = (ALint)Source->DopplerFactor; break; + case AL_VIRTUAL_CHANNELS_SOFT: + *plValue = Source->VirtualChannels; + break; + case AL_DISTANCE_MODEL: *plValue = Source->DistanceModel; break; @@ -1245,6 +1260,7 @@ AL_API void AL_APIENTRY alGetSourceiv(ALuint source, ALenum eParam, ALint* plVal case AL_AUXILIARY_SEND_FILTER_GAIN_AUTO: case AL_AUXILIARY_SEND_FILTER_GAINHF_AUTO: case AL_DISTANCE_MODEL: + case AL_VIRTUAL_CHANNELS_SOFT: alGetSourcei(source, eParam, plValues); return; @@ -1807,6 +1823,7 @@ static ALvoid InitSourceParams(ALsource *Source) Source->AirAbsorptionFactor = 0.0f; Source->RoomRolloffFactor = 0.0f; Source->DopplerFactor = 1.0f; + Source->VirtualChannels = AL_TRUE; Source->DistanceModel = AL_INVERSE_DISTANCE_CLAMPED; |