summaryrefslogtreecommitdiff
path: root/src/openal.c
diff options
context:
space:
mode:
authorSteven Fuller <relnev@icculus.org>2008-05-22 21:04:28 -0700
committerPatryk Obara <dreamer.tan@gmail.com>2019-08-20 02:22:37 +0200
commit243e6d8f550a2f518e1c07ce7fd1c7257b50ea86 (patch)
tree00daa94cdc669cd7902d0ce9a5b3b405877a6d9b /src/openal.c
parentc6dec0e4d9906e0064f23bfbaccca4e18b5b0152 (diff)
OpenAL WIP.
Diffstat (limited to 'src/openal.c')
-rw-r--r--src/openal.c132
1 files changed, 115 insertions, 17 deletions
diff --git a/src/openal.c b/src/openal.c
index 5008805..0798e6d 100644
--- a/src/openal.c
+++ b/src/openal.c
@@ -19,6 +19,10 @@
#include "dynblock.h"
#include "stratdef.h"
+#if defined( _MSC_VER )
+#include <eax.h>
+#endif
+
ACTIVESOUNDSAMPLE ActiveSounds[SOUND_MAXACTIVE];
ACTIVESOUNDSAMPLE BlankActiveSound = {SID_NOSOUND,ASP_Minimum,0,0,NULL,0,0,0,0,0, { {0,0,0},{0,0,0},0,0 }, 0, 0, { 0.0, 0.0, 0.0 }, { 0.0, 0.0, 0.0 }, NULL, NULL, NULL};
SOUNDSAMPLEDATA BlankGameSound = {0,0,0,0,0,NULL,0,0,NULL,0};
@@ -32,6 +36,24 @@ extern int WantSound;
static int SoundActivated = 0;
+static struct {
+ unsigned int flags;
+ BOOL reverb_changed;
+ float reverb_mix;
+ unsigned int env_index;
+} SoundConfig;
+
+#if defined(_MSC_VER)
+// EAX1.0
+#define EAX_REVERBMIX_USEDISTANCE -1.0F
+
+// EAX1.0
+#define EAX_ENVIRONMENT_DEFAULT EAX_ENVIRONMENT_PLAIN
+
+ALAPI ALenum ALAPIENTRY (*EAX_pfPropSet)(const GUID *propertySetID,ALuint property,ALuint source,ALvoid *pValue,ALuint size);
+ALAPI ALenum ALAPIENTRY (*EAX_pfPropGet)(const GUID *propertySetID,ALuint property,ALuint source,ALvoid *value,ALuint size);
+#endif
+
/* start simplistic riff wave parsing */
#define lsb8 (buf, x) (((unsigned int)buf[(x)+0] << 0))
#define lsb16(buf, x) (((unsigned int)buf[(x)+0] << 0) | ((unsigned int)buf[(x)+1] << 8))
@@ -143,6 +165,7 @@ openal.c TODO:
1. There is no EAX/Reverb. But there's probably not much I can do...
2. Restarting sound system may or may not work.
3. Better Error Handling (device not avail, etc).
+4. Implement sample offsets in psnd.c using AL_SAMPLE_OFFSET (add api here)
*/
int PlatStartSoundSys()
{
@@ -158,6 +181,12 @@ int PlatStartSoundSys()
0
};
+ /* Set the globals. */
+ SoundConfig.flags = 0;
+ SoundConfig.reverb_changed = TRUE;
+ SoundConfig.reverb_mix = 0.0f;
+ SoundConfig.env_index = 1000;
+
SoundActivated = 0;
if (WantSound == 0) {
return 0;
@@ -196,9 +225,24 @@ int PlatStartSoundSys()
alDistanceModel(AL_NONE);
if (alGetError() != AL_NO_ERROR) {
+ // TODO: this shouldn't exit abruptly..
+ // TODO: better error handling throughout
fprintf(stderr, "alListenerfv() error = ...\n");
exit(1);
}
+
+#if defined(_MSC_VER)
+ EAX_pfPropSet = NULL;
+ EAX_pfPropGet = NULL;
+
+ if( alISExtensionPresent( (ALubyte*) "EAX" ) == AL_TRUE ) {
+ EAX_pfPropSet = alGetProcAddress( (ALubyte*) "EAXSet" );
+ EAX_pfPropGet = alGetProcAddress( (ALubyte*) "EAXGet" );
+ }
+
+ // Set a default environment value.
+ PlatSetEnviroment(EAX_ENVIRONMENT_DEFAULT, EAX_REVERBMIX_USEDISTANCE);
+#endif
memset( ActiveSounds, 0, sizeof(ActiveSounds) );
@@ -213,6 +257,8 @@ int PlatStartSoundSys()
break;
}
+ // TODO: remove the incorrectly named PropSetP variables
+
ActiveSounds[i].ds3DBufferP = p;
ActiveSounds[i].PropSetP_pos[0] = 0.0;
@@ -512,14 +558,17 @@ int PlatPlaySound(int activeIndex)
alSourcei(ActiveSounds[activeIndex].ds3DBufferP, AL_LOOPING,
ActiveSounds[activeIndex].loop ? AL_TRUE : AL_FALSE);
-
+
+ /* may need to initialise pitch before playing */
if (1 || ActiveSounds[activeIndex].pitch != GameSounds[si].pitch) {
PlatChangeSoundPitch(activeIndex, ActiveSounds[activeIndex].pitch);
}
if (ActiveSounds[activeIndex].threedee) {
alSourcei(ActiveSounds[activeIndex].ds3DBufferP, AL_SOURCE_RELATIVE, AL_FALSE);
-
+
+ // TODO: min distance ActiveSounds[activeIndex].threedeedata.inner_range?
+ // TODO: max distance DS3D_DEFAULTMAXDISTANCE?
PlatDo3dSound(activeIndex);
} else {
ALfloat zero[3] = { 0.0f, 0.0f, 0.0f };
@@ -535,6 +584,12 @@ int PlatPlaySound(int activeIndex)
PlatChangeSoundVolume (activeIndex, ActiveSounds[activeIndex].volume);
}
+
+ if (!ActiveSounds[activeIndex].reverb_off) {
+ // TODO: DSPROPERTY_EAXBUFFER_REVERBMIX set to &SoundConfig.reverb_mix
+ } else {
+ // TODO: DSPROPERTY_EAXBUFFER_REVERBMIX set to 0
+ }
if (!ActiveSounds[activeIndex].paused) {
alSourcePlay (ActiveSounds[activeIndex].ds3DBufferP);
@@ -692,9 +747,6 @@ int PlatDo3dSound(int activeIndex)
return 0;
}
-// if (ActiveSounds[activeIndex].threedee == 0)
-// return 1;
-
relativePosn.vx = ActiveSounds[activeIndex].threedeedata.position.vx -
Global_VDB_Ptr->VDB_World.vx;
relativePosn.vy = ActiveSounds[activeIndex].threedeedata.position.vy -
@@ -780,6 +832,8 @@ fprintf(stderr, "OPENAL: Sound : (%f, %f, %f) [%d] [%d,%d]\n", ActiveSounds[acti
// ActiveSounds[activeIndex].threedeedata.velocity.vz;
// alSourcefv (ActiveSounds[activeIndex].ds3DBufferP,
// AL_VELOCITY, ActiveSounds[activeIndex].PropSetP_vel);
+
+ // TODO: fake 3d support ?
}
return 1;
@@ -790,10 +844,11 @@ void PlatUpdatePlayer()
{
ALfloat vel[3], or[6], pos[3];
- if (!SoundActivated)
+ if (!SoundActivated) {
return;
-
- if (Global_VDB_Ptr) {
+ }
+
+ if (Global_VDB_Ptr != NULL) {
extern int NormalFrameTime;
extern int DopplerShiftIsOn;
@@ -842,8 +897,59 @@ void PlatUpdatePlayer()
alListenerfv (AL_VELOCITY, vel);
alListenerfv (AL_POSITION, pos);
}
+
+#if defined( _MSC_VER )
+ if( SoundConfig.reverb_changed ) {
+ // TODO: reverb handling
+ }
+#endif
+}
+
+void PlatSetEnviroment(unsigned int env_index, float reverb_mix)
+{
+#ifdef OPENAL_DEBUG
+ fprintf(stderr, "OPENAL: PlatSetEnvironment(%d, %f)\n", env_index, reverb_mix);
+#endif
+
+#if defined( _MSC_VER )
+ if( SoundConfig.env_index != env_index ) {
+
+ // TODO: support the custom plain reverb
+ if( env_index >= EAX_ENVIRONMENT_COUNT ) {
+ env_index = EAX_ENVIRONMENT_DEFAULT;
+ }
+
+ if( EAX_pfPropSet != NULL ) {
+ ALulong ulEAXVal = env_index;
+
+ EAX_pfPropSet(PROPSETID_EAX_ListenerProperties,
+ DSPROPERTY_EAXLISTENER_ENVIRONMENT, 0, &ulEAXVal, sizeof( ulEAXVal ) );
+
+ // how to set all parameters:
+ // EAXLISTENERPROPERTIES mystruct = { ... };
+ // EAX_pfPrp[Set(PROPSETID_EAX_ListenerProperites,
+ // DSPROPERTY_EAXLISTENER_ALL, 0, &mystruct, sizeof(EAXLISTENERPROPERTIES));
+ }
+
+ SoundConfig.env_index = env_index;
+ }
- // TODO: reverb handling
+ if( reverb_mix == SoundConfig.reverb_mix ) {
+ return;
+ }
+
+ // EAX2.0: EAX_REVERBMIX_USEDISTANCE is DSPPROPERTY_EAXBUFFER_ROOMROLLOFFFACTOR?
+ // But I don't think AvP even set this in the final version.
+
+ if( (reverb_mix < 0.0f) || (reverb_mix > 1.0f) ) {
+ // TODO: handle EAX_REVERBMIX_USEDISTANCE
+ SoundConfig.reverb_mix = EAX_REVERBMIX_USEDISTANCE;
+ } else {
+ SoundConfig.reverb_mix = reverb_mix;
+ }
+
+ SoundConfig.reverb_changed = TRUE;
+#endif
}
void PlatEndGameSound(SOUNDINDEX index)
@@ -909,14 +1015,6 @@ void InitialiseBaseFrequency(SOUNDINDEX soundNum)
GameSounds[soundNum].dsFrequency = frequency;
}
-void PlatSetEnviroment(unsigned int env_index, float reverb_mix)
-{
- // TODO: implement
-#ifdef OPENAL_DEBUG
- fprintf(stderr, "OPENAL: PlatSetEnvironment(%d, %f)\n", env_index, reverb_mix);
-#endif
-}
-
void UpdateSoundFrequencies()
{
extern int SoundSwitchedOn;