From 0ea5fc66924303d1bf73ba283a383e2aadee02f2 Mon Sep 17 00:00:00 2001 From: neodarz Date: Sat, 11 Aug 2018 20:21:34 +0200 Subject: Initial commit --- .../doxygen/nel/sound__driver__al_8cpp-source.html | 521 +++++++++++++++++++++ 1 file changed, 521 insertions(+) create mode 100644 docs/doxygen/nel/sound__driver__al_8cpp-source.html (limited to 'docs/doxygen/nel/sound__driver__al_8cpp-source.html') diff --git a/docs/doxygen/nel/sound__driver__al_8cpp-source.html b/docs/doxygen/nel/sound__driver__al_8cpp-source.html new file mode 100644 index 00000000..ee362760 --- /dev/null +++ b/docs/doxygen/nel/sound__driver__al_8cpp-source.html @@ -0,0 +1,521 @@ + + + + nevrax.org : docs + + + + + + + + + + + + + + +
# Home   # nevrax.com   
+ + + + +
Nevrax
+ + + + + + + + + + +
+ + +
+ Nevrax.org
+ + + + + + + +
#News
#Mailing-list
#Documentation
#CVS
#Bugs
#License
+
+ + +
+ + +
+Docs + +
+  + + + + + +
Documentation 
+ +
+Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Related Pages   Search  
+

sound_driver_al.cpp

Go to the documentation of this file.
00001 
+00007 /* Copyright, 2001 Nevrax Ltd.
+00008  *
+00009  * This file is part of NEVRAX NEL.
+00010  * NEVRAX NEL is free software; you can redistribute it and/or modify
+00011  * it under the terms of the GNU General Public License as published by
+00012  * the Free Software Foundation; either version 2, or (at your option)
+00013  * any later version.
+00014 
+00015  * NEVRAX NEL is distributed in the hope that it will be useful, but
+00016  * WITHOUT ANY WARRANTY; without even the implied warranty of
+00017  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+00018  * General Public License for more details.
+00019 
+00020  * You should have received a copy of the GNU General Public License
+00021  * along with NEVRAX NEL; see the file COPYING. If not, write to the
+00022  * Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
+00023  * MA 02111-1307, USA.
+00024  */
+00025 
+00026 #include "stdopenal.h"
+00027 
+00028 #include "buffer_al.h"
+00029 #include "listener_al.h"
+00030 
+00031 using namespace std;
+00032 
+00033 
+00034 namespace NLSOUND {
+00035 
+00036 
+00037 #ifdef EAX_AVAILABLE
+00038 // EAXSet global function
+00039 EAXSet                                  EAXSetProp = NULL;
+00040 
+00041 // EAXGet global function
+00042 EAXGet                                  EAXGetProp = NULL;
+00043 #endif
+00044 
+00045 
+00046 // Currently, the OpenAL headers are different between Windows and Linux versions !
+00047 // AL_INVALID_XXXX are part of the spec, though.
+00048 #ifdef NL_OS_UNIX
+00049 #define AL_INVALID_ENUM AL_ILLEGAL_ENUM  
+00050 #define AL_INVALID_OPERATION AL_ILLEGAL_COMMAND 
+00051 #endif
+00052 
+00053 
+00054 #ifdef NL_DEBUG
+00055 // Test error in debug mode
+00056 void TestALError()
+00057 {
+00058         ALuint errcode = alGetError();
+00059         switch( errcode )
+00060         {
+00061         case AL_NO_ERROR : break;
+00062         case AL_INVALID_NAME : nlerror( "OpenAL: Invalid name" );
+00063         case AL_INVALID_ENUM  : nlerror( "OpenAL: Invalid enum" );
+00064         case AL_INVALID_VALUE  : nlerror( "OpenAL: Invalid value" );
+00065         case AL_INVALID_OPERATION  : nlerror( "OpenAL: Invalid operation" );
+00066         case AL_OUT_OF_MEMORY  : nlerror( "OpenAL: Out of memory" );
+00067         // alGetString( errcode ) seems to fail !
+00068         }
+00069 }
+00070 #endif
+00071 
+00072 
+00073 #define INITIAL_BUFFERS 8
+00074 #define INITIAL_SOURCES 8
+00075 #define BUFFER_ALLOC_RATE 8
+00076 #define SOURCE_ALLOC_RATE 8
+00077 
+00078 #define ROLLOFF_FACTOR_DEFAULT 1.0f
+00079 
+00080 /*
+00081  * Sound driver instance creation
+00082  */
+00083 #ifdef NL_OS_WINDOWS
+00084         
+00085 __declspec(dllexport) ISoundDriver *NLSOUND_createISoundDriverInstance()
+00086 {
+00087         CSoundDriverAL *driver = new CSoundDriverAL();
+00088         driver->init();
+00089         return driver;
+00090 }
+00091 
+00092 __declspec(dllexport) uint32 NLSOUND_interfaceVersion ()
+00093 {
+00094         return ISoundDriver::InterfaceVersion;
+00095 }
+00096 
+00097 #elif defined (NL_OS_UNIX)
+00098 
+00099 extern "C"
+00100 {
+00101 ISoundDriver* NLSOUND_createISoundDriverInstance ()
+00102 {
+00103         CSoundDriverAL *driver = new CSoundDriverAL();
+00104         driver->init();
+00105         return driver;
+00106 }
+00107 
+00108 uint32 NLSOUND_interfaceVersion ()
+00109 {
+00110         return ISoundDriver::InterfaceVersion;
+00111 }
+00112 }
+00113 
+00114 #endif // NL_OS_UNIX
+00115 
+00116 
+00117 // The instance of the singleton
+00118 CSoundDriverAL  *CSoundDriverAL::_Instance = NULL;
+00119 
+00120 
+00121 /*
+00122  * Constructor
+00123  */
+00124 CSoundDriverAL::CSoundDriverAL() :
+00125         ISoundDriver(), _NbExpBuffers( 0 ), _NbExpSources( 0 ), _RolloffFactor( 1.0f )
+00126 {
+00127         if ( _Instance == NULL )
+00128         {
+00129                 _Instance = this;
+00130         }
+00131         else
+00132         {
+00133                 nlerror( "Sound driver singleton instanciated twice" );
+00134         }
+00135 }
+00136 
+00137 
+00138 /*
+00139  * Destructor
+00140  */
+00141 CSoundDriverAL::~CSoundDriverAL()
+00142 {
+00143         // Remove the allocated (but not exported) source and buffer names
+00144         alDeleteSources( compactAliveNames( _Sources, alIsSource ), &*_Sources.begin() );
+00145         alDeleteBuffers( compactAliveNames( _Buffers, alIsBuffer ), &*_Buffers.begin() );
+00146 
+00147         // OpenAL exit
+00148         alutExit();
+00149 
+00150         _Instance = NULL;
+00151 }
+00152 
+00153 
+00154 /*
+00155  * Initialization
+00156  */
+00157 bool            CSoundDriverAL::init()
+00158 {
+00159         // OpenAL initialization
+00160         alutInit( NULL, NULL );
+00161 
+00162         // Display version information
+00163         const ALubyte *alversion, *alrenderer, *alvendor, *alext;
+00164         alversion = alGetString( AL_VERSION );
+00165         alrenderer = alGetString( AL_RENDERER );
+00166         alvendor = alGetString( AL_VENDOR );
+00167         alext = alGetString( AL_EXTENSIONS );
+00168         TestALError();
+00169         nlinfo( "Loading OpenAL lib: %s, %s, %s", alversion, alrenderer, alvendor );
+00170         nlinfo( "Listing extensions: %s", alext );
+00171 
+00172 #ifdef EAX_AVAILABLE
+00173     // Set EAX environment if EAX is available
+00174         if ( alIsExtensionPresent((ALubyte *)"EAX") == AL_TRUE ) // or EAX2.0
+00175         {
+00176                 nlinfo( "Initializing EAX" );
+00177             EAXSetProp = (EAXSet)alGetProcAddress((ALubyte*)"EAXSet");
+00178                 EAXGetProp = (EAXGet)alGetProcAddress((ALubyte*)"EAXGet");
+00179                 if ( EAXSetProp != NULL )
+00180                 {
+00181                         unsigned long ulEAXVal;
+00182                         long lGlobalReverb;
+00183                     lGlobalReverb = 0;
+00184                         EAXSetProp( &DSPROPSETID_EAX_ListenerProperties, DSPROPERTY_EAXLISTENER_ROOM, 0, &lGlobalReverb, sizeof(unsigned long) );
+00185                         ulEAXVal = EAX_ENVIRONMENT_GENERIC;
+00186                         EAXSetProp( &DSPROPSETID_EAX_ListenerProperties, DSPROPERTY_EAXLISTENER_ENVIRONMENT, 0, &ulEAXVal, sizeof(unsigned long) );
+00187                 }
+00188         }
+00189         else
+00190 #endif
+00191         {
+00192                 nlinfo( "EAX not available" );
+00193         }
+00194 
+00195         // Choose the I3DL2 model (same as DirectSound3D)
+00196         alDistanceModel( AL_INVERSE_DISTANCE_CLAMPED );
+00197         TestALError();
+00198 
+00199         // Initial buffers and sources allocation
+00200         allocateNewItems( alGenBuffers, alIsBuffer, _Buffers, _NbExpBuffers, INITIAL_BUFFERS );
+00201         allocateNewItems( alGenSources, alIsSource, _Sources, _NbExpSources, INITIAL_SOURCES );
+00202 
+00203         return true;
+00204 }
+00205 
+00206 
+00207 /*
+00208  * Allocate nb new items
+00209  */
+00210 void            CSoundDriverAL::allocateNewItems( TGenFunctionAL algenfunc, TTestFunctionAL altestfunc,
+00211                                                                                           vector<ALuint>& names, uint index, uint nb )
+00212 {
+00213         nlassert( index == names.size() );
+00214         names.resize( index + nb );
+00215         generateItems( algenfunc, altestfunc, nb, &(names[index]) );
+00216 }
+00217 
+00218 
+00219 /*
+00220  * throwGenException
+00221  */
+00222 void ThrowGenException( TGenFunctionAL algenfunc )
+00223 {
+00224         if ( algenfunc == alGenBuffers )
+00225                 throw ESoundDriverGenBuf();
+00226         else if ( algenfunc == alGenSources )
+00227                 throw ESoundDriverGenSrc();
+00228         else
+00229                 nlstop;
+00230 }
+00231 
+00232 /*
+00233  * Generate nb buffers/sources
+00234  */
+00235 void            CSoundDriverAL::generateItems( TGenFunctionAL algenfunc, TTestFunctionAL altestfunc, uint nb, ALuint *array )
+00236 {
+00237         algenfunc( nb, array );
+00238 
+00239         // Error handling
+00240         if ( alGetError() != AL_NO_ERROR )
+00241         {
+00242                 ThrowGenException( algenfunc );
+00243         }
+00244 
+00245         // Check buffers
+00246         uint i;
+00247         for ( i=0; i!=nb; i++ )
+00248         {
+00249                 if ( ! altestfunc( array[i] ) )
+00250                 {
+00251                         ThrowGenException( algenfunc );
+00252                 }
+00253         }
+00254 }
+00255 
+00256 
+00257 /*
+00258  * Create a sound buffer
+00259  */
+00260 IBuffer                 *CSoundDriverAL::createBuffer()
+00261 {
+00262         return new CBufferAL( createItem( alGenBuffers, alIsBuffer, _Buffers, _NbExpBuffers, BUFFER_ALLOC_RATE ) );
+00263 }
+00264 
+00265 
+00266 /*
+00267  * Create a source
+00268  */
+00269 ISource                 *CSoundDriverAL::createSource()
+00270 {
+00271         CSourceAL *sourceal = new CSourceAL( createItem( alGenSources, alIsSource, _Sources, _NbExpSources, SOURCE_ALLOC_RATE ) );
+00272         if ( _RolloffFactor != ROLLOFF_FACTOR_DEFAULT )
+00273         {
+00274                 alSourcef( sourceal->sourceName(), AL_ROLLOFF_FACTOR, _RolloffFactor );
+00275         }
+00276         return sourceal;
+00277 }
+00278 
+00279 
+00280 /*
+00281  * Create a sound buffer or a sound source
+00282  */
+00283 ALuint                  CSoundDriverAL::createItem( TGenFunctionAL algenfunc, TTestFunctionAL altestfunc,
+00284                                                                                         vector<ALuint>& names, uint& index, uint allocrate )
+00285 {
+00286         nlassert( index <= names.size() );
+00287         if ( index == names.size() )
+00288         {
+00289                 // Generate new items
+00290                 uint nbalive = compactAliveNames( names, altestfunc );
+00291                 if ( nbalive == names.size() )
+00292                 {
+00293                         // Extend vector of names
+00294                         allocateNewItems( algenfunc, altestfunc, names, index, allocrate );
+00295                 }
+00296                 else
+00297                 {
+00298                         // Take the room of the deleted names
+00299                         nlassert( nbalive < names.size() );
+00300                         index = nbalive;
+00301                         generateItems( algenfunc, altestfunc, names.size() - nbalive, &(names[nbalive]) );
+00302                 }
+00303         }
+00304 
+00305         // Return the name of the item
+00306         nlassert( index < names.size() );
+00307         ALuint itemname = names[index];
+00308         index++;
+00309         return itemname;
+00310 }
+00311 
+00312 
+00313 /*
+00314  * Remove names of deleted buffers and return the number of valid buffers
+00315  */
+00316 uint                    CSoundDriverAL::compactAliveNames( vector<ALuint>& names, TTestFunctionAL altestfunc )
+00317 {
+00318         vector<ALuint>::iterator iball, ibcompacted;
+00319         for ( iball=names.begin(), ibcompacted=names.begin(); iball!=names.end(); ++iball )
+00320         {
+00321                 // iball is incremented every iteration
+00322                 // ibcompacted is not incremented if a buffer is not valid anymore
+00323                 if ( altestfunc( *iball ) )
+00324                 {
+00325                         *ibcompacted = *iball;
+00326                         ++ibcompacted;
+00327                 }
+00328         }
+00329         nlassert( ibcompacted <= names.end() );
+00330         return ibcompacted - names.begin();
+00331 }
+00332 
+00333 
+00334 /*
+00335  * Remove a buffer
+00336  */
+00337 void                    CSoundDriverAL::removeBuffer( IBuffer *buffer )
+00338 {
+00339         nlassert( buffer != NULL );
+00340         CBufferAL *bufferAL = dynamic_cast<CBufferAL*>(buffer);
+00341         if ( ! deleteItem( bufferAL->bufferName(), alDeleteBuffers, _Buffers ) )
+00342         {
+00343                 nlwarning( "Deleting buffer: name not found" );
+00344         }
+00345 }
+00346 
+00347 
+00348 /*
+00349  * Remove a source
+00350  */
+00351 void                    CSoundDriverAL::removeSource( ISource *source )
+00352 {
+00353         nlassert( source != NULL );
+00354         CSourceAL *sourceAL = dynamic_cast<CSourceAL*>(source);
+00355         if ( ! deleteItem( sourceAL->sourceName(), alDeleteSources, _Sources ) )
+00356         {
+00357                 nlwarning( "Deleting source: name not found" );
+00358         }
+00359 }
+00360 
+00361 
+00362 /*
+00363  * Delete a buffer or a source
+00364  */
+00365 bool                    CSoundDriverAL::deleteItem( ALuint name, TGenFunctionAL aldeletefunc, vector<ALuint>& names )
+00366 {
+00367         vector<ALuint>::iterator ibn = find( names.begin(), names.end(), name );
+00368         if ( ibn == names.end() )
+00369         {
+00370                 return false;
+00371         }
+00372         aldeletefunc( 1, &*ibn );
+00373         *ibn = AL_NONE;
+00374         TestALError();
+00375         return true;
+00376 }
+00377 
+00378 
+00379 /*
+00380  * Create the listener instance
+00381  */
+00382 IListener               *CSoundDriverAL::createListener()
+00383 {
+00384         nlassert( CListenerAL::instance() == NULL );
+00385         return new CListenerAL();
+00386 }
+00387 
+00388 
+00389 /*
+00390  * Apply changes of rolloff factor to all sources
+00391  */
+00392 void                    CSoundDriverAL::applyRolloffFactor( float f )
+00393 {
+00394         _RolloffFactor = f;
+00395         vector<ALuint>::iterator ibn;
+00396         for ( ibn=_Sources.begin(); ibn!=_Sources.end(); ++ibn )
+00397         {
+00398                 alSourcef( *ibn, AL_ROLLOFF_FACTOR, _RolloffFactor );
+00399         }
+00400         TestALError();
+00401 }
+00402 
+00403 
+00404 /*
+00405  * Helper for loadWavFile()
+00406  */
+00407 TSampleFormat ALtoNLSoundFormat( ALenum alformat )
+00408 {
+00409         switch ( alformat )
+00410         {
+00411         case AL_FORMAT_MONO8 : return Mono8;
+00412         case AL_FORMAT_MONO16 : return Mono16;
+00413         case AL_FORMAT_STEREO8 : return Stereo8;
+00414         case AL_FORMAT_STEREO16 : return Stereo16;
+00415         default : nlstop; return Mono8;
+00416         }
+00417 }
+00418 
+00419 
+00420 /*
+00421  * Temp
+00422  */
+00423 bool                    CSoundDriverAL::loadWavFile( IBuffer *destbuffer, const char *filename )
+00424 {
+00425 // Currently, the OpenAL UT headers are different between Windows and Linux versions
+00426 #ifdef NL_OS_WINDOWS
+00427         ALsizei size,freq;
+00428         ALenum format;
+00429         ALvoid *data;
+00430         ALboolean loop;
+00431         alutLoadWAVFile( const_cast<char*>(filename), &format, &data, &size, &freq, &loop ); // last arg in some al.h
+00432 #else
+00433         ALsizei bits;
+00434         ALsizei size,freq;
+00435         ALsizei format;
+00436         ALvoid *data;
+00437         alutLoadWAV( const_cast<char*>(filename), &data, &format, &size, &bits, &freq ); 
+00438 #endif
+00439         if ( data == NULL )
+00440         {
+00441                 return false;
+00442         }
+00443         destbuffer->setFormat( ALtoNLSoundFormat(format), freq );
+00444         destbuffer->fillBuffer( data, size );
+00445 #ifdef NL_OS_WINDOWS
+00446         alutUnloadWAV(format,data,size,freq); // Where is it on Linux ?!?
+00447 #endif
+00448         return true;
+00449 }
+00450 
+00451 
+00452 } // NLSOUND
+
+ + +
                                                                                                                                                                    +
+ + -- cgit v1.2.1