From 97e6c15e935666c1b295b7508a182d0da4b481f1 Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Wed, 19 Nov 2008 12:51:29 -0600 Subject: VWR-2662: OpenAL support (patch by Tofu Linden) --- linden/indra/cmake/LLAudio.cmake | 2 + linden/indra/llaudio/CMakeLists.txt | 19 ++ linden/indra/llaudio/audioengine.cpp | 323 ++++++++++++++------- linden/indra/llaudio/audioengine.h | 130 +++++---- linden/indra/llaudio/audioengine_fmod.cpp | 271 ++++++------------ linden/indra/llaudio/audioengine_fmod.h | 31 +- linden/indra/llaudio/audioengine_openal.cpp | 422 ++++++++++++++++++++++++++++ linden/indra/llaudio/audioengine_openal.h | 100 +++++++ linden/indra/llaudio/listener_fmod.h | 10 +- linden/indra/llaudio/listener_openal.cpp | 94 +++++++ linden/indra/llaudio/listener_openal.h | 12 +- linden/indra/llaudio/windgen.h | 138 +++++++++ linden/indra/newview/CMakeLists.txt | 7 + linden/indra/newview/llappviewer.cpp | 3 +- linden/indra/newview/llstartup.cpp | 24 +- 15 files changed, 1215 insertions(+), 371 deletions(-) create mode 100644 linden/indra/llaudio/audioengine_openal.cpp create mode 100644 linden/indra/llaudio/audioengine_openal.h create mode 100644 linden/indra/llaudio/listener_openal.cpp create mode 100644 linden/indra/llaudio/windgen.h (limited to 'linden') diff --git a/linden/indra/cmake/LLAudio.cmake b/linden/indra/cmake/LLAudio.cmake index 7b9f254..893aa68 100644 --- a/linden/indra/cmake/LLAudio.cmake +++ b/linden/indra/cmake/LLAudio.cmake @@ -1,6 +1,7 @@ # -*- cmake -*- include(Audio) +include(OPENAL) set(LLAUDIO_INCLUDE_DIRS ${LIBS_OPEN_DIR}/llaudio @@ -12,4 +13,5 @@ set(LLAUDIO_LIBRARIES ${VORBISFILE_LIBRARIES} ${VORBIS_LIBRARIES} ${OGG_LIBRARIES} + ${OPENAL_LIBRARIES} ) diff --git a/linden/indra/llaudio/CMakeLists.txt b/linden/indra/llaudio/CMakeLists.txt index b662023..aa15a9d 100644 --- a/linden/indra/llaudio/CMakeLists.txt +++ b/linden/indra/llaudio/CMakeLists.txt @@ -9,6 +9,7 @@ include(LLCommon) include(LLMath) include(LLMessage) include(LLVFS) +include(LLMedia) include_directories( ${FMOD_INCLUDE_DIR} @@ -20,6 +21,10 @@ include_directories( ${VORBISENC_INCLUDE_DIRS} ${VORBISFILE_INCLUDE_DIRS} ${VORBIS_INCLUDE_DIRS} + ${OPENAL_LIB_INCLUDE_DIRS} + ${FREEAULT_LIB_INCLUDE_DIRS} + ${LLMEDIA_INCLUDE_DIRS} + ${GSTREAMER_INCLUDE_DIRS} ) set(llaudio_SOURCE_FILES @@ -38,6 +43,7 @@ set(llaudio_HEADER_FILES llaudiodecodemgr.h vorbisdecode.h vorbisencode.h + windgen.h ) if (FMOD) @@ -59,6 +65,19 @@ if (FMOD) endif (LINUX) endif (FMOD) +if (OPENAL) + list(APPEND llaudio_SOURCE_FILES + audioengine_openal.cpp + listener_openal.cpp + ) + + list(APPEND llaudio_HEADER_FILES + audioengine_openal.h + listener_openal.h + ) + +endif (OPENAL) + set_source_files_properties(${llaudio_HEADER_FILES} PROPERTIES HEADER_FILE_ONLY TRUE) diff --git a/linden/indra/llaudio/audioengine.cpp b/linden/indra/llaudio/audioengine.cpp index 5dd5b28..0a450e9 100644 --- a/linden/indra/llaudio/audioengine.cpp +++ b/linden/indra/llaudio/audioengine.cpp @@ -44,14 +44,13 @@ #include "llaudiodecodemgr.h" #include "llassetstorage.h" +#include "llmediamanager.h" + // necessary for grabbing sounds from sim (implemented in viewer) extern void request_sound(const LLUUID &sound_guid); LLAudioEngine* gAudiop = NULL; -// Maximum amount of time we wait for a transfer to complete before starting -// off another one. -const F32 MAX_CURRENT_TRANSFER_TIME = 60.f; // // LLAudioEngine implementation @@ -75,13 +74,13 @@ void LLAudioEngine::setDefaults() mListenerp = NULL; - mMuted = FALSE; + mMuted = false; mUserData = NULL; mLastStatus = 0; mNumChannels = 0; - mEnableWind = FALSE; + mEnableWind = false; S32 i; for (i = 0; i < MAX_CHANNELS; i++) @@ -91,15 +90,18 @@ void LLAudioEngine::setDefaults() for (i = 0; i < MAX_BUFFERS; i++) { mBuffers[i] = NULL; - } + } mMasterGain = 1.f; mInternetStreamGain = 0.125f; mNextWindUpdate = 0.f; + + mInternetStreamMedia = NULL; + mInternetStreamURL.clear(); } -BOOL LLAudioEngine::init(const S32 num_channels, void* userdata) +bool LLAudioEngine::init(const S32 num_channels, void* userdata) { setDefaults(); @@ -111,7 +113,9 @@ BOOL LLAudioEngine::init(const S32 num_channels, void* userdata) // Initialize the decode manager gAudioDecodeMgrp = new LLAudioDecodeMgr; - return TRUE; + llinfos << "LLAudioEngine::init() AudioEngine successfully initialized" << llendl; + + return true; } @@ -141,22 +145,146 @@ void LLAudioEngine::shutdown() S32 i; for (i = 0; i < MAX_CHANNELS; i++) { - if (mChannels[i]) - { - delete mChannels[i]; - mChannels[i] = NULL; - } + delete mChannels[i]; + mChannels[i] = NULL; } // Clean up buffers for (i = 0; i < MAX_BUFFERS; i++) { - if (mBuffers[i]) + delete mBuffers[i]; + mBuffers[i] = NULL; + } + + delete mInternetStreamMedia; + mInternetStreamMedia = NULL; + mInternetStreamURL.clear(); +} + + +// virtual +void LLAudioEngine::startInternetStream(const std::string& url) +{ + llinfos << "entered startInternetStream()" << llendl; + + if (!mInternetStreamMedia) + { + LLMediaManager* mgr = LLMediaManager::getInstance(); + if (mgr) { - delete mBuffers[i]; - mBuffers[i] = NULL; + mInternetStreamMedia = mgr->createSourceFromMimeType(LLURI(url).scheme(), "audio/mpeg"); // assumes that whatever media implementation supports mp3 also supports vorbis. + llinfos << "mInternetStreamMedia is now " << mInternetStreamMedia << llendl; + } + } + + if(!mInternetStreamMedia) + return; + + if (!url.empty()) { + llinfos << "Starting internet stream: " << url << llendl; + mInternetStreamURL = url; + mInternetStreamMedia->navigateTo ( url ); + llinfos << "Playing....." << llendl; + mInternetStreamMedia->addCommand(LLMediaBase::COMMAND_START); + mInternetStreamMedia->updateMedia(); + } else { + llinfos << "setting stream to NULL"<< llendl; + mInternetStreamURL.clear(); + mInternetStreamMedia->addCommand(LLMediaBase::COMMAND_STOP); + mInternetStreamMedia->updateMedia(); + } + //#endif +} + +// virtual +void LLAudioEngine::stopInternetStream() +{ + llinfos << "entered stopInternetStream()" << llendl; + + if(mInternetStreamMedia) + { + if( ! mInternetStreamMedia->addCommand(LLMediaBase::COMMAND_STOP)){ + llinfos << "attempting to stop stream failed!" << llendl; } + mInternetStreamMedia->updateMedia(); } + + mInternetStreamURL.clear(); +} + +// virtual +void LLAudioEngine::pauseInternetStream(int pause) +{ + llinfos << "entered pauseInternetStream()" << llendl; + + if(!mInternetStreamMedia) + return; + + if(pause) + { + if(! mInternetStreamMedia->addCommand(LLMediaBase::COMMAND_PAUSE)) + { + llinfos << "attempting to pause stream failed!" << llendl; + } + } else { + if(! mInternetStreamMedia->addCommand(LLMediaBase::COMMAND_START)) + { + llinfos << "attempting to unpause stream failed!" << llendl; + } + } + mInternetStreamMedia->updateMedia(); +} + +// virtual +void LLAudioEngine::updateInternetStream() +{ + if (mInternetStreamMedia) + mInternetStreamMedia->updateMedia(); +} + +// virtual +int LLAudioEngine::isInternetStreamPlaying() +{ + if (!mInternetStreamMedia) + return 0; + + if (mInternetStreamMedia->getStatus() == LLMediaBase::STATUS_STARTED) + { + return 1; // Active and playing + } + + if (mInternetStreamMedia->getStatus() == LLMediaBase::STATUS_PAUSED) + { + return 2; // paused + } + + return 0; // Stopped +} + +// virtual +void LLAudioEngine::getInternetStreamInfo(char* artist, char* title) +{ + artist[0] = 0; + title[0] = 0; +} + +// virtual +void LLAudioEngine::setInternetStreamGain(F32 vol) +{ + mInternetStreamGain = vol; + + if(!mInternetStreamMedia) + return; + + vol = llclamp(vol, 0.f, 1.f); + mInternetStreamMedia->setVolume(vol); + mInternetStreamMedia->updateMedia(); +} + +// virtual +const std::string& LLAudioEngine::getInternetStreamURL() +{ + return mInternetStreamURL; } @@ -200,7 +328,7 @@ void LLAudioEngine::idle(F32 max_decode_time) { if (mBuffers[i]) { - mBuffers[i]->mInUse = FALSE; + mBuffers[i]->mInUse = false; } } @@ -252,11 +380,11 @@ void LLAudioEngine::idle(F32 max_decode_time) { // A sync slave, it doesn't start playing until it's synced up with the master. // Flag this channel as waiting for sync, and return true. - channelp->setWaiting(TRUE); + channelp->setWaiting(true); } else { - channelp->setWaiting(FALSE); + channelp->setWaiting(false); channelp->play(); } } @@ -396,7 +524,7 @@ void LLAudioEngine::idle(F32 max_decode_time) if (sync_masterp->getChannel()) { channelp->playSynced(master_channelp); - channelp->setWaiting(FALSE); + channelp->setWaiting(false); } } } @@ -426,7 +554,7 @@ void LLAudioEngine::idle(F32 max_decode_time) { if (mChannels[i]) { - mChannels[i]->mLoopedThisFrame = FALSE; + mChannels[i]->mLoopedThisFrame = false; } } @@ -437,13 +565,17 @@ void LLAudioEngine::idle(F32 max_decode_time) // missed picking it up in all the places that can add // or request new data. startNextTransfer(); + + updateInternetStream(); } -BOOL LLAudioEngine::updateBufferForData(LLAudioData *adp, const LLUUID &audio_uuid) + + +bool LLAudioEngine::updateBufferForData(LLAudioData *adp, const LLUUID &audio_uuid) { if (!adp) { - return FALSE; + return false; } // Update the audio buffer first - load a sound if we have it. @@ -466,14 +598,14 @@ BOOL LLAudioEngine::updateBufferForData(LLAudioData *adp, const LLUUID &audio_uu } else { - return FALSE; + return false; } } - return TRUE; + return true; } -void LLAudioEngine::enableWind(BOOL enable) +void LLAudioEngine::enableWind(bool enable) { if (enable && (!mEnableWind)) { @@ -601,7 +733,7 @@ void LLAudioEngine::cleanupBuffer(LLAudioBuffer *bufferp) } -BOOL LLAudioEngine::preloadSound(const LLUUID &uuid) +bool LLAudioEngine::preloadSound(const LLUUID &uuid) { gAudiop->getAudioData(uuid); // We don't care about the return value, this is just to make sure // that we have an entry, which will mean that the audio engine knows about this @@ -609,23 +741,23 @@ BOOL LLAudioEngine::preloadSound(const LLUUID &uuid) if (gAudioDecodeMgrp->addDecodeRequest(uuid)) { // This means that we do have a local copy, and we're working on decoding it. - return TRUE; + return true; } // At some point we need to have the audio/asset system check the static VFS // before it goes off and fetches stuff from the server. //llwarns << "Used internal preload for non-local sound" << llendl; - return FALSE; + return false; } -BOOL LLAudioEngine::isWindEnabled() +bool LLAudioEngine::isWindEnabled() { return mEnableWind; } -void LLAudioEngine::setMuted(BOOL muted) +void LLAudioEngine::setMuted(bool muted) { mMuted = muted; enableWind(!mMuted); @@ -735,7 +867,7 @@ void LLAudioEngine::triggerSound(const LLUUID &audio_uuid, const LLUUID& owner_i gAudiop->addAudioSource(asp); if (pos_global.isExactlyZero()) { - asp->setAmbient(TRUE); + asp->setAmbient(true); } else { @@ -914,7 +1046,7 @@ void LLAudioEngine::cleanupAudioSource(LLAudioSource *asp) } -BOOL LLAudioEngine::hasDecodedFile(const LLUUID &uuid) +bool LLAudioEngine::hasDecodedFile(const LLUUID &uuid) { std::string uuid_str; uuid.toString(uuid_str); @@ -925,16 +1057,16 @@ BOOL LLAudioEngine::hasDecodedFile(const LLUUID &uuid) if (gDirUtilp->fileExists(wav_path)) { - return TRUE; + return true; } else { - return FALSE; + return false; } } -BOOL LLAudioEngine::hasLocalFile(const LLUUID &uuid) +bool LLAudioEngine::hasLocalFile(const LLUUID &uuid) { // See if it's in the VFS. return gVFS->getExists(uuid, LLAssetType::AT_SOUND); @@ -1150,9 +1282,9 @@ void LLAudioEngine::assetCallback(LLVFS *vfs, const LLUUID &uuid, LLAssetType::E LLAudioData *adp = gAudiop->getAudioData(uuid); if (adp) { - adp->setHasValidData(FALSE); - adp->setHasLocalData(FALSE); - adp->setHasDecodedData(FALSE); + adp->setHasValidData(false); + adp->setHasLocalData(false); + adp->setHasDecodedData(false); } } else @@ -1165,8 +1297,8 @@ void LLAudioEngine::assetCallback(LLVFS *vfs, const LLUUID &uuid, LLAssetType::E } else { - adp->setHasValidData(TRUE); - adp->setHasLocalData(TRUE); + adp->setHasValidData(true); + adp->setHasLocalData(true); gAudioDecodeMgrp->addDecodeRequest(uuid); } } @@ -1185,12 +1317,12 @@ LLAudioSource::LLAudioSource(const LLUUID& id, const LLUUID& owner_id, const F32 mOwnerID(owner_id), mPriority(0.f), mGain(gain), - mAmbient(FALSE), - mLoop(FALSE), - mSyncMaster(FALSE), - mSyncSlave(FALSE), - mQueueSounds(FALSE), - mPlayedOnce(FALSE), + mAmbient(false), + mLoop(false), + mSyncMaster(false), + mSyncSlave(false), + mQueueSounds(false), + mPlayedOnce(false), mChannelp(NULL), mCurrentDatap(NULL), mQueuedDatap(NULL) @@ -1254,7 +1386,7 @@ void LLAudioSource::updatePriority() } } -BOOL LLAudioSource::setupChannel() +bool LLAudioSource::setupChannel() { LLAudioData *adp = getCurrentData(); @@ -1262,7 +1394,7 @@ BOOL LLAudioSource::setupChannel() { // We're not ready to play back the sound yet, so don't try and allocate a channel for it. //llwarns << "Aborting, no buffer" << llendl; - return FALSE; + return false; } @@ -1280,15 +1412,15 @@ BOOL LLAudioSource::setupChannel() // Now we have to reprioritize. // For now, just don't play the sound. //llwarns << "Aborting, no free channels" << llendl; - return FALSE; + return false; } mChannelp->setSource(this); - return TRUE; + return true; } -BOOL LLAudioSource::play(const LLUUID &audio_uuid) +bool LLAudioSource::play(const LLUUID &audio_uuid) { if (audio_uuid.isNull()) { @@ -1296,7 +1428,7 @@ BOOL LLAudioSource::play(const LLUUID &audio_uuid) { getChannel()->setSource(NULL); setChannel(NULL); - addAudioData(NULL, TRUE); + addAudioData(NULL, true); } } // Reset our age timeout if someone attempts to play the source. @@ -1304,7 +1436,7 @@ BOOL LLAudioSource::play(const LLUUID &audio_uuid) LLAudioData *adp = gAudiop->getAudioData(audio_uuid); - BOOL has_buffer = gAudiop->updateBufferForData(adp, audio_uuid); + bool has_buffer = gAudiop->updateBufferForData(adp, audio_uuid); addAudioData(adp); @@ -1312,47 +1444,48 @@ BOOL LLAudioSource::play(const LLUUID &audio_uuid) if (!has_buffer) { // Don't bother trying to set up a channel or anything, we don't have an audio buffer. - return FALSE; + return false; } if (!setupChannel()) { - return FALSE; + return false; } if (isSyncSlave()) { // A sync slave, it doesn't start playing until it's synced up with the master. // Flag this channel as waiting for sync, and return true. - getChannel()->setWaiting(TRUE); - return TRUE; + getChannel()->setWaiting(true); + return true; } getChannel()->play(); - return TRUE; + return true; } -BOOL LLAudioSource::isDone() +bool LLAudioSource::isDone() { const F32 MAX_AGE = 60.f; const F32 MAX_UNPLAYED_AGE = 15.f; + if (isLoop()) { // Looped sources never die on their own. - return FALSE; + return false; } if (hasPendingPreloads()) { - return FALSE; + return false; } if (mQueuedDatap) { // Don't kill this sound if we've got something queued up to play. - return FALSE; + return false; } F32 elapsed = mAgeTimer.getElapsedTimeF32(); @@ -1365,11 +1498,11 @@ BOOL LLAudioSource::isDone() // We don't have a channel assigned, and it's been // over 5 seconds since we tried to play it. Don't bother. //llinfos << "No channel assigned, source is done" << llendl; - return TRUE; + return true; } else { - return FALSE; + return false; } } @@ -1377,27 +1510,27 @@ BOOL LLAudioSource::isDone() { if (elapsed > MAX_AGE) { - // Arbitarily cut off non-looped sounds when they're 20 seconds old. - return TRUE; + // Arbitarily cut off non-looped sounds when they're old. + return true; } else { // Sound is still playing and we haven't timed out, don't kill it. - return FALSE; + return false; } } if ((elapsed > MAX_UNPLAYED_AGE) || mPlayedOnce) { // The sound isn't playing back after 5 seconds or we're already done playing it, kill it. - return TRUE; + return true; } - return FALSE; + return false; } -void LLAudioSource::addAudioData(LLAudioData *adp, const BOOL set_current) +void LLAudioSource::addAudioData(LLAudioData *adp, const bool set_current) { // Only handle a single piece of audio data associated with a source right now, // until I implement prefetch. @@ -1465,7 +1598,7 @@ void LLAudioSource::addAudioData(LLAudioData *adp, const BOOL set_current) } -BOOL LLAudioSource::hasPendingPreloads() const +bool LLAudioSource::hasPendingPreloads() const { // Check to see if we've got any preloads on deck for this source data_map::const_iterator iter; @@ -1475,11 +1608,11 @@ BOOL LLAudioSource::hasPendingPreloads() const if (!adp->hasDecodedData()) { // This source is still waiting for a preload - return TRUE; + return true; } } - return FALSE; + return false; } @@ -1514,8 +1647,8 @@ LLAudioBuffer *LLAudioSource::getCurrentBuffer() LLAudioChannel::LLAudioChannel() : mCurrentSourcep(NULL), mCurrentBufferp(NULL), - mLoopedThisFrame(FALSE), - mWaiting(FALSE) + mLoopedThisFrame(false), + mWaiting(false) { } @@ -1542,7 +1675,7 @@ void LLAudioChannel::setSource(LLAudioSource *sourcep) //llinfos << "Clearing source for channel" << llendl; cleanup(); mCurrentSourcep = NULL; - mWaiting = FALSE; + mWaiting = false; return; } @@ -1558,13 +1691,13 @@ void LLAudioChannel::setSource(LLAudioSource *sourcep) } -BOOL LLAudioChannel::updateBuffer() +bool LLAudioChannel::updateBuffer() { if (!mCurrentSourcep) { // This channel isn't associated with any source, nothing // to be updated - return FALSE; + return false; } LLAudioBuffer *bufferp = mCurrentSourcep->getCurrentBuffer(); @@ -1574,9 +1707,9 @@ BOOL LLAudioChannel::updateBuffer() { // The source hasn't changed what buffer it's playing bufferp->mLastUseTimer.reset(); - bufferp->mInUse = TRUE; + bufferp->mInUse = true; } - return FALSE; + return false; } // @@ -1589,16 +1722,16 @@ BOOL LLAudioChannel::updateBuffer() if (bufferp) { bufferp->mLastUseTimer.reset(); - bufferp->mInUse = TRUE; + bufferp->mInUse = true; } if (!mCurrentBufferp) { // There's no new buffer to be played, so we just abort. - return FALSE; + return false; } - return TRUE; + return true; } @@ -1612,9 +1745,9 @@ BOOL LLAudioChannel::updateBuffer() LLAudioData::LLAudioData(const LLUUID &uuid) : mID(uuid), mBufferp(NULL), - mHasLocalData(FALSE), - mHasDecodedData(FALSE), - mHasValidData(TRUE) + mHasLocalData(false), + mHasDecodedData(false), + mHasValidData(true) { if (uuid.isNull()) { @@ -1625,24 +1758,24 @@ LLAudioData::LLAudioData(const LLUUID &uuid) : if (gAudiop && gAudiop->hasDecodedFile(uuid)) { // Already have a decoded version, don't need to decode it. - mHasLocalData = TRUE; - mHasDecodedData = TRUE; + mHasLocalData = true; + mHasDecodedData = true; } else if (gAssetStorage && gAssetStorage->hasLocalAsset(uuid, LLAssetType::AT_SOUND)) { - mHasLocalData = TRUE; + mHasLocalData = true; } } -BOOL LLAudioData::load() +bool LLAudioData::load() { // For now, just assume we're going to use one buffer per audiodata. if (mBufferp) { // We already have this sound in a buffer, don't do anything. llinfos << "Already have a buffer for this sound, don't bother loading!" << llendl; - return TRUE; + return true; } mBufferp = gAudiop->getFreeBuffer(); @@ -1650,7 +1783,7 @@ BOOL LLAudioData::load() { // No free buffers, abort. llinfos << "Not able to allocate a new audio buffer, aborting." << llendl; - return FALSE; + return false; } std::string uuid_str; @@ -1664,10 +1797,10 @@ BOOL LLAudioData::load() gAudiop->cleanupBuffer(mBufferp); mBufferp = NULL; - return FALSE; + return false; } mBufferp->mAudioDatap = this; - return TRUE; + return true; } diff --git a/linden/indra/llaudio/audioengine.h b/linden/indra/llaudio/audioengine.h index e38413f..94134f5 100644 --- a/linden/indra/llaudio/audioengine.h +++ b/linden/indra/llaudio/audioengine.h @@ -45,6 +45,8 @@ #include "llframetimer.h" #include "llassettype.h" +class LLMediaBase; + const F32 LL_WIND_UPDATE_INTERVAL = 0.1f; const F32 LL_ROLLOFF_MULTIPLIER_UNDER_WATER = 5.f; // How much sounds are weaker under water const F32 LL_WIND_UNDERWATER_CENTER_FREQ = 20.f; @@ -82,9 +84,7 @@ public: virtual ~LLAudioEngine(); // initialization/startup/shutdown - //virtual BOOL init(); - - virtual BOOL init(const S32 num_channels, void *userdata); + virtual bool init(const S32 num_channels, void *userdata); virtual void shutdown(); // Used by the mechanics of the engine @@ -97,14 +97,14 @@ public: // // "End user" functionality // - virtual BOOL isWindEnabled(); - virtual void enableWind(BOOL state_b); + virtual bool isWindEnabled(); + virtual void enableWind(bool state_b); // Use these for temporarily muting the audio system. // Does not change buffers, initialization, etc. but // stops playing new sounds. - virtual void setMuted(BOOL muted); - virtual BOOL getMuted() const { return mMuted; } + virtual void setMuted(bool muted); + virtual bool getMuted() const { return mMuted; } F32 getMasterGain(); void setMasterGain(F32 gain); @@ -123,7 +123,7 @@ public: // Methods actually related to setting up and removing sounds // Owner ID is the owner of the object making the request void triggerSound(const LLUUID &sound_id, const LLUUID& owner_id, const F32 gain, const LLVector3d &pos_global = LLVector3d::zero); - BOOL preloadSound(const LLUUID &id); + bool preloadSound(const LLUUID &id); void addAudioSource(LLAudioSource *asp); void cleanupAudioSource(LLAudioSource *asp); @@ -132,14 +132,16 @@ public: LLAudioData *getAudioData(const LLUUID &audio_uuid); - virtual void startInternetStream(const std::string& url) = 0; - virtual void stopInternetStream() = 0; - virtual void pauseInternetStream(int pause) = 0; - virtual int isInternetStreamPlaying() = 0; - virtual void getInternetStreamInfo(char* artist, char* title) { artist[0] = 0; title[0] = 0; } + // Internet stream methods + virtual void startInternetStream(const std::string& url); + virtual void stopInternetStream(); + virtual void pauseInternetStream(int pause); + virtual void updateInternetStream(); + virtual int isInternetStreamPlaying(); + virtual void getInternetStreamInfo(char* artist, char* title); // use a value from 0.0 to 1.0, inclusive - virtual void setInternetStreamGain(F32 vol) { mInternetStreamGain = vol; } - virtual const std::string& getInternetStreamURL() { return LLStringUtil::null; } + virtual void setInternetStreamGain(F32 vol); + virtual const std::string& getInternetStreamURL(); // For debugging usage virtual LLVector3 getListenerPos(); @@ -148,17 +150,16 @@ public: LLAudioChannel *getFreeChannel(const F32 priority); // Get a free channel or flush an existing one if your priority is higher void cleanupBuffer(LLAudioBuffer *bufferp); - BOOL hasDecodedFile(const LLUUID &uuid); - BOOL hasLocalFile(const LLUUID &uuid); + bool hasDecodedFile(const LLUUID &uuid); + bool hasLocalFile(const LLUUID &uuid); - BOOL updateBufferForData(LLAudioData *adp, const LLUUID &audio_uuid = LLUUID::null); + bool updateBufferForData(LLAudioData *adp, const LLUUID &audio_uuid = LLUUID::null); // Asset callback when we're retrieved a sound from the asset server. void startNextTransfer(); static void assetCallback(LLVFS *vfs, const LLUUID &uuid, LLAssetType::EType type, void *user_data, S32 result_code, LLExtStat ext_status); - friend class LLPipeline; // For debugging public: F32 mMaxWindGain; // Hack. Public to set before fade in? @@ -176,11 +177,6 @@ protected: virtual void allocateListener() = 0; - // Internet stream methods - virtual void initInternetStream() {} - virtual void updateInternetStream() {} - - // listener methods virtual void setListenerPos(LLVector3 vec); virtual void setListenerVelocity(LLVector3 vec); @@ -195,13 +191,13 @@ protected: protected: LLListener *mListenerp; - BOOL mMuted; + bool mMuted; void* mUserData; S32 mLastStatus; S32 mNumChannels; - BOOL mEnableWind; + bool mEnableWind; LLUUID mCurrentTransfer; // Audio file currently being transferred by the system LLFrameTimer mCurrentTransferTimer; @@ -225,6 +221,7 @@ protected: // Hack! Internet streams are treated differently from other sources! F32 mInternetStreamGain; + std::string mInternetStreamURL; F32 mNextWindUpdate; @@ -232,6 +229,7 @@ protected: private: void setDefaults(); + LLMediaBase *mInternetStreamMedia; }; @@ -255,24 +253,24 @@ public: void preload(const LLUUID &audio_id); // Only used for preloading UI sounds, now. - void addAudioData(LLAudioData *adp, BOOL set_current = TRUE); + void addAudioData(LLAudioData *adp, bool set_current = TRUE); - void setAmbient(const BOOL ambient) { mAmbient = ambient; } - BOOL isAmbient() const { return mAmbient; } + void setAmbient(const bool ambient) { mAmbient = ambient; } + bool isAmbient() const { return mAmbient; } - void setLoop(const BOOL loop) { mLoop = loop; } - BOOL isLoop() const { return mLoop; } + void setLoop(const bool loop) { mLoop = loop; } + bool isLoop() const { return mLoop; } - void setSyncMaster(const BOOL master) { mSyncMaster = master; } - BOOL isSyncMaster() const { return mSyncMaster; } + void setSyncMaster(const bool master) { mSyncMaster = master; } + bool isSyncMaster() const { return mSyncMaster; } - void setSyncSlave(const BOOL slave) { mSyncSlave = slave; } - BOOL isSyncSlave() const { return mSyncSlave; } + void setSyncSlave(const bool slave) { mSyncSlave = slave; } + bool isSyncSlave() const { return mSyncSlave; } - void setQueueSounds(const BOOL queue) { mQueueSounds = queue; } - BOOL isQueueSounds() const { return mQueueSounds; } + void setQueueSounds(const bool queue) { mQueueSounds = queue; } + bool isQueueSounds() const { return mQueueSounds; } - void setPlayedOnce(const BOOL played_once) { mPlayedOnce = played_once; } + void setPlayedOnce(const bool played_once) { mPlayedOnce = played_once; } void setPositionGlobal(const LLVector3d &position_global) { mPositionGlobal = position_global; } LLVector3d getPositionGlobal() const { return mPositionGlobal; } @@ -284,16 +282,16 @@ public: virtual void setGain(const F32 gain) { mGain = llclamp(gain, 0.f, 1.f); } const LLUUID &getID() const { return mID; } - BOOL isDone(); + bool isDone(); LLAudioData *getCurrentData(); LLAudioData *getQueuedData(); LLAudioBuffer *getCurrentBuffer(); - BOOL setupChannel(); - BOOL play(const LLUUID &audio_id); // Start the audio source playing + bool setupChannel(); + bool play(const LLUUID &audio_id); // Start the audio source playing - BOOL hasPendingPreloads() const; // Has preloads that haven't been done yet + bool hasPendingPreloads() const; // Has preloads that haven't been done yet friend class LLAudioEngine; friend class LLAudioChannel; @@ -306,12 +304,12 @@ protected: LLUUID mOwnerID; // owner of the object playing the sound F32 mPriority; F32 mGain; - BOOL mAmbient; - BOOL mLoop; - BOOL mSyncMaster; - BOOL mSyncSlave; - BOOL mQueueSounds; - BOOL mPlayedOnce; + bool mAmbient; + bool mLoop; + bool mSyncMaster; + bool mSyncSlave; + bool mQueueSounds; + bool mPlayedOnce; LLVector3d mPositionGlobal; LLVector3 mVelocity; @@ -340,27 +338,27 @@ class LLAudioData { public: LLAudioData(const LLUUID &uuid); - BOOL load(); + bool load(); LLUUID getID() const { return mID; } LLAudioBuffer *getBuffer() const { return mBufferp; } - BOOL hasLocalData() const { return mHasLocalData; } - BOOL hasDecodedData() const { return mHasDecodedData; } - BOOL hasValidData() const { return mHasValidData; } + bool hasLocalData() const { return mHasLocalData; } + bool hasDecodedData() const { return mHasDecodedData; } + bool hasValidData() const { return mHasValidData; } - void setHasLocalData(const BOOL hld) { mHasLocalData = hld; } - void setHasDecodedData(const BOOL hdd) { mHasDecodedData = hdd; } - void setHasValidData(const BOOL hvd) { mHasValidData = hvd; } + void setHasLocalData(const bool hld) { mHasLocalData = hld; } + void setHasDecodedData(const bool hdd) { mHasDecodedData = hdd; } + void setHasValidData(const bool hvd) { mHasValidData = hvd; } friend class LLAudioEngine; // Severe laziness, bad. protected: LLUUID mID; LLAudioBuffer *mBufferp; // If this data is being used by the audio system, a pointer to the buffer will be set here. - BOOL mHasLocalData; - BOOL mHasDecodedData; - BOOL mHasValidData; + bool mHasLocalData; + bool mHasDecodedData; + bool mHasValidData; }; @@ -386,18 +384,18 @@ protected: virtual void play() = 0; virtual void playSynced(LLAudioChannel *channelp) = 0; virtual void cleanup() = 0; - virtual BOOL isPlaying() = 0; - void setWaiting(const BOOL waiting) { mWaiting = waiting; } - BOOL isWaiting() const { return mWaiting; } + virtual bool isPlaying() = 0; + void setWaiting(const bool waiting) { mWaiting = waiting; } + bool isWaiting() const { return mWaiting; } - virtual BOOL updateBuffer(); // Check to see if the buffer associated with the source changed, and update if necessary. + virtual bool updateBuffer(); // Check to see if the buffer associated with the source changed, and update if necessary. virtual void update3DPosition() = 0; virtual void updateLoop() = 0; // Update your loop/completion status, for use by queueing/syncing. protected: LLAudioSource *mCurrentSourcep; LLAudioBuffer *mCurrentBufferp; - BOOL mLoopedThisFrame; - BOOL mWaiting; // Waiting for sync. + bool mLoopedThisFrame; + bool mWaiting; // Waiting for sync. }; @@ -412,14 +410,14 @@ class LLAudioBuffer { public: virtual ~LLAudioBuffer() {}; - virtual BOOL loadWAV(const std::string& filename) = 0; + virtual bool loadWAV(const std::string& filename) = 0; virtual U32 getLength() = 0; friend class LLAudioEngine; friend class LLAudioChannel; friend class LLAudioData; protected: - BOOL mInUse; + bool mInUse; LLAudioData *mAudioDatap; LLFrameTimer mLastUseTimer; }; diff --git a/linden/indra/llaudio/audioengine_fmod.cpp b/linden/indra/llaudio/audioengine_fmod.cpp index 16d820c..354ef95 100644 --- a/linden/indra/llaudio/audioengine_fmod.cpp +++ b/linden/indra/llaudio/audioengine_fmod.cpp @@ -1,7 +1,6 @@ /** * @file audioengine_fmod.cpp - * @brief Implementation of LLAudioEngine class abstracting the audio - * support as a FMOD 3D implementation + * @brief Implementation of LLAudioEngine class abstracting the audio support as a FMOD 3D implementation * * $LicenseInfo:firstyear=2002&license=viewergpl$ * @@ -46,27 +45,12 @@ #include "sound_ids.h" +extern "C" { + void * F_CALLBACKAPI windCallback(void *originalbuffer, void *newbuffer, int length, void* userdata); +} -void * F_CALLBACKAPI windCallback(void *originalbuffer, void *newbuffer, int length, void* userdata); FSOUND_DSPUNIT *gWindDSP = NULL; -// These globals for the wind filter. Blech! -F64 gbuf0 = 0.0; -F64 gbuf1 = 0.0; -F64 gbuf2 = 0.0; -F64 gbuf3 = 0.0; -F64 gbuf4 = 0.0; -F64 gbuf5 = 0.0; -F64 gY0 = 0.0; -F64 gY1 = 0.0; - -F32 gTargetGain = 0.f; -F32 gCurrentGain = 0.f; -F32 gTargetFreq = 100.f; -F32 gCurrentFreq = 100.f; -F32 gTargetPanGainR = 0.5f; -F32 gCurrentPanGainR = 0.5f; - // Safe strcpy #if 0 //(unused) //LL_WINDOWS || LL_LINUX @@ -94,9 +78,10 @@ static size_t strlcpy( char* dest, const char* src, size_t dst_size ) LLAudioEngine_FMOD::LLAudioEngine_FMOD() { - mInited = FALSE; + mInited = false; mCurrentInternetStreamp = NULL; mInternetStreamChannel = -1; + mWindGen = NULL; } @@ -105,7 +90,7 @@ LLAudioEngine_FMOD::~LLAudioEngine_FMOD() } -BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) +bool LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) { mFadeIn = -10000; @@ -124,7 +109,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) { LL_WARNS("AppInit") << "Error : You are using the wrong FMOD version (" << version << ")! You should be using FMOD " << FMOD_VERSION << LL_ENDL; - //return FALSE; + //return false; } U32 fmod_flags = 0x0; @@ -139,7 +124,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) { LL_WARNS("AppInit") << "Error setting FMOD window: " << FMOD_ErrorString(FSOUND_GetError()) << LL_ENDL; - return FALSE; + return false; } // Play audio when we don't have focus. // (For example, IM client on top of us.) @@ -167,7 +152,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) // on top of ALSA is ironically more reliable than raw ALSA. // Ack, and ESD has more reliable failure modes - but has worse // latency - than all of them, so wins for now. - BOOL audio_ok = FALSE; + bool audio_ok = false; if (!audio_ok) if (NULL == getenv("LL_BAD_ESD")) /*Flawfinder: ignore*/ @@ -178,7 +163,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) { LL_DEBUGS("AppInit") << "ESD audio output initialized OKAY" << LL_ENDL; - audio_ok = TRUE; + audio_ok = true; } else { LL_WARNS("AppInit") << "ESD audio output FAILED to initialize: " << FMOD_ErrorString(FSOUND_GetError()) << LL_ENDL; @@ -195,7 +180,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) FSOUND_Init(44100, num_channels, fmod_flags)) { LL_DEBUGS("AppInit") << "OSS audio output initialized OKAY" << LL_ENDL; - audio_ok = TRUE; + audio_ok = true; } else { LL_WARNS("AppInit") << "OSS audio output FAILED to initialize: " << FMOD_ErrorString(FSOUND_GetError()) << LL_ENDL; @@ -212,7 +197,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) FSOUND_Init(44100, num_channels, fmod_flags)) { LL_DEBUGS("AppInit") << "ALSA audio output initialized OKAY" << LL_ENDL; - audio_ok = TRUE; + audio_ok = true; } else { LL_WARNS("AppInit") << "ALSA audio output FAILED to initialize: " << FMOD_ErrorString(FSOUND_GetError()) << LL_ENDL; @@ -224,7 +209,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) if (!audio_ok) { LL_WARNS("AppInit") << "Overall audio init failure." << LL_ENDL; - return FALSE; + return false; } // On Linux, FMOD causes a SIGPIPE for some netstream error @@ -250,7 +235,7 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) { LL_WARNS("AppInit") << "Error initializing FMOD: " << FMOD_ErrorString(FSOUND_GetError()) << LL_ENDL; - return FALSE; + return false; } #endif @@ -259,17 +244,9 @@ BOOL LLAudioEngine_FMOD::init(const S32 num_channels, void* userdata) LL_DEBUGS("AppInit") << "LLAudioEngine_FMOD::init() FMOD initialized correctly" << LL_ENDL; - mInited = TRUE; + mInited = true; - return TRUE; -} - - -void LLAudioEngine_FMOD::idle(F32 max_decode_time) -{ - LLAudioEngine::idle(max_decode_time); - - updateInternetStream(); + return true; } @@ -287,7 +264,7 @@ void LLAudioEngine_FMOD::shutdown() { if (gWindDSP) { - FSOUND_DSP_SetActive(gWindDSP,FALSE); + FSOUND_DSP_SetActive(gWindDSP,false); FSOUND_DSP_Free(gWindDSP); } @@ -318,13 +295,15 @@ LLAudioChannel *LLAudioEngine_FMOD::createChannel() void LLAudioEngine_FMOD::initWind() { + mWindGen = new LLWindGen; + if (!gWindDSP) { - gWindDSP = FSOUND_DSP_Create(&windCallback, FSOUND_DSP_DEFAULTPRIORITY_CLEARUNIT + 20, NULL); + gWindDSP = FSOUND_DSP_Create(&windCallback, FSOUND_DSP_DEFAULTPRIORITY_CLEARUNIT + 20, mWindGen); } if (gWindDSP) { - FSOUND_DSP_SetActive(gWindDSP, TRUE); + FSOUND_DSP_SetActive(gWindDSP, true); } mNextWindUpdate = 0.0; } @@ -334,10 +313,13 @@ void LLAudioEngine_FMOD::cleanupWind() { if (gWindDSP) { - FSOUND_DSP_SetActive(gWindDSP, FALSE); + FSOUND_DSP_SetActive(gWindDSP, false); FSOUND_DSP_Free(gWindDSP); gWindDSP = NULL; } + + delete mWindGen; + mWindGen = NULL; } @@ -367,9 +349,9 @@ void LLAudioEngine_FMOD::updateWind(LLVector3 wind_vec, F32 camera_height_above_ pitch = 1.0 + mapWindVecToPitch(wind_vec); center_freq = 80.0 * pow(pitch,2.5*(mapWindVecToGain(wind_vec)+1.0)); - gTargetFreq = (F32)center_freq; - gTargetGain = (F32)mapWindVecToGain(wind_vec) * mMaxWindGain; - gTargetPanGainR = (F32)mapWindVecToPan(wind_vec); + mWindGen->mTargetFreq = (F32)center_freq; + mWindGen->mTargetGain = (F32)mapWindVecToGain(wind_vec) * mMaxWindGain; + mWindGen->mTargetPanGainR = (F32)mapWindVecToPan(wind_vec); } } @@ -457,11 +439,11 @@ LLAudioChannelFMOD::~LLAudioChannelFMOD() } -BOOL LLAudioChannelFMOD::updateBuffer() +bool LLAudioChannelFMOD::updateBuffer() { if (LLAudioChannel::updateBuffer()) { - // Base class update returned TRUE, which means that we need to actually + // Base class update returned true, which means that we need to actually // set up the channel for a different buffer. LLAudioBufferFMOD *bufferp = (LLAudioBufferFMOD *)mCurrentSourcep->getCurrentBuffer(); @@ -473,13 +455,13 @@ BOOL LLAudioChannelFMOD::updateBuffer() // This is bad, there should ALWAYS be a sample associated with a legit // buffer. llerrs << "No FMOD sample!" << llendl; - return FALSE; + return false; } // Actually play the sound. Start it off paused so we can do all the necessary // setup. - mChannelID = FSOUND_PlaySoundEx(FSOUND_FREE, samplep, FSOUND_DSP_GetSFXUnit(), TRUE); + mChannelID = FSOUND_PlaySoundEx(FSOUND_FREE, samplep, FSOUND_DSP_GetSFXUnit(), true); //llinfos << "Setting up channel " << std::hex << mChannelID << std::dec << llendl; } @@ -501,7 +483,7 @@ BOOL LLAudioChannelFMOD::updateBuffer() } } - return TRUE; + return true; } @@ -524,12 +506,12 @@ void LLAudioChannelFMOD::update3DPosition() if (mCurrentSourcep->isAmbient()) { // Ambient sound, don't need to do any positional updates. - bufferp->set3DMode(FALSE); + bufferp->set3DMode(false); } else { // Localized sound. Update the position and velocity of the sound. - bufferp->set3DMode(TRUE); + bufferp->set3DMode(true); LLVector3 float_pos; float_pos.setVec(mCurrentSourcep->getPositionGlobal()); @@ -556,7 +538,7 @@ void LLAudioChannelFMOD::updateLoop() U32 cur_pos = FSOUND_GetCurrentPosition(mChannelID); if (cur_pos < (U32)mLastSamplePos) { - mLoopedThisFrame = TRUE; + mLoopedThisFrame = true; } mLastSamplePos = cur_pos; } @@ -589,11 +571,11 @@ void LLAudioChannelFMOD::play() return; } - if (!FSOUND_SetPaused(mChannelID, FALSE)) + if (!FSOUND_SetPaused(mChannelID, false)) { llwarns << "LLAudioChannelFMOD::play error: " << FMOD_ErrorString(FSOUND_GetError()) << llendl; } - getSource()->setPlayedOnce(TRUE); + getSource()->setPlayedOnce(true); } @@ -618,11 +600,11 @@ void LLAudioChannelFMOD::playSynced(LLAudioChannel *channelp) } -BOOL LLAudioChannelFMOD::isPlaying() +bool LLAudioChannelFMOD::isPlaying() { if (!mChannelID) { - return FALSE; + return false; } return FSOUND_IsPlaying(mChannelID) && (!FSOUND_GetPaused(mChannelID)); @@ -652,14 +634,14 @@ LLAudioBufferFMOD::~LLAudioBufferFMOD() } -BOOL LLAudioBufferFMOD::loadWAV(const std::string& filename) +bool LLAudioBufferFMOD::loadWAV(const std::string& filename) { // Try to open a wav file from disk. This will eventually go away, as we don't // really want to block doing this. if (filename.empty()) { // invalid filename, abort. - return FALSE; + return false; } S32 file_size = 0; @@ -667,7 +649,7 @@ BOOL LLAudioBufferFMOD::loadWAV(const std::string& filename) if (!apr_file) { // File not found, abort. - return FALSE; + return false; } apr_file_close(apr_file); @@ -717,11 +699,11 @@ BOOL LLAudioBufferFMOD::loadWAV(const std::string& filename) // // file is probably corrupt - remove it. LLFile::remove(filename); - return FALSE; + return false; } - // Everything went well, return TRUE - return TRUE; + // Everything went well, return true + return true; } @@ -736,7 +718,7 @@ U32 LLAudioBufferFMOD::getLength() } -void LLAudioBufferFMOD::set3DMode(BOOL use3d) +void LLAudioBufferFMOD::set3DMode(bool use3d) { U16 current_mode = FSOUND_Sample_GetMode(mSamplep); @@ -765,7 +747,7 @@ void LLAudioEngine_FMOD::initInternetStream() { // Number of milliseconds of audio to buffer for the audio card. // Must be larger than the usual Second Life frame stutter time. - FSOUND_Stream_SetBufferSize(200); + FSOUND_Stream_SetBufferSize(200); // Here's where we set the size of the network buffer and some buffering // parameters. In this case we want a network buffer of 16k, we want it @@ -810,19 +792,19 @@ signed char F_CALLBACKAPI LLAudioEngine_FMOD::callbackMetaData(char *name, char if (!strcmp("ARTIST", name)) { strlcpy(self->mInternetStreamArtist, value, 256); - self->mInternetStreamNewMetaData = TRUE; - return TRUE; + self->mInternetStreamNewMetaData = true; + return true; } if (!strcmp("TITLE", name)) { strlcpy(self->mInternetStreamTitle, value, 256); - self->mInternetStreamNewMetaData = TRUE; - return TRUE; + self->mInternetStreamNewMetaData = true; + return true; } */ - return TRUE; + return true; } @@ -867,7 +849,7 @@ void LLAudioEngine_FMOD::updateInternetStream() { // Reset volume to previously set volume setInternetStreamGain(mInternetStreamGain); - FSOUND_SetPaused(mInternetStreamChannel, FALSE); + FSOUND_SetPaused(mInternetStreamChannel, false); //FSOUND_Stream_Net_SetMetadataCallback(mInternetStream, callbackMetaData, this); } } @@ -909,7 +891,7 @@ void LLAudioEngine_FMOD::stopInternetStream() { if (mInternetStreamChannel != -1) { - FSOUND_SetPaused(mInternetStreamChannel, TRUE); + FSOUND_SetPaused(mInternetStreamChannel, true); FSOUND_SetPriority(mInternetStreamChannel, 0); mInternetStreamChannel = -1; } @@ -971,16 +953,10 @@ int LLAudioEngine_FMOD::isInternetStreamPlaying() } -void LLAudioEngine_FMOD::getInternetStreamInfo(char* artist_out, char* title_out) -{ - //strlcpy(artist_out, mInternetStreamArtist, 256); - //strlcpy(title_out, mInternetStreamTitle, 256); -} - - void LLAudioEngine_FMOD::setInternetStreamGain(F32 vol) { - LLAudioEngine::setInternetStreamGain(vol); + mInternetStreamGain = vol; + if (mInternetStreamChannel != -1) { vol = llclamp(vol, 0.f, 1.f); @@ -990,15 +966,9 @@ void LLAudioEngine_FMOD::setInternetStreamGain(F32 vol) } -const std::string& LLAudioEngine_FMOD::getInternetStreamURL() -{ - return mInternetStreamURL; -} - - LLAudioStreamFMOD::LLAudioStreamFMOD(const std::string& url) : mInternetStream(NULL), - mReady(FALSE) + mReady(false) { mInternetStreamURL = url; mInternetStream = FSOUND_Stream_Open(url.c_str(), FSOUND_NORMAL | FSOUND_NONBLOCKING, 0, 0); @@ -1007,11 +977,11 @@ LLAudioStreamFMOD::LLAudioStreamFMOD(const std::string& url) : llwarns << "Couldn't open fmod stream, error " << FMOD_ErrorString(FSOUND_GetError()) << llendl; - mReady = FALSE; + mReady = false; return; } - mReady = TRUE; + mReady = true; } int LLAudioStreamFMOD::startStream() @@ -1026,10 +996,10 @@ int LLAudioStreamFMOD::startStream() // Make sure the stream is set to 2D mode. FSOUND_Stream_SetMode(mInternetStream, FSOUND_2D); - return FSOUND_Stream_PlayEx(FSOUND_FREE, mInternetStream, NULL, TRUE); + return FSOUND_Stream_PlayEx(FSOUND_FREE, mInternetStream, NULL, true); } -BOOL LLAudioStreamFMOD::stopStream() +bool LLAudioStreamFMOD::stopStream() { if (mInternetStream) { @@ -1039,34 +1009,34 @@ BOOL LLAudioStreamFMOD::stopStream() unsigned int flags = 0x0; FSOUND_Stream_Net_GetStatus(mInternetStream, &status, &read_percent, &bitrate, &flags); - BOOL close = TRUE; + bool close = true; switch (status) { case FSOUND_STREAM_NET_CONNECTING: - close = FALSE; + close = false; break; case FSOUND_STREAM_NET_NOTCONNECTED: case FSOUND_STREAM_NET_BUFFERING: case FSOUND_STREAM_NET_READY: case FSOUND_STREAM_NET_ERROR: default: - close = TRUE; + close = true; } if (close) { FSOUND_Stream_Close(mInternetStream); mInternetStream = NULL; - return TRUE; + return true; } else { - return FALSE; + return false; } } else { - return TRUE; + return true; } } @@ -1076,94 +1046,35 @@ int LLAudioStreamFMOD::getOpenState() return open_state; } -/* This determines the format of the mixbuffer being passed in. change if you want to support int32 or float32 */ -#if LL_DARWIN - #define MIXBUFFERFORMAT S32 -#else - #define MIXBUFFERFORMAT S16 -#endif - -inline MIXBUFFERFORMAT clipSample(MIXBUFFERFORMAT sample, MIXBUFFERFORMAT min, MIXBUFFERFORMAT max) -{ - if (sample > max) - sample = max; - else if (sample < min) - sample = min; - - return sample; -} - -void * F_CALLBACKAPI windCallback(void *originalbuffer, void *newbuffer, int length, void*) +void * F_CALLBACKAPI windCallback(void *originalbuffer, void *newbuffer, int length, void* userdata) { -// originalbuffer = fsounds original mixbuffer. -// newbuffer = the buffer passed from the previous DSP unit. -// length = length in samples at this mix time. -// param = user parameter passed through in FSOUND_DSP_Create. -// -// modify the buffer in some fashion + // originalbuffer = fmod's original mixbuffer. + // newbuffer = the buffer passed from the previous DSP unit. + // length = length in samples at this mix time. + // param = user parameter passed through in FSOUND_DSP_Create. + // + // modify the buffer in some fashion - U8 *cursamplep = (U8*)newbuffer; - U8 wordsize = 2; + LLWindGen *windgen = + (LLWindGen *)userdata; + U8 stride; #if LL_DARWIN - wordsize = sizeof(MIXBUFFERFORMAT); + stride = sizeof(LLAudioEngine_FMOD::MIXBUFFERFORMAT); #else - int mixertype = FSOUND_GetMixer(); - if (mixertype == FSOUND_MIXER_BLENDMODE || mixertype == FSOUND_MIXER_QUALITY_FPU) - { - wordsize = 4; - } -#endif - - double bandwidth = 50; - double inputSamplingRate = 44100; - double a0,b1,b2; - - // calculate resonant filter coeffs - b2 = exp(-(F_TWO_PI) * (bandwidth / inputSamplingRate)); - - while (length--) - { - gCurrentFreq = (float)((0.999 * gCurrentFreq) + (0.001 * gTargetFreq)); - gCurrentGain = (float)((0.999 * gCurrentGain) + (0.001 * gTargetGain)); - gCurrentPanGainR = (float)((0.999 * gCurrentPanGainR) + (0.001 * gTargetPanGainR)); - b1 = (-4.0 * b2) / (1.0 + b2) * cos(F_TWO_PI * (gCurrentFreq / inputSamplingRate)); - a0 = (1.0 - b2) * sqrt(1.0 - (b1 * b1) / (4.0 * b2)); - double nextSample; - - // start with white noise - nextSample = ll_frand(2.0f) - 1.0f; - -#if 1 // LLAE_WIND_PINK apply pinking filter - gbuf0 = 0.997f * gbuf0 + 0.0126502f * nextSample; - gbuf1 = 0.985f * gbuf1 + 0.0139083f * nextSample; - gbuf2 = 0.950f * gbuf2 + 0.0205439f * nextSample; - gbuf3 = 0.850f * gbuf3 + 0.0387225f * nextSample; - gbuf4 = 0.620f * gbuf4 + 0.0465932f * nextSample; - gbuf5 = 0.250f * gbuf5 + 0.1093477f * nextSample; - - nextSample = gbuf0 + gbuf1 + gbuf2 + gbuf3 + gbuf4 + gbuf5; -#endif - -#if 1 //LLAE_WIND_RESONANT // do a resonant filter on the noise - nextSample = (double)( a0 * nextSample - b1 * gY0 - b2 * gY1 ); - - gY1 = gY0; - gY0 = nextSample; + int mixertype = FSOUND_GetMixer(); + if (mixertype == FSOUND_MIXER_BLENDMODE || + mixertype == FSOUND_MIXER_QUALITY_FPU) + { + stride = 4; + } + else + { + stride = 2; + } #endif - nextSample *= gCurrentGain; - - MIXBUFFERFORMAT sample; - - sample = llfloor(((F32)nextSample*32768.f*(1.0f - gCurrentPanGainR))+0.5f); - *(MIXBUFFERFORMAT*)cursamplep = clipSample((*(MIXBUFFERFORMAT*)cursamplep) + sample, -32768, 32767); - cursamplep += wordsize; - - sample = llfloor(((F32)nextSample*32768.f*gCurrentPanGainR)+0.5f); - *(MIXBUFFERFORMAT*)cursamplep = clipSample((*(MIXBUFFERFORMAT*)cursamplep) + sample, -32768, 32767); - cursamplep += wordsize; - } + newbuffer = windgen->windGenerate((LLAudioEngine_FMOD::MIXBUFFERFORMAT *)newbuffer, length, stride); return newbuffer; } diff --git a/linden/indra/llaudio/audioengine_fmod.h b/linden/indra/llaudio/audioengine_fmod.h index 41177b6..132afb1 100644 --- a/linden/indra/llaudio/audioengine_fmod.h +++ b/linden/indra/llaudio/audioengine_fmod.h @@ -35,6 +35,7 @@ #include "audioengine.h" #include "listener_fmod.h" +#include "windgen.h" #include "fmod.h" @@ -47,13 +48,11 @@ public: virtual ~LLAudioEngine_FMOD(); // initialization/startup/shutdown - virtual BOOL init(const S32 num_channels, void *user_data); + virtual bool init(const S32 num_channels, void *user_data); virtual void allocateListener(); virtual void shutdown(); - virtual void idle(F32 max_decode_time = 0.f); - // Internet stream methods virtual void initInternetStream(); virtual void startInternetStream(const std::string& url); @@ -61,15 +60,19 @@ public: virtual void stopInternetStream(); virtual void pauseInternetStream(int pause); virtual int isInternetStreamPlaying(); - virtual void getInternetStreamInfo(char* artist, char* title); virtual void setInternetStreamGain(F32 vol); - virtual const std::string& getInternetStreamURL(); /*virtual*/ void initWind(); /*virtual*/ void cleanupWind(); /*virtual*/void updateWind(LLVector3 direction, F32 camera_height_above_water); +#if LL_DARWIN + typedef S32 MIXBUFFERFORMAT; +#else + typedef S16 MIXBUFFERFORMAT; +#endif + protected: /*virtual*/ LLAudioBuffer *createBuffer(); // Get a free buffer, or flush an existing one if you have to. /*virtual*/ LLAudioChannel *createChannel(); // Create a new audio channel. @@ -79,7 +82,6 @@ protected: static signed char F_CALLBACKAPI callbackMetaData(char* name, char* value, void* userdata); LLAudioStreamFMOD *mCurrentInternetStreamp; - std::string mInternetStreamURL; int mInternetStreamChannel; std::list mDeadStreams; @@ -88,11 +90,12 @@ protected: //F32 mMaxDistance[MAX_BUFFERS]; S32 mFadeIn; - BOOL mInited; + bool mInited; // On Windows, userdata is the HWND of the application window. void* mUserData; + LLWindGen *mWindGen; }; @@ -106,9 +109,9 @@ protected: /*virtual*/ void play(); /*virtual*/ void playSynced(LLAudioChannel *channelp); /*virtual*/ void cleanup(); - /*virtual*/ BOOL isPlaying(); + /*virtual*/ bool isPlaying(); - /*virtual*/ BOOL updateBuffer(); + /*virtual*/ bool updateBuffer(); /*virtual*/ void update3DPosition(); /*virtual*/ void updateLoop(); @@ -124,11 +127,11 @@ public: LLAudioBufferFMOD(); virtual ~LLAudioBufferFMOD(); - /*virtual*/ BOOL loadWAV(const std::string& filename); + /*virtual*/ bool loadWAV(const std::string& filename); /*virtual*/ U32 getLength(); friend class LLAudioChannelFMOD; - void set3DMode(BOOL use3d); + void set3DMode(bool use3d); protected: FSOUND_SAMPLE *getSample() { return mSamplep; } protected: @@ -140,15 +143,15 @@ class LLAudioStreamFMOD public: LLAudioStreamFMOD(const std::string& url); int startStream(); - BOOL stopStream(); // Returns true if the stream was successfully stopped. - BOOL ready(); + bool stopStream(); // Returns true if the stream was successfully stopped. + bool ready(); const std::string& getURL() { return mInternetStreamURL; } int getOpenState(); protected: FSOUND_STREAM* mInternetStream; - BOOL mReady; + bool mReady; std::string mInternetStreamURL; }; diff --git a/linden/indra/llaudio/audioengine_openal.cpp b/linden/indra/llaudio/audioengine_openal.cpp new file mode 100644 index 0000000..606d9f6 --- /dev/null +++ b/linden/indra/llaudio/audioengine_openal.cpp @@ -0,0 +1,422 @@ +/** + * @file audioengine_openal.cpp + * @brief implementation of audio engine using OpenAL + * support as a OpenAL 3D implementation + * + * $LicenseInfo:firstyear=2002&license=viewergpl$ + * + * Copyright (c) 2002-2008, Linden Research, Inc. + * + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab. Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + * + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + * + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + * + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ + +#include "linden_common.h" +#include "lldir.h" + +#include "audioengine_openal.h" +#include "listener_openal.h" + + +// Variables and definitions for Wind +#define MAX_NUM_WIND_BUFFERS 40 +static int empty_num_wind_buffers = MAX_NUM_WIND_BUFFERS; +static const float wind_buffer_size_sec = 0.05f; // 1/20th sec +static const U32 wind_gen_freq = LLWindGen::getInputSamplingRate(); +static ALuint wind_source; +static S16 *winddata=NULL; + + +LLAudioEngine_OpenAL::LLAudioEngine_OpenAL() +{ + mWindGen = NULL; +} + +LLAudioEngine_OpenAL::~LLAudioEngine_OpenAL() +{ +} + +bool LLAudioEngine_OpenAL::init(const S32 num_channels, void* userdata) +{ + mWindGen = NULL; + LLAudioEngine::init(num_channels, userdata); + + if(!alutInit(NULL, NULL)) + { + llwarns << "LLAudioEngine_OpenAL::init() ALUT initialization failed: " << alutGetErrorString (alutGetError ()) << llendl; + return false; + } + + llinfos << "LLAudioEngine_OpenAL::init() OpenAL successfully initialized" << llendl; + + llinfos << "OpenAL version: " + << ll_safe_string(alGetString(AL_VERSION)) << llendl; + llinfos << "OpenAL vendor: " + << ll_safe_string(alGetString(AL_VENDOR)) << llendl; + llinfos << "OpenAL renderer: " + << ll_safe_string(alGetString(AL_RENDERER)) << llendl; + + ALint major = alutGetMajorVersion (); + ALint minor = alutGetMinorVersion (); + llinfos << "ALUT version: " << major << "." << minor << llendl; + + ALCdevice *device = alcGetContextsDevice(alcGetCurrentContext()); + + alcGetIntegerv(device, ALC_MAJOR_VERSION, 1, &major); + alcGetIntegerv(device, ALC_MAJOR_VERSION, 1, &minor); + llinfos << "ALC version: " << major << "." << minor << llendl; + + llinfos << "ALC default device: " + << ll_safe_string(alcGetString(device, + ALC_DEFAULT_DEVICE_SPECIFIER)) + << llendl; + + llinfos << "LLAudioEngine_OpenAL::init() Speed of sound is: " << alGetFloat(AL_SPEED_OF_SOUND) << llendl; + + return true; +} + +void LLAudioEngine_OpenAL::allocateListener() +{ + mListenerp = (LLListener *) new LLListener_OpenAL(); + if(!mListenerp) + { + llwarns << "LLAudioEngine_OpenAL::allocateListener() Listener creation failed" << llendl; + } +} + +void LLAudioEngine_OpenAL::shutdown() +{ + llinfos << "About to LLAudioEngine::shutdown()" << llendl; + LLAudioEngine::shutdown(); + + llinfos << "About to alutExit()" << llendl; + if(!alutExit()) + { + llwarns << "Nuts." << llendl; + llwarns << "LLAudioEngine_OpenAL::shutdown() ALUT shutdown failed: " << alutGetErrorString (alutGetError ()) << llendl; + } + + llinfos << "LLAudioEngine_OpenAL::shutdown() OpenAL successfully shut down" << llendl; + + delete mListenerp; + mListenerp = NULL; +} + +LLAudioBuffer *LLAudioEngine_OpenAL::createBuffer() +{ + return new LLAudioBufferOpenAL(); +} + +LLAudioChannel *LLAudioEngine_OpenAL::createChannel() +{ + return new LLAudioChannelOpenAL(); +} + +void LLAudioEngine_OpenAL::setInternalGain(F32 gain) +{ + //llinfos << "LLAudioEngine_OpenAL::setInternalGain() Gain: " << gain << llendl; + alListenerf(AL_GAIN, gain); +} + +LLAudioChannelOpenAL::LLAudioChannelOpenAL() +{ + alGenSources(1, &mALSource); +} + +LLAudioChannelOpenAL::~LLAudioChannelOpenAL() +{ + cleanup(); + alDeleteSources(1, &mALSource); +} + +void LLAudioChannelOpenAL::cleanup() +{ + alSourceStop(mALSource); + mCurrentBufferp = NULL; +} + +void LLAudioChannelOpenAL::play() +{ + if(!isPlaying()){ + alSourcePlay(mALSource); + getSource()->setPlayedOnce(true); + } +} + +void LLAudioChannelOpenAL::playSynced(LLAudioChannel *channelp) +{ + play(); +} + +bool LLAudioChannelOpenAL::isPlaying() +{ + ALint state; + alGetSourcei(mALSource, AL_SOURCE_STATE, &state); + if(state == AL_PLAYING){ + return true; + } + return false; +} + +bool LLAudioChannelOpenAL::updateBuffer() +{ + if (LLAudioChannel::updateBuffer()) + { + // Base class update returned true, which means that we need to actually + // set up the source for a different buffer. + LLAudioBufferOpenAL *bufferp = (LLAudioBufferOpenAL *)mCurrentSourcep->getCurrentBuffer(); + alSourcei(mALSource, AL_BUFFER, bufferp->getBuffer()); + alSourcef(mALSource, AL_GAIN, mCurrentSourcep->getGain()); + alSourcei(mALSource, AL_LOOPING, mCurrentSourcep->isLoop() ? AL_TRUE : AL_FALSE); + } + + return true; +} + +void LLAudioChannelOpenAL::update3DPosition() +{ + if(!mCurrentSourcep) + { + return; + } + if (mCurrentSourcep->isAmbient()) + { + alSource3f(mALSource, AL_POSITION, 0.0, 0.0, 0.0); + alSource3f(mALSource, AL_VELOCITY, 0.0, 0.0, 0.0); + //alSource3f(mALSource, AL_DIRECTION, 0.0, 0.0, 0.0); + alSourcef (mALSource, AL_ROLLOFF_FACTOR, 0.0); + alSourcei (mALSource, AL_SOURCE_RELATIVE, AL_TRUE); + } else { + LLVector3 float_pos; + float_pos.setVec(mCurrentSourcep->getPositionGlobal()); + alSourcefv(mALSource, AL_POSITION, float_pos.mV); + //llinfos << "LLAudioChannelOpenAL::update3DPosition() Velocity: " << mCurrentSourcep->getVelocity() << llendl; + alSourcefv(mALSource, AL_VELOCITY, mCurrentSourcep->getVelocity().mV); + //alSource3f(mALSource, AL_DIRECTION, 0.0, 0.0, 0.0); + alSourcef (mALSource, AL_ROLLOFF_FACTOR, 1.0); + alSourcei (mALSource, AL_SOURCE_RELATIVE, AL_FALSE); + } + //llinfos << "LLAudioChannelOpenAL::update3DPosition() Gain: " << mCurrentSourcep->getGain() << llendl; + alSourcef(mALSource, AL_GAIN, mCurrentSourcep->getGain()); +} + +LLAudioBufferOpenAL::LLAudioBufferOpenAL() +{ + mALBuffer = AL_NONE; +} + +LLAudioBufferOpenAL::~LLAudioBufferOpenAL() +{ + cleanup(); +} + +void LLAudioBufferOpenAL::cleanup() +{ + if(mALBuffer != AL_NONE) + { + alDeleteBuffers(1, &mALBuffer); + mALBuffer = AL_NONE; + } +} + +bool LLAudioBufferOpenAL::loadWAV(const std::string& filename) +{ + cleanup(); + mALBuffer = alutCreateBufferFromFile(filename.c_str()); + if(mALBuffer == AL_NONE){ + ALenum error = alutGetError(); + if (gDirUtilp->fileExists(filename)) { + llwarns << + "LLAudioBufferOpenAL::loadWAV() Error loading " + << filename + << " " << alutGetErrorString(error) << llendl; + } else { + // It's common for the file to not actually exist. + lldebugs << + "LLAudioBufferOpenAL::loadWAV() Error loading " + << filename + << " " << alutGetErrorString(error) << llendl; + } + return false; + } + + return true; +} + +U32 LLAudioBufferOpenAL::getLength(){ + if(mALBuffer == AL_NONE){ + return 0; + } + ALint length; + alGetBufferi(mALBuffer, AL_SIZE, &length); + return length >> 2; +} + +// ------------ + +void LLAudioEngine_OpenAL::initWind(){ + ALenum error; + llinfos << "LLAudioEngine_OpenAL::initWind() start" << llendl; + + alGetError(); /* clear error */ + + alGenSources(1,&wind_source); + + if((error=alGetError()) != AL_NO_ERROR) + { + llwarns << "LLAudioEngine_OpenAL::initWind() Error creating wind sources: "<; + + llinfos << "LLAudioEngine_OpenAL::initWind() done" << llendl; +} + +void LLAudioEngine_OpenAL::cleanupWind(){ + llinfos << "LLAudioEngine_OpenAL::cleanupWind()" << llendl; + + alDeleteSources(1, &wind_source); + + if(winddata) + free(winddata); + + delete mWindGen; + mWindGen = NULL; +} + +void LLAudioEngine_OpenAL::updateWind(LLVector3 wind_vec, F32 camera_altitude) +{ + LLVector3 wind_pos; + F64 pitch; + F64 center_freq; + ALenum error; + + mMaxWindGain=1.0; + + if (!mEnableWind) + return; + + if(!winddata) + return; + + if (mWindUpdateTimer.checkExpirationAndReset(LL_WIND_UPDATE_INTERVAL)) + { + + // wind comes in as Linden coordinate (+X = forward, +Y = left, +Z = up) + // need to convert this to the conventional orientation DS3D and OpenAL use + // where +X = right, +Y = up, +Z = backwards + + wind_vec.setVec(-wind_vec.mV[1], wind_vec.mV[2], -wind_vec.mV[0]); + + pitch = 1.0 + mapWindVecToPitch(wind_vec); + center_freq = 80.0 * pow(pitch,2.5*(mapWindVecToGain(wind_vec)+1.0)); + + mWindGen->mTargetFreq = (F32)center_freq; + mWindGen->mTargetGain = (F32)mapWindVecToGain(wind_vec) * mMaxWindGain; + mWindGen->mTargetPanGainR = (F32)mapWindVecToPan(wind_vec); + + alSourcei(wind_source, AL_LOOPING, AL_FALSE); + alSource3f(wind_source, AL_POSITION, 0.0, 0.0, 0.0); + alSource3f(wind_source, AL_VELOCITY, 0.0, 0.0, 0.0); + alSourcef(wind_source, AL_ROLLOFF_FACTOR, 0.0); + alSourcei(wind_source, AL_SOURCE_RELATIVE, AL_TRUE); + } + + // ok lets make a wind buffer now + + int processed, queued, unprocessed; + alGetSourcei(wind_source, AL_BUFFERS_PROCESSED, &processed); + alGetSourcei(wind_source, AL_BUFFERS_QUEUED, &queued); + unprocessed = queued - processed; + + // ensure that there are always at least 3x as many filled buffers + // queued as we managed to empty since last time. + empty_num_wind_buffers = llmin(empty_num_wind_buffers + processed * 3 - unprocessed, MAX_NUM_WIND_BUFFERS-unprocessed); + empty_num_wind_buffers = llmax(empty_num_wind_buffers, 0); + + //llinfos << "empty_num_wind_buffers: " << empty_num_wind_buffers <<" (" << unprocessed << ":" << processed << ")" << llendl; + + while(processed--) // unqueue old buffers + { + ALuint buffer; + int error; + alGetError(); /* clear error */ + alSourceUnqueueBuffers(wind_source, 1, &buffer); + error = alGetError(); + if(error != AL_NO_ERROR) + { + llwarns << "LLAudioEngine_OpenAL::updateWind() error swapping (unqueuing) buffers" << llendl; + } + else + { + alDeleteBuffers(1, &buffer); + } + } + + while (empty_num_wind_buffers > 0) // fill+queue new buffers + { + ALuint buffer; + alGetError(); /* clear error */ + alGenBuffers(1,&buffer); + if((error=alGetError()) != AL_NO_ERROR) + { + llwarns << "LLAudioEngine_OpenAL::initWind() Error creating wind buffer: " << error << llendl; + break; + } + + alBufferData(buffer, + AL_FORMAT_STEREO16, + mWindGen->windGenerate(winddata, + int(wind_gen_freq*wind_buffer_size_sec), 2), + int(2*wind_gen_freq*wind_buffer_size_sec*sizeof(S16)), + wind_gen_freq); + error = alGetError(); + if(error != AL_NO_ERROR) + llwarns << "LLAudioEngine_OpenAL::updateWind() error swapping (bufferdata) buffers" << llendl; + + alSourceQueueBuffers(wind_source, 1, &buffer); + error = alGetError(); + if(error != AL_NO_ERROR) + llwarns << "LLAudioEngine_OpenAL::updateWind() error swapping (queuing) buffers" << llendl; + + --empty_num_wind_buffers; + } + + int playing; + alGetSourcei(wind_source, AL_SOURCE_STATE, &playing); + if(playing != AL_PLAYING) + { + alSourcePlay(wind_source); + + llinfos << "Wind had stopped - probably ran out of buffers - restarting: " << (unprocessed+empty_num_wind_buffers) << " now queued." << llendl; + } +} + diff --git a/linden/indra/llaudio/audioengine_openal.h b/linden/indra/llaudio/audioengine_openal.h new file mode 100644 index 0000000..6289f99 --- /dev/null +++ b/linden/indra/llaudio/audioengine_openal.h @@ -0,0 +1,100 @@ +/** + * @file audioengine_openal.cpp + * @brief implementation of audio engine using OpenAL + * support as a OpenAL 3D implementation + * + * Copyright (c) 2002-2008, Linden Research, Inc. + * + * $LicenseInfo:firstyear=2002&license=viewergpl$ + * + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab. Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + * + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + * + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + * + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ + + +#ifndef LL_AUDIOENGINE_OpenAL_H +#define LL_AUDIOENGINE_OpenAL_H + +#include "audioengine.h" +#include "listener_openal.h" +#include "windgen.h" + +class LLAudioEngine_OpenAL : public LLAudioEngine +{ + public: + LLAudioEngine_OpenAL(); + virtual ~LLAudioEngine_OpenAL(); + + virtual bool init(const S32 num_channels, void *user_data); + virtual void allocateListener(); + + virtual void shutdown(); + + void setInternalGain(F32 gain); + + LLAudioBuffer* createBuffer(); + LLAudioChannel* createChannel(); + + /*virtual*/ void initWind(); + /*virtual*/ void cleanupWind(); + /*virtual*/ void updateWind(LLVector3 direction, F32 camera_altitude); + + private: + void * windDSP(void *newbuffer, int length); + LLWindGen *mWindGen; +}; + +class LLAudioChannelOpenAL : public LLAudioChannel +{ + public: + LLAudioChannelOpenAL(); + virtual ~LLAudioChannelOpenAL(); + protected: + void play(); + void playSynced(LLAudioChannel *channelp); + void cleanup(); + bool isPlaying(); + + bool updateBuffer(); + void update3DPosition(); + void updateLoop(){}; + + ALuint mALSource; +}; + +class LLAudioBufferOpenAL : public LLAudioBuffer{ + public: + LLAudioBufferOpenAL(); + virtual ~LLAudioBufferOpenAL(); + + bool loadWAV(const std::string& filename); + U32 getLength(); + + friend class LLAudioChannelOpenAL; + protected: + void cleanup(); + ALuint getBuffer() {return mALBuffer;} + + ALuint mALBuffer; +}; + +#endif diff --git a/linden/indra/llaudio/listener_fmod.h b/linden/indra/llaudio/listener_fmod.h index 7b7c4c6..95b31ac 100644 --- a/linden/indra/llaudio/listener_fmod.h +++ b/linden/indra/llaudio/listener_fmod.h @@ -37,11 +37,6 @@ class LLListener_FMOD : public LLListener { - protected: - F32 mDopplerFactor; - F32 mDistanceFactor; - F32 mRolloffFactor; - public: LLListener_FMOD(); virtual ~LLListener_FMOD(); @@ -59,6 +54,11 @@ class LLListener_FMOD : public LLListener virtual F32 getDistanceFactor(); virtual void setRolloffFactor(F32 factor); virtual F32 getRolloffFactor(); + + protected: + F32 mDopplerFactor; + F32 mDistanceFactor; + F32 mRolloffFactor; }; #endif diff --git a/linden/indra/llaudio/listener_openal.cpp b/linden/indra/llaudio/listener_openal.cpp new file mode 100644 index 0000000..e72b078 --- /dev/null +++ b/linden/indra/llaudio/listener_openal.cpp @@ -0,0 +1,94 @@ +/** + * @file audioengine_openal.cpp + * @brief implementation of audio engine using OpenAL + * support as a OpenAL 3D implementation + * + * $LicenseInfo:firstyear=2002&license=viewergpl$ + * + * Copyright (c) 2002-2007, Linden Research, Inc. + * + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab. Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + * + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + * + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + * + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ + +#include "linden_common.h" +#include "audioengine.h" + +#include "listener_openal.h" + +LLListener_OpenAL::LLListener_OpenAL(){ + init(); +} + +LLListener_OpenAL::~LLListener_OpenAL(){ +} + +void LLListener_OpenAL::translate(LLVector3 offset){ + LLListener::translate(offset); + llinfos << "LLListener_OpenAL::translate() : " << offset << llendl; +} + +void LLListener_OpenAL::setPosition(LLVector3 pos){ + LLListener::setPosition(pos); + //llinfos << "LLListener_OpenAL::setPosition() : " << pos << llendl; +} + +void LLListener_OpenAL::setVelocity(LLVector3 vel){ + LLListener::setVelocity(vel); +} + +void LLListener_OpenAL::orient(LLVector3 up, LLVector3 at){ + LLListener::orient(up, at); + //llinfos << "LLListener_OpenAL::orient() up: " << up << " at: " << at << llendl; +} + +void LLListener_OpenAL::commitDeferredChanges(){ + ALfloat orientation[6]; + orientation[0] = mListenAt.mV[0]; + orientation[1] = mListenAt.mV[1]; + orientation[2] = mListenAt.mV[2]; + orientation[3] = mListenUp.mV[0]; + orientation[4] = mListenUp.mV[1]; + orientation[5] = mListenUp.mV[2]; + + ALfloat velocity[3]; + velocity[0] = mVelocity.mV[0]; + velocity[1] = mVelocity.mV[1]; + velocity[2] = mVelocity.mV[2]; + + alListenerfv(AL_ORIENTATION, orientation); + alListenerfv(AL_POSITION, mPosition.mV); + alListenerfv(AL_VELOCITY, velocity); +} + +void LLListener_OpenAL::setDopplerFactor(F32 factor){ + //llinfos << "LLListener_OpenAL::setDopplerFactor() : " << factor << llendl; + alDopplerFactor(factor); +} + +F32 LLListener_OpenAL::getDopplerFactor(){ + ALfloat factor; + factor = alGetFloat(AL_DOPPLER_FACTOR); + //llinfos << "LLListener_OpenAL::getDopplerFactor() : " << factor << llendl; + return factor; +} + diff --git a/linden/indra/llaudio/listener_openal.h b/linden/indra/llaudio/listener_openal.h index cc4bb9e..737343e 100644 --- a/linden/indra/llaudio/listener_openal.h +++ b/linden/indra/llaudio/listener_openal.h @@ -40,12 +40,6 @@ class LLListener_OpenAL : public LLListener { - private: - protected: - public: - - private: - protected: public: LLListener_OpenAL(); virtual ~LLListener_OpenAL(); @@ -54,6 +48,12 @@ class LLListener_OpenAL : public LLListener virtual void setPosition(LLVector3 pos); virtual void setVelocity(LLVector3 vel); virtual void orient(LLVector3 up, LLVector3 at); + virtual void commitDeferredChanges(); + + virtual void setDopplerFactor(F32 factor); + virtual F32 getDopplerFactor(); + + protected: }; #endif diff --git a/linden/indra/llaudio/windgen.h b/linden/indra/llaudio/windgen.h new file mode 100644 index 0000000..39ce568 --- /dev/null +++ b/linden/indra/llaudio/windgen.h @@ -0,0 +1,138 @@ +/** + * @file windgen.h + * @brief Templated wind noise generation + * + * $LicenseInfo:firstyear=2002&license=viewergpl$ + * + * Copyright (c) 2002-2008, Linden Research, Inc. + * + * Second Life Viewer Source Code + * The source code in this file ("Source Code") is provided by Linden Lab + * to you under the terms of the GNU General Public License, version 2.0 + * ("GPL"), unless you have obtained a separate licensing agreement + * ("Other License"), formally executed by you and Linden Lab. Terms of + * the GPL can be found in doc/GPL-license.txt in this distribution, or + * online at http://secondlife.com/developers/opensource/gplv2 + * + * There are special exceptions to the terms and conditions of the GPL as + * it is applied to this Source Code. View the full text of the exception + * in the file doc/FLOSS-exception.txt in this software distribution, or + * online at http://secondlife.com/developers/opensource/flossexception + * + * By copying, modifying or distributing this software, you acknowledge + * that you have read and understood your obligations described above, + * and agree to abide by those obligations. + * + * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO + * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, + * COMPLETENESS OR PERFORMANCE. + * $/LicenseInfo$ + */ +#ifndef WINDGEN_H +#define WINDGEN_H + +#include "llcommon.h" +#include "llrand.h" + +template +class LLWindGen +{ +public: + LLWindGen() : + mTargetGain(0.f), + mTargetFreq(100.f), + mTargetPanGainR(0.5f), + mbuf0(0.0), + mbuf1(0.0), + mbuf2(0.0), + mbuf3(0.0), + mbuf4(0.0), + mbuf5(0.0), + mY0(0.0), + mY1(0.0), + mCurrentGain(0.f), + mCurrentFreq(100.f), + mCurrentPanGainR(0.5f) {}; + + static const U32 getInputSamplingRate() {return mInputSamplingRate;} + + // newbuffer = the buffer passed from the previous DSP unit. + // numsamples = length in samples-per-channel at this mix time. + // stride = number of bytes between start of each sample. + // NOTE: generates L/R interleaved stereo + MIXBUFFERFORMAT_T* windGenerate(MIXBUFFERFORMAT_T *newbuffer, int numsamples, int stride) + { + U8 *cursamplep = (U8*)newbuffer; + + double bandwidth = 50.0F; + double a0,b1,b2; + + // calculate resonant filter coeffs + b2 = exp(-(F_TWO_PI) * (bandwidth / mInputSamplingRate)); + + while (numsamples--) + { + mCurrentFreq = (float)((0.999 * mCurrentFreq) + (0.001 * mTargetFreq)); + mCurrentGain = (float)((0.999 * mCurrentGain) + (0.001 * mTargetGain)); + mCurrentPanGainR = (float)((0.999 * mCurrentPanGainR) + (0.001 * mTargetPanGainR)); + b1 = (-4.0 * b2) / (1.0 + b2) * cos(F_TWO_PI * (mCurrentFreq / mInputSamplingRate)); + a0 = (1.0 - b2) * sqrt(1.0 - (b1 * b1) / (4.0 * b2)); + double nextSample; + + // start with white noise + nextSample = ll_frand(2.0f) - 1.0f; + +#if 1 // LLAE_WIND_PINK apply pinking filter + mbuf0 = 0.997f * mbuf0 + 0.0126502f * nextSample; + mbuf1 = 0.985f * mbuf1 + 0.0139083f * nextSample; + mbuf2 = 0.950f * mbuf2 + 0.0205439f * nextSample; + mbuf3 = 0.850f * mbuf3 + 0.0387225f * nextSample; + mbuf4 = 0.620f * mbuf4 + 0.0465932f * nextSample; + mbuf5 = 0.250f * mbuf5 + 0.1093477f * nextSample; + + nextSample = mbuf0 + mbuf1 + mbuf2 + mbuf3 + mbuf4 + mbuf5; +#endif + +#if 1 //LLAE_WIND_RESONANT // do a resonant filter on the noise + nextSample = (double)( a0 * nextSample - b1 * mY0 - b2 * mY1 ); + + mY1 = mY0; + mY0 = nextSample; +#endif + + nextSample *= mCurrentGain; + + MIXBUFFERFORMAT_T sample; + + sample = llfloor(((F32)nextSample*32768.f*(1.0f - mCurrentPanGainR))+0.5f); + *(MIXBUFFERFORMAT_T*)cursamplep = llclamp(sample, (MIXBUFFERFORMAT_T)-32768, (MIXBUFFERFORMAT_T)32767); + cursamplep += stride; + + sample = llfloor(((F32)nextSample*32768.f*mCurrentPanGainR)+0.5f); + *(MIXBUFFERFORMAT_T*)cursamplep = llclamp(sample, (MIXBUFFERFORMAT_T)-32768, (MIXBUFFERFORMAT_T)32767); + cursamplep += stride; + } + + return newbuffer; + } + + F32 mTargetGain; + F32 mTargetFreq; + F32 mTargetPanGainR; + +private: + static const U32 mInputSamplingRate = 44100; + F64 mbuf0; + F64 mbuf1; + F64 mbuf2; + F64 mbuf3; + F64 mbuf4; + F64 mbuf5; + F64 mY0; + F64 mY1; + F32 mCurrentGain; + F32 mCurrentFreq; + F32 mCurrentPanGainR; +}; + +#endif diff --git a/linden/indra/newview/CMakeLists.txt b/linden/indra/newview/CMakeLists.txt index ddf6897..4bfbf02 100644 --- a/linden/indra/newview/CMakeLists.txt +++ b/linden/indra/newview/CMakeLists.txt @@ -8,6 +8,7 @@ include(BuildVersion) include(DirectX) include(ELFIO) include(FMOD) +include(OPENAL) include(FindOpenGL) include(LLAudio) include(LLCharacter) @@ -56,6 +57,7 @@ include_directories( ${LLXML_INCLUDE_DIRS} ${LSCRIPT_INCLUDE_DIRS} ${LSCRIPT_INCLUDE_DIRS}/lscript_compile + ${GSTREAMER_INCLUDE_DIRS} ) set(viewer_SOURCE_FILES @@ -1239,6 +1241,11 @@ set_source_files_properties(${viewer_CHARACTER_FILES} list(APPEND viewer_SOURCE_FILES ${viewer_CHARACTER_FILES}) + +if (OPENAL) + set_source_files_properties(llstartup.cpp PROPERTIES COMPILE_FLAGS -DLL_OPENAL) +endif (OPENAL) + if (FMOD) set_source_files_properties(llstartup.cpp PROPERTIES COMPILE_FLAGS -DLL_FMOD) diff --git a/linden/indra/newview/llappviewer.cpp b/linden/indra/newview/llappviewer.cpp index 6301421..f442f38 100644 --- a/linden/indra/newview/llappviewer.cpp +++ b/linden/indra/newview/llappviewer.cpp @@ -1178,7 +1178,8 @@ bool LLAppViewer::cleanup() llinfos << "Global stuff deleted" << llendflush; -#if !LL_RELEASE_FOR_DOWNLOAD +#if (!defined(LL_FMOD)) || (!LL_RELEASE_FOR_DOWNLOAD) + // OpenAL likes to crash on exit if we *don't* explicitly shut it down. if (gAudiop) { gAudiop->shutdown(); diff --git a/linden/indra/newview/llstartup.cpp b/linden/indra/newview/llstartup.cpp index 0978fbb..941787b 100644 --- a/linden/indra/newview/llstartup.cpp +++ b/linden/indra/newview/llstartup.cpp @@ -45,6 +45,10 @@ # include "audioengine_fmod.h" #endif +#ifdef LL_OPENAL +#include "audioengine_openal.h" +#endif + #include "llares.h" #include "llcachename.h" #include "llviewercontrol.h" @@ -579,10 +583,17 @@ bool idle_startup() if (FALSE == gSavedSettings.getBOOL("NoAudio")) { + gAudiop = NULL; + #ifdef LL_FMOD gAudiop = (LLAudioEngine *) new LLAudioEngine_FMOD(); -#else - gAudiop = NULL; +#endif + +#ifdef LL_OPENAL + if (!gAudiop) + { + gAudiop = (LLAudioEngine *) new LLAudioEngine_OpenAL(); + } #endif if (gAudiop) @@ -595,11 +606,16 @@ bool idle_startup() void* window_handle = NULL; #endif bool init = gAudiop->init(kAUDIO_NUM_SOURCES, window_handle); - if(!init) + if(init) + { + gAudiop->setMuted(TRUE); + } + else { LL_WARNS("AppInit") << "Unable to initialize audio engine" << LL_ENDL; + delete gAudiop; + gAudiop = NULL; } - gAudiop->setMuted(TRUE); } } -- cgit v1.1 From d45dcd8daa6a02405ea9fc1f4824ec92fe73f7b2 Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Wed, 19 Nov 2008 17:02:10 -0600 Subject: Package up OpenAL libs. --- linden/indra/newview/viewer_manifest.py | 25 +++++++++++++++---------- 1 file changed, 15 insertions(+), 10 deletions(-) (limited to 'linden') diff --git a/linden/indra/newview/viewer_manifest.py b/linden/indra/newview/viewer_manifest.py index be28809..bdf537a 100755 --- a/linden/indra/newview/viewer_manifest.py +++ b/linden/indra/newview/viewer_manifest.py @@ -208,18 +208,20 @@ class WindowsManifest(ViewerManifest): self.end_prefix() # Vivox runtimes - #if self.prefix(src="vivox-runtime/i686-win32", dst=""): + if self.prefix(src="vivox-runtime/i686-win32", dst=""): + self.path("alut.dll") + self.path("wrap_oal.dll") + # self.path("SLVoice.exe") # self.path("SLVoiceAgent.exe") # self.path("libeay32.dll") # self.path("srtp.dll") # self.path("ssleay32.dll") # self.path("tntk.dll") - # self.path("alut.dll") # self.path("vivoxsdk.dll") # self.path("ortp.dll") - # self.path("wrap_oal.dll") - # self.end_prefix() + + self.end_prefix() # # pull in the crash logger and updater from other projects # self.path(src=self.find_existing_file( # tag:"crash-logger" here as a cue to the exporter @@ -398,9 +400,10 @@ class DarwinManifest(ViewerManifest): self.path("Japanese.lproj") self.path("Korean.lproj") + # SLVoice and vivox lols - #self.path("vivox-runtime/universal-darwin/libalut.dylib", "libalut.dylib") - #self.path("vivox-runtime/universal-darwin/libopenal.dylib", "libopenal.dylib") + self.path("vivox-runtime/universal-darwin/libalut.dylib", "libalut.dylib") + self.path("vivox-runtime/universal-darwin/libopenal.dylib", "libopenal.dylib") #self.path("vivox-runtime/universal-darwin/libortp.dylib", "libortp.dylib") #self.path("vivox-runtime/universal-darwin/libvivoxsdk.dylib", "libvivoxsdk.dylib") #self.path("vivox-runtime/universal-darwin/SLVoice", "SLVoice") @@ -625,18 +628,20 @@ class Linux_i686Manifest(LinuxManifest): #self.path("libtcmalloc.so.0") - bugged #self.path("libstacktrace.so.0") - probably bugged # self.path("libllkdu.so", "../bin/libllkdu.so") # llkdu goes in bin for some reason + self.end_prefix("lib") # Vivox runtimes #if self.prefix(src="vivox-runtime/i686-linux", dst="bin"): # self.path("SLVoice") # self.end_prefix() - #if self.prefix(src="vivox-runtime/i686-linux", dst="lib"): - # self.path("libopenal.so.1") + + if self.prefix(src="vivox-runtime/i686-linux", dst="lib"): + self.path("libopenal.so.1") + self.path("libalut.so") # self.path("libortp.so") # self.path("libvivoxsdk.so") - # self.path("libalut.so") - # self.end_prefix("lib") + self.end_prefix("lib") class Linux_x86_64Manifest(LinuxManifest): def construct(self): -- cgit v1.1 From e563b107a2b58935ef8c3ab2cfdfdbc2d7cdfa2d Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Wed, 19 Nov 2008 19:48:44 -0600 Subject: (Forgot to check this file in with the OpenAL patch.) --- linden/indra/cmake/OPENAL.cmake | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 linden/indra/cmake/OPENAL.cmake (limited to 'linden') diff --git a/linden/indra/cmake/OPENAL.cmake b/linden/indra/cmake/OPENAL.cmake new file mode 100644 index 0000000..b0d9dac --- /dev/null +++ b/linden/indra/cmake/OPENAL.cmake @@ -0,0 +1,14 @@ +# -*- cmake -*- + +set(OPENAL OFF CACHE BOOL "Enable OpenAL") + +if (OPENAL) + include(FindPkgConfig) + pkg_check_modules(OPENAL_LIB REQUIRED openal) + pkg_check_modules(FREEAULT_LIB REQUIRED freealut) + set(OPENAL_LIBRARIES + openal + alut + ) + +endif (OPENAL) -- cgit v1.1 From bb5e735d6e9c1a0179a10b838d8126bd301649d8 Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Thu, 20 Nov 2008 12:54:34 -0600 Subject: Enable OpenAL by default. Configure with -DOPENAL:BOOL=OFF to disable. --- linden/indra/cmake/OPENAL.cmake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'linden') diff --git a/linden/indra/cmake/OPENAL.cmake b/linden/indra/cmake/OPENAL.cmake index b0d9dac..1849fbf 100644 --- a/linden/indra/cmake/OPENAL.cmake +++ b/linden/indra/cmake/OPENAL.cmake @@ -1,6 +1,6 @@ # -*- cmake -*- -set(OPENAL OFF CACHE BOOL "Enable OpenAL") +set(OPENAL ON CACHE BOOL "Enable OpenAL") if (OPENAL) include(FindPkgConfig) -- cgit v1.1 From 285dcc2660ef0ed31bfbdc4f0a5cc53f40e90e36 Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Fri, 21 Nov 2008 22:11:19 -0600 Subject: (Oops, bad indentation in viewer_manifest.py) --- linden/indra/newview/viewer_manifest.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'linden') diff --git a/linden/indra/newview/viewer_manifest.py b/linden/indra/newview/viewer_manifest.py index bdf537a..cbc9a84 100755 --- a/linden/indra/newview/viewer_manifest.py +++ b/linden/indra/newview/viewer_manifest.py @@ -221,7 +221,7 @@ class WindowsManifest(ViewerManifest): # self.path("vivoxsdk.dll") # self.path("ortp.dll") - self.end_prefix() + self.end_prefix() # # pull in the crash logger and updater from other projects # self.path(src=self.find_existing_file( # tag:"crash-logger" here as a cue to the exporter -- cgit v1.1 From b4e5b8567b18a9289b912c720255a7f5d3bcdbf1 Mon Sep 17 00:00:00 2001 From: Jacek Antonelli Date: Fri, 21 Nov 2008 21:25:58 -0600 Subject: Cross-platform checking for OpenAL libs. --- linden/indra/cmake/LLAudio.cmake | 1 + linden/indra/cmake/OPENAL.cmake | 83 +++++++++++++++++++++++++++++++++++++--- 2 files changed, 78 insertions(+), 6 deletions(-) (limited to 'linden') diff --git a/linden/indra/cmake/LLAudio.cmake b/linden/indra/cmake/LLAudio.cmake index 893aa68..dcfd269 100644 --- a/linden/indra/cmake/LLAudio.cmake +++ b/linden/indra/cmake/LLAudio.cmake @@ -5,6 +5,7 @@ include(OPENAL) set(LLAUDIO_INCLUDE_DIRS ${LIBS_OPEN_DIR}/llaudio + ${OPENAL_INCLUDE_DIRS} ) set(LLAUDIO_LIBRARIES diff --git a/linden/indra/cmake/OPENAL.cmake b/linden/indra/cmake/OPENAL.cmake index 1849fbf..277e3f9 100644 --- a/linden/indra/cmake/OPENAL.cmake +++ b/linden/indra/cmake/OPENAL.cmake @@ -2,13 +2,84 @@ set(OPENAL ON CACHE BOOL "Enable OpenAL") + if (OPENAL) - include(FindPkgConfig) - pkg_check_modules(OPENAL_LIB REQUIRED openal) - pkg_check_modules(FREEAULT_LIB REQUIRED freealut) - set(OPENAL_LIBRARIES - openal - alut + + # message(STATUS "Building with OpenAL audio support") + + # OPENAL_LIB + + find_library(OPENAL_LIB + NAMES openal OpenAL OpenAL32 wrap_oal + PATHS ${ARCH_PREBUILT_DIRS_RELEASE} + ) + + if (NOT OPENAL_LIB) + message(FATAL_ERROR "OpenAL not found!") + else (NOT OPENAL_LIB) + # message(STATUS "OpenAL found: ${OPENAL_LIB}") + endif (NOT OPENAL_LIB) + + + + # OPENAL_INCLUDE_DIR + + find_path(OPENAL_INCLUDE_DIR + NAMES al.h + PATHS ${LIBS_PREBUILT_DIR}/include + ) + + if (NOT OPENAL_INCLUDE_DIR) + message(FATAL_ERROR "al.h not found!") + else (NOT OPENAL_INCLUDE_DIR) + # message(STATUS "al.h found in: ${OPENAL_INCLUDE_DIR}") + endif (NOT OPENAL_INCLUDE_DIR) + + + + # ALUT_LIB + + find_library(ALUT_LIB + NAMES alut freealut + PATHS ${ARCH_PREBUILT_DIRS_RELEASE} + ) + + if (NOT ALUT_LIB) + message(FATAL_ERROR "ALUT not found!") + else (NOT ALUT_LIB) + # message(STATUS "ALUT found: ${ALUT_LIB}") + endif (NOT ALUT_LIB) + + + + # ALUT_INCLUDE_DIR + + find_path(ALUT_INCLUDE_DIR + NAMES alut.h + PATHS ${LIBS_PREBUILT_DIR}/include + ) + + if (NOT ALUT_INCLUDE_DIR) + message(FATAL_ERROR "alut.h not found!") + else (NOT ALUT_INCLUDE_DIR) + # message(STATUS "alut.h found in: ${ALUT_INCLUDE_DIR}") + endif (NOT ALUT_INCLUDE_DIR) + + + + set(OPENAL_LIBRARIES + ${OPENAL_LIB} + ${ALUT_LIB} + ) + + set(OPENAL_INCLUDE_DIRS + ${OPENAL_INCLUDE_DIR} + ${ALUT_INCLUDE_DIR} ) + + set(OPENAL_FOUND TRUE CACHE BOOL + "Found OpenAL and ALUT libraries successfully" + ) + endif (OPENAL) -- cgit v1.1 From 73d23531e60425993305dbcd6e1f12eb4da79d2c Mon Sep 17 00:00:00 2001 From: McCabe Maxsted Date: Sun, 23 Nov 2008 20:22:10 -0700 Subject: Trying to get openal working --- linden/indra/llaudio/audioengine_openal.cpp | 4 ++-- linden/indra/llaudio/listener_openal.h | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) (limited to 'linden') diff --git a/linden/indra/llaudio/audioengine_openal.cpp b/linden/indra/llaudio/audioengine_openal.cpp index 606d9f6..85d2080 100644 --- a/linden/indra/llaudio/audioengine_openal.cpp +++ b/linden/indra/llaudio/audioengine_openal.cpp @@ -321,10 +321,10 @@ void LLAudioEngine_OpenAL::updateWind(LLVector3 wind_vec, F32 camera_altitude) mMaxWindGain=1.0; - if (!mEnableWind) + if (mEnableWind) return; - if(!winddata) + if(winddata) return; if (mWindUpdateTimer.checkExpirationAndReset(LL_WIND_UPDATE_INTERVAL)) diff --git a/linden/indra/llaudio/listener_openal.h b/linden/indra/llaudio/listener_openal.h index 737343e..33063bb 100644 --- a/linden/indra/llaudio/listener_openal.h +++ b/linden/indra/llaudio/listener_openal.h @@ -35,8 +35,8 @@ #include "listener.h" -#include "AL/al.h" -#include "AL/alut.h" +#include "al.h" +#include "alut.h" class LLListener_OpenAL : public LLListener { -- cgit v1.1 From 65272bae7013a785cb4e1dccb810e58e9f7fdfda Mon Sep 17 00:00:00 2001 From: McCabe Maxsted Date: Sat, 6 Dec 2008 09:18:52 -0700 Subject: updated to RC2 --- .../xui/en-us/floater_instant_message_group.xml | 164 ++++++++++----------- 1 file changed, 82 insertions(+), 82 deletions(-) (limited to 'linden') diff --git a/linden/indra/newview/skins/default/xui/en-us/floater_instant_message_group.xml b/linden/indra/newview/skins/default/xui/en-us/floater_instant_message_group.xml index be18c7e..72c92bd 100644 --- a/linden/indra/newview/skins/default/xui/en-us/floater_instant_message_group.xml +++ b/linden/indra/newview/skins/default/xui/en-us/floater_instant_message_group.xml @@ -1,82 +1,82 @@ - - - - Joining Voice Chat... - - - Connected, click End Call to hang up - - - Left Voice Chat - - - icn_voice-groupfocus.tga - - - *** Welcome to Help Request *** - Please first check our SL Help Pages by pressing F1, or by accessing the Knowledge Base http://secondlife.com/knowledgebase/ - If your answer is not there, please enter your question to begin, then allow a few moments for available helpers to respond. - -=-=- Response times will vary, especially during peak times -=-=- - - - Instant Message with [NAME] - - - [NAME] is typing... - - - Starting session with [NAME], please wait. - - - (Moderated: Voices off by default) - - - Click here to instant message. - - - Your text chat has been disabled by a Group Moderator. - - - -