audioengine.h

Go to the documentation of this file.
00001 
00033 #ifndef LL_AUDIOENGINE_H
00034 #define LL_AUDIOENGINE_H
00035 
00036 #include <list>
00037 #include <map>
00038 
00039 #ifndef LL_FMOD
00040 #  define LL_FMOD 1
00041 #endif
00042 
00043 #include "listener.h"
00044 #include "v3math.h"
00045 #include "v3dmath.h"
00046 #include "listener.h"
00047 #include "lltimer.h"
00048 #include "lluuid.h"
00049 #include "llframetimer.h"
00050 #include "llassettype.h"
00051 
00052 const F32 LL_WIND_UPDATE_INTERVAL = 0.1f;
00053 const F32 LL_ROLLOFF_MULTIPLIER_UNDER_WATER = 5.f;                      //  How much sounds are weaker under water
00054 const F32 LL_WIND_UNDERWATER_CENTER_FREQ = 20.f;
00055 
00056 const F32 ATTACHED_OBJECT_TIMEOUT = 5.0f;
00057 const F32 DEFAULT_MIN_DISTANCE = 2.0f;
00058 
00059 #define MAX_CHANNELS 30
00060 #define MAX_BUFFERS 40  // Some extra for preloading, maybe?
00061 
00062 // This define is intended to allow us to switch from os based wav
00063 // file loading to vfs based wav file loading. The problem is that I
00064 // am unconvinced that the LLWaveFile works for loading sounds from
00065 // memory. So, until that is fixed up, changed, whatever, this remains
00066 // undefined.
00067 //#define USE_WAV_VFILE
00068 
00069 class LLVFS;
00070 
00071 class LLAudioSource;
00072 class LLAudioData;
00073 class LLAudioChannel;
00074 class LLAudioBuffer;
00075 
00076 
00077 
00078 //
00079 //  LLAudioEngine definition
00080 //
00081 
00082 class LLAudioEngine 
00083 {
00084 public:
00085         LLAudioEngine();
00086         virtual ~LLAudioEngine();
00087 
00088         // initialization/startup/shutdown
00089         //virtual BOOL init();
00090 
00091         virtual BOOL init(const S32 num_channels, void *userdata);
00092         virtual void shutdown();
00093 
00094         // Used by the mechanics of the engine
00095         //virtual void processQueue(const LLUUID &sound_guid);
00096         virtual void setListener(LLVector3 pos,LLVector3 vel,LLVector3 up,LLVector3 at);
00097         virtual void updateWind(LLVector3 direction, F32 camera_height_above_water) = 0;
00098         virtual void idle(F32 max_decode_time = 0.f);
00099         virtual void updateChannels();
00100 
00101         //
00102         // "End user" functionality
00103         //
00104         virtual BOOL isWindEnabled();
00105         virtual void enableWind(BOOL state_b);
00106 
00107         // Use these for temporarily muting the audio system.
00108         // Does not change buffers, initialization, etc. but
00109         // stops playing new sounds.
00110         virtual void setMuted(BOOL muted);
00111         virtual BOOL getMuted() const { return mMuted; }
00112 
00113         F32 getMasterGain();
00114         void setMasterGain(F32 gain);
00115 
00116         F32 getInternetStreamGain();
00117 
00118         virtual void setDopplerFactor(F32 factor);
00119         virtual F32 getDopplerFactor();
00120         virtual void setDistanceFactor(F32 factor);
00121         virtual F32 getDistanceFactor();
00122         virtual void setRolloffFactor(F32 factor);
00123         virtual F32 getRolloffFactor();
00124         virtual void setMaxWindGain(F32 gain);
00125 
00126 
00127         // Methods actually related to setting up and removing sounds
00128         // Owner ID is the owner of the object making the request
00129         void triggerSound(const LLUUID &sound_id, const LLUUID& owner_id, const F32 gain, const LLVector3d &pos_global = LLVector3d::zero);
00130         BOOL preloadSound(const LLUUID &id);
00131 
00132         void addAudioSource(LLAudioSource *asp);
00133         void cleanupAudioSource(LLAudioSource *asp);
00134 
00135         LLAudioSource *findAudioSource(const LLUUID &source_id);
00136         LLAudioData *getAudioData(const LLUUID &audio_uuid);
00137 
00138 
00139         virtual void startInternetStream(const char* url) = 0;
00140         virtual void stopInternetStream() = 0;
00141         virtual void pauseInternetStream(int pause) = 0;
00142         virtual int isInternetStreamPlaying() = 0;
00143         virtual void getInternetStreamInfo(char* artist, char* title) { artist[0] = 0; title[0] = 0; }
00144         // use a value from 0.0 to 1.0, inclusive
00145         virtual void setInternetStreamGain(F32 vol) { mInternetStreamGain = vol; }
00146         virtual const char* getInternetStreamURL() { return ""; }
00147 
00148         // For debugging usage
00149         virtual LLVector3 getListenerPos();
00150 
00151         LLAudioBuffer *getFreeBuffer(); // Get a free buffer, or flush an existing one if you have to.
00152         LLAudioChannel *getFreeChannel(const F32 priority); // Get a free channel or flush an existing one if your priority is higher
00153         void cleanupBuffer(LLAudioBuffer *bufferp);
00154 
00155         BOOL hasDecodedFile(const LLUUID &uuid);
00156         BOOL hasLocalFile(const LLUUID &uuid);
00157 
00158         BOOL updateBufferForData(LLAudioData *adp, const LLUUID &audio_uuid = LLUUID::null);
00159 
00160 
00161         // Asset callback when we're retrieved a sound from the asset server.
00162         void startNextTransfer();
00163         static void assetCallback(LLVFS *vfs, const LLUUID &uuid, LLAssetType::EType type, void *user_data, S32 result_code, LLExtStat ext_status);
00164 
00165 
00166         friend class LLPipeline; // For debugging
00167 public:
00168         F32 mMaxWindGain; // Hack.  Public to set before fade in?
00169 
00170 protected:
00171         virtual LLAudioBuffer *createBuffer() = 0;
00172         virtual LLAudioChannel *createChannel() = 0;
00173 
00174         virtual void initWind() = 0;
00175         virtual void cleanupWind() = 0;
00176         virtual void setInternalGain(F32 gain) = 0;
00177 
00178         void commitDeferredChanges();
00179 
00180         virtual void allocateListener() = 0;
00181 
00182 
00183         // Internet stream methods
00184         virtual void initInternetStream() {}
00185         virtual void updateInternetStream() {}
00186 
00187 
00188         // listener methods
00189         virtual void setListenerPos(LLVector3 vec);
00190         virtual void setListenerVelocity(LLVector3 vec);
00191         virtual void orientListener(LLVector3 up, LLVector3 at);
00192         virtual void translateListener(LLVector3 vec);
00193 
00194 
00195         F64 mapWindVecToGain(LLVector3 wind_vec);
00196         F64 mapWindVecToPitch(LLVector3 wind_vec);
00197         F64 mapWindVecToPan(LLVector3 wind_vec);
00198 
00199 protected:
00200         LLListener *mListenerp;
00201 
00202         BOOL mMuted;
00203         void* mUserData;
00204 
00205         S32 mLastStatus;
00206         
00207         S32 mNumChannels;
00208         BOOL mEnableWind;
00209 
00210         LLUUID mCurrentTransfer; // Audio file currently being transferred by the system
00211         LLFrameTimer mCurrentTransferTimer;
00212 
00213         // A list of all audio sources that are known to the viewer at this time.
00214         // This is most likely a superset of the ones that we actually have audio
00215         // data for, or are playing back.
00216         typedef std::map<LLUUID, LLAudioSource *> source_map;
00217         typedef std::map<LLUUID, LLAudioData *> data_map;
00218 
00219         source_map mAllSources;
00220         data_map mAllData;
00221 
00222         LLAudioChannel *mChannels[MAX_CHANNELS];
00223 
00224         // Buffers needs to change into a different data structure, as the number of buffers
00225         // that we have active should be limited by RAM usage, not count.
00226         LLAudioBuffer *mBuffers[MAX_BUFFERS];
00227         
00228         F32 mMasterGain;
00229 
00230         // Hack!  Internet streams are treated differently from other sources!
00231         F32 mInternetStreamGain;
00232 
00233         F32 mNextWindUpdate;
00234 
00235         LLFrameTimer mWindUpdateTimer;
00236 
00237 private:
00238         void setDefaults();
00239 };
00240 
00241 
00242 
00243 
00244 //
00245 // Standard audio source.  Can be derived from for special sources, such as those attached to objects.
00246 //
00247 
00248 
00249 class LLAudioSource
00250 {
00251 public:
00252         // owner_id is the id of the agent responsible for making this sound
00253         // play, for example, the owner of the object currently playing it
00254         LLAudioSource(const LLUUID &id, const LLUUID& owner_id, const F32 gain);
00255         virtual ~LLAudioSource();
00256 
00257         virtual void update();                                          // Update this audio source
00258         void updatePriority();
00259 
00260         void preload(const LLUUID &audio_id); // Only used for preloading UI sounds, now.
00261 
00262         void addAudioData(LLAudioData *adp, BOOL set_current = TRUE);
00263 
00264         void setAmbient(const BOOL ambient)                                             { mAmbient = ambient; }
00265         BOOL isAmbient() const                                                                  { return mAmbient; }
00266 
00267         void setLoop(const BOOL loop)                                                   { mLoop = loop; }
00268         BOOL isLoop() const                                                                             { return mLoop; }
00269 
00270         void setSyncMaster(const BOOL master)                                   { mSyncMaster = master; }
00271         BOOL isSyncMaster() const                                                               { return mSyncMaster; }
00272 
00273         void setSyncSlave(const BOOL slave)                                             { mSyncSlave = slave; }
00274         BOOL isSyncSlave() const                                                                { return mSyncSlave; }
00275 
00276         void setQueueSounds(const BOOL queue)                                   { mQueueSounds = queue; }
00277         BOOL isQueueSounds() const                                                              { return mQueueSounds; }
00278 
00279         void setPlayedOnce(const BOOL played_once)                              { mPlayedOnce = played_once; }
00280 
00281         void setPositionGlobal(const LLVector3d &position_global)               { mPositionGlobal = position_global; }
00282         LLVector3d getPositionGlobal() const                                                    { return mPositionGlobal; }
00283         LLVector3 getVelocity() const                                                                   { return mVelocity; }                           
00284         F32 getPriority() const                                                                                 { return mPriority; }
00285 
00286         // Gain should always be clamped between 0 and 1.
00287         F32 getGain() const                                                                                             { return mGain; }
00288         virtual void setGain(const F32 gain)                                                    { mGain = llclamp(gain, 0.f, 1.f); }
00289 
00290         const LLUUID &getID() const             { return mID; }
00291         BOOL isDone();
00292 
00293         LLAudioData *getCurrentData();
00294         LLAudioData *getQueuedData();
00295         LLAudioBuffer *getCurrentBuffer();
00296 
00297         BOOL setupChannel();
00298         BOOL play(const LLUUID &audio_id);      // Start the audio source playing
00299 
00300         BOOL hasPendingPreloads() const;        // Has preloads that haven't been done yet
00301 
00302         friend class LLAudioEngine;
00303         friend class LLAudioChannel;
00304 protected:
00305         void setChannel(LLAudioChannel *channelp);
00306         LLAudioChannel *getChannel() const                                              { return mChannelp; }
00307 
00308 protected:
00309         LLUUID                  mID; // The ID of the source is that of the object if it's attached to an object.
00310         LLUUID                  mOwnerID;       // owner of the object playing the sound
00311         F32                             mPriority;
00312         F32                             mGain;
00313         BOOL                    mAmbient;
00314         BOOL                    mLoop;
00315         BOOL                    mSyncMaster;
00316         BOOL                    mSyncSlave;
00317         BOOL                    mQueueSounds;
00318         BOOL                    mPlayedOnce;
00319         LLVector3d              mPositionGlobal;
00320         LLVector3               mVelocity;
00321 
00322         //LLAudioSource *mSyncMasterp;  // If we're a slave, the source that we're synced to.
00323         LLAudioChannel  *mChannelp;             // If we're currently playing back, this is the channel that we're assigned to.
00324         LLAudioData             *mCurrentDatap;
00325         LLAudioData             *mQueuedDatap;
00326 
00327         typedef std::map<LLUUID, LLAudioData *> data_map;
00328         data_map mPreloadMap;
00329 
00330         LLFrameTimer mAgeTimer;
00331 };
00332 
00333 
00334 
00335 
00336 //
00337 // Generic metadata about a particular piece of audio data.
00338 // The actual data is handled by the derived LLAudioBuffer classes which are
00339 // derived for each audio engine.
00340 //
00341 
00342 
00343 class LLAudioData
00344 {
00345 public:
00346         LLAudioData(const LLUUID &uuid);
00347         BOOL load();
00348 
00349         LLUUID getID() const                            { return mID; }
00350         LLAudioBuffer *getBuffer() const        { return mBufferp; }
00351 
00352         BOOL    hasLocalData() const            { return mHasLocalData; }
00353         BOOL    hasDecodedData() const          { return mHasDecodedData; }
00354         BOOL    hasValidData() const            { return mHasValidData; }
00355 
00356         void    setHasLocalData(const BOOL hld)         { mHasLocalData = hld; }
00357         void    setHasDecodedData(const BOOL hdd)       { mHasDecodedData = hdd; }
00358         void    setHasValidData(const BOOL hvd)         { mHasValidData = hvd; }
00359 
00360         friend class LLAudioEngine; // Severe laziness, bad.
00361 
00362 protected:
00363         LLUUID mID;
00364         LLAudioBuffer *mBufferp;        // If this data is being used by the audio system, a pointer to the buffer will be set here.
00365         BOOL mHasLocalData;
00366         BOOL mHasDecodedData;
00367         BOOL mHasValidData;
00368 };
00369 
00370 
00371 //
00372 // Base class for an audio channel, i.e. a channel which is capable of playing back a sound.
00373 // Management of channels is done generically, methods for actually manipulating the channel
00374 // are derived for each audio engine.
00375 //
00376 
00377 
00378 class LLAudioChannel
00379 {
00380 public:
00381         LLAudioChannel();
00382         virtual ~LLAudioChannel();
00383 
00384         virtual void setSource(LLAudioSource *sourcep);
00385         LLAudioSource *getSource() const                        { return mCurrentSourcep; }
00386 
00387         friend class LLAudioEngine;
00388         friend class LLAudioSource;
00389 protected:
00390         virtual void play() = 0;
00391         virtual void playSynced(LLAudioChannel *channelp) = 0;
00392         virtual void cleanup() = 0;
00393         virtual BOOL isPlaying() = 0;
00394         void setWaiting(const BOOL waiting)                     { mWaiting = waiting; }
00395         BOOL isWaiting() const                                          { return mWaiting; }
00396 
00397         virtual BOOL updateBuffer(); // Check to see if the buffer associated with the source changed, and update if necessary.
00398         virtual void update3DPosition() = 0;
00399         virtual void updateLoop() = 0; // Update your loop/completion status, for use by queueing/syncing.
00400 protected:
00401         LLAudioSource   *mCurrentSourcep;
00402         LLAudioBuffer   *mCurrentBufferp;
00403         BOOL                    mLoopedThisFrame;
00404         BOOL                    mWaiting;       // Waiting for sync.
00405 };
00406 
00407 
00408 
00409 
00410 // Basically an interface class to the engine-specific implementation
00411 // of audio data that's ready for playback.
00412 // Will likely get more complex as we decide to do stuff like real streaming audio.
00413 
00414 
00415 class LLAudioBuffer
00416 {
00417 public:
00418         virtual ~LLAudioBuffer() {};
00419         virtual BOOL loadWAV(const char *filename) = 0;
00420         virtual U32 getLength() = 0;
00421 
00422         friend class LLAudioEngine;
00423         friend class LLAudioChannel;
00424         friend class LLAudioData;
00425 protected:
00426         BOOL mInUse;
00427         LLAudioData *mAudioDatap;
00428         LLFrameTimer mLastUseTimer;
00429 };
00430 
00431 
00432 
00433 extern LLAudioEngine* gAudiop;
00434 
00435 #endif

Generated on Fri May 16 08:31:54 2008 for SecondLife by  doxygen 1.5.5