Added to various functions a check whether an OpenAL source exists on which OpenAL functions can be called.

Playback of background music starts now with the previously set volume, independent of the OpenAL source state.
Added a delete on the SimpleSoundEngine object within CocosDenshionTest::onExit() so that alutExit() gets called to release allocated resources by OpenAL.
This commit is contained in:
rafael.x 2013-07-19 01:00:24 +02:00
parent 3d23b65ad9
commit c4ef2c9250
3 changed files with 64 additions and 19 deletions

View File

@ -57,6 +57,8 @@ static inline unsigned int getHashCodeByString(const char *key)
/** /**
@class SimpleAudioEngine @class SimpleAudioEngine
@brief Offers a VERY simple interface to play background music & sound effects. @brief Offers a VERY simple interface to play background music & sound effects.
@note Make sure to call SimpleAudioEngine::end() when the sound engine is not needed anymore
to release allocated resources.
*/ */
class EXPORT_DLL SimpleAudioEngine : public TypeInfo class EXPORT_DLL SimpleAudioEngine : public TypeInfo
@ -76,26 +78,26 @@ public:
/** /**
@brief Release the shared Engine object @brief Release the shared Engine object
@warning It must be called before the application exit, or a memroy leak will be caused. @warning It must be called before the application exit, or a memory leak will be caused.
*/ */
static void end(); static void end();
/** /**
@brief Preload background music @brief Preload background music
@param pszFilePath The path of the background music file, or the FileName of T_SoundResInfo @param pszFilePath The path of the background music file.
*/ */
void preloadBackgroundMusic(const char* pszFilePath); void preloadBackgroundMusic(const char* pszFilePath);
/** /**
@brief Play background music @brief Play background music
@param pszFilePath The path of the background music file, or the FileName of T_SoundResInfo @param pszFilePath The path of the background music file.
@param bLoop Determines whether the background music should loop or not @param bLoop Determines whether the background music should loop or not.
*/ */
void playBackgroundMusic(const char* pszFilePath, bool bLoop); void playBackgroundMusic(const char* pszFilePath, bool bLoop);
/** /**
@brief Play background music once @brief Play background music once
@param pszFilePath The path of the background music file, or the FileName of T_SoundResInfo @param pszFilePath The path of the background music file.
@see CocosDenshion::playBackgroundMusic(const char* pszFilePath, bool bLoop) @see CocosDenshion::playBackgroundMusic(const char* pszFilePath, bool bLoop)
*/ */
void playBackgroundMusic(const char* pszFilePath) { void playBackgroundMusic(const char* pszFilePath) {
@ -134,7 +136,6 @@ public:
/** /**
@brief Indicates whether any background music can be played or not. @brief Indicates whether any background music can be played or not.
@return <i>true</i> if background music can be played, otherwise <i>false</i>. @return <i>true</i> if background music can be played, otherwise <i>false</i>.
@remark Returns currently always true.
*/ */
bool willPlayBackgroundMusic(); bool willPlayBackgroundMusic();
@ -155,7 +156,7 @@ public:
/** /**
@brief Set the volume of background music @brief Set the volume of background music
@param volume must be within the range of 0.0 as the minimum and 1.0 as the maximum @param volume must be within the range of 0.0 as the minimum and 1.0 as the maximum.
*/ */
void setBackgroundMusicVolume(float volume); void setBackgroundMusicVolume(float volume);
@ -166,7 +167,7 @@ public:
/** /**
@brief Set the volume of sound effects @brief Set the volume of sound effects
@param volume must be within the range of 0.0 as the minimum and 1.0 as the maximum @param volume must be within the range of 0.0 as the minimum and 1.0 as the maximum.
*/ */
void setEffectsVolume(float volume); void setEffectsVolume(float volume);
@ -176,7 +177,7 @@ public:
/** /**
@brief Play sound effect @brief Play sound effect
@param pszFilePath The path of the effect file, or the FileName of T_SoundResInfo @param pszFilePath The path of the effect file.
@param bLoop Determines whether to loop the effect playing or not. The default value is false. @param bLoop Determines whether to loop the effect playing or not. The default value is false.
*/ */
unsigned int playEffect(const char* pszFilePath, bool bLoop) { unsigned int playEffect(const char* pszFilePath, bool bLoop) {
@ -185,7 +186,7 @@ public:
/** /**
@brief Play sound effect once @brief Play sound effect once
@param pszFilePath The path of the effect file, or the FileName of T_SoundResInfo @param pszFilePath The path of the effect file.
@see CocosDenshion::playEffect(const char* pszFilePath, bool bLoop) @see CocosDenshion::playEffect(const char* pszFilePath, bool bLoop)
*/ */
unsigned int playEffect(const char* pszFilePath) { unsigned int playEffect(const char* pszFilePath) {
@ -194,7 +195,7 @@ public:
/** /**
@brief Play sound effect with a file path, pitch, pan and gain @brief Play sound effect with a file path, pitch, pan and gain
@param pszFilePath The path of the effect file, or the FileName of T_SoundResInfo @param pszFilePath The path of the effect file.
@param bLoop Determines whether to loop the effect playing or not. The default value is false. @param bLoop Determines whether to loop the effect playing or not. The default value is false.
@param pitch Frequency, normal value is 1.0. Will also change effect play time. @param pitch Frequency, normal value is 1.0. Will also change effect play time.
@param pan Stereo effect, in the range of [-1..1] where -1 enables only left channel. @param pan Stereo effect, in the range of [-1..1] where -1 enables only left channel.
@ -246,13 +247,13 @@ public:
/** /**
@brief preload a compressed audio file @brief preload a compressed audio file
@details the compressed audio will be decoded to wave, then written into an internal buffer in SimpleAudioEngine @details the compressed audio will be decoded to wave, then written into an internal buffer in SimpleAudioEngine
@param pszFilePath The path of the effect file, or the FileName of T_SoundResInfo @param pszFilePath The path of the effect file
*/ */
void preloadEffect(const char* pszFilePath); void preloadEffect(const char* pszFilePath);
/** /**
@brief unload the preloaded effect from internal buffer @brief unload the preloaded effect from internal buffer
@param pszFilePath The path of the effect file, or the FileName of T_SoundResInfo @param pszFilePath The path of the effect file
*/ */
void unloadEffect(const char* pszFilePath); void unloadEffect(const char* pszFilePath);
}; };

View File

@ -111,7 +111,12 @@ namespace CocosDenshion
static void stopBackground(bool bReleaseData) static void stopBackground(bool bReleaseData)
{ {
alSourceStop(s_backgroundSource); // The background music might have been already stopped
// Stop request can come from
// - stopBackgroundMusic(..)
// - end(..)
if (s_backgroundSource != AL_NONE)
alSourceStop(s_backgroundSource);
if (bReleaseData) if (bReleaseData)
{ {
@ -130,7 +135,7 @@ namespace CocosDenshion
} }
} }
s_backgroundSource = AL_NONE; s_backgroundSource = AL_NONE;
} }
static void setBackgroundVolume(float volume) static void setBackgroundVolume(float volume)
@ -246,6 +251,7 @@ namespace CocosDenshion
void SimpleAudioEngine::playBackgroundMusic(const char* pszFilePath, bool bLoop) void SimpleAudioEngine::playBackgroundMusic(const char* pszFilePath, bool bLoop)
{ {
// If there is already a background music source we stop it first
if (s_backgroundSource != AL_NONE) if (s_backgroundSource != AL_NONE)
stopBackgroundMusic(false); stopBackgroundMusic(false);
@ -263,6 +269,7 @@ namespace CocosDenshion
{ {
s_backgroundSource = it->second->source; s_backgroundSource = it->second->source;
alSourcei(s_backgroundSource, AL_LOOPING, bLoop ? AL_TRUE : AL_FALSE); alSourcei(s_backgroundSource, AL_LOOPING, bLoop ? AL_TRUE : AL_FALSE);
setBackgroundVolume(s_volume);
alSourcePlay(s_backgroundSource); alSourcePlay(s_backgroundSource);
checkALError("playBackgroundMusic:alSourcePlay"); checkALError("playBackgroundMusic:alSourcePlay");
} }
@ -270,6 +277,10 @@ namespace CocosDenshion
void SimpleAudioEngine::stopBackgroundMusic(bool bReleaseData) void SimpleAudioEngine::stopBackgroundMusic(bool bReleaseData)
{ {
// If there is no source, then there is nothing that can be stopped
if (s_backgroundSource == AL_NONE)
return;
ALint state; ALint state;
alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state); alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state);
if (state == AL_PLAYING) if (state == AL_PLAYING)
@ -278,27 +289,43 @@ namespace CocosDenshion
void SimpleAudioEngine::pauseBackgroundMusic() void SimpleAudioEngine::pauseBackgroundMusic()
{ {
// If there is no source, then there is nothing that can be paused
if (s_backgroundSource == AL_NONE)
return;
ALint state; ALint state;
alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state); alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state);
if (state == AL_PLAYING) if (state == AL_PLAYING)
alSourcePause(s_backgroundSource); alSourcePause(s_backgroundSource);
checkALError("pauseBackgroundMusic:alSourcePause"); checkALError("pauseBackgroundMusic:alSourcePause");
} }
void SimpleAudioEngine::resumeBackgroundMusic() void SimpleAudioEngine::resumeBackgroundMusic()
{ {
// If there is no source, then there is nothing that can be resumed
if (s_backgroundSource == AL_NONE)
return;
ALint state; ALint state;
alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state); alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state);
if (state == AL_PAUSED) if (state == AL_PAUSED)
alSourcePlay(s_backgroundSource); alSourcePlay(s_backgroundSource);
checkALError("resumeBackgroundMusic:alSourcePlay");
checkALError("resumeBackgroundMusic:alSourcePlay");
} }
void SimpleAudioEngine::rewindBackgroundMusic() void SimpleAudioEngine::rewindBackgroundMusic()
{ {
// If there is no source, then there is nothing that can be rewinded
if (s_backgroundSource == AL_NONE)
return;
// Rewind and prevent the last state the source had
ALint state; ALint state;
alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state); alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &state);
alSourceRewind(s_backgroundSource); alSourceRewind(s_backgroundSource);
if (state == AL_PLAYING) if (state == AL_PLAYING)
{ {
alSourcePlay(s_backgroundSource); alSourcePlay(s_backgroundSource);
@ -313,13 +340,23 @@ namespace CocosDenshion
bool SimpleAudioEngine::willPlayBackgroundMusic() bool SimpleAudioEngine::willPlayBackgroundMusic()
{ {
return true; // We are able to play background music
// if we have a valid background source
if (s_backgroundSource == AL_NONE)
return false;
return (alIsSource(s_backgroundSource) == AL_TRUE ? true : false);
} }
bool SimpleAudioEngine::isBackgroundMusicPlaying() bool SimpleAudioEngine::isBackgroundMusicPlaying()
{ {
// If there is no source, then there is nothing that is playing
if (s_backgroundSource == AL_NONE)
return false;
ALint play_status; ALint play_status;
alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &play_status); alGetSourcei(s_backgroundSource, AL_SOURCE_STATE, &play_status);
checkALError("isBackgroundMusicPlaying:alGetSourcei");
return (play_status == AL_PLAYING); return (play_status == AL_PLAYING);
} }
@ -331,11 +368,17 @@ namespace CocosDenshion
void SimpleAudioEngine::setBackgroundMusicVolume(float volume) void SimpleAudioEngine::setBackgroundMusicVolume(float volume)
{ {
if (s_volume != volume && volume >= -0.0001 && volume <= 1.0001) if (s_volume != volume && volume >= -0.0001 && volume <= 1.0001)
{ {
s_volume = volume; s_volume = volume;
setBackgroundVolume(volume); // No source, no background music, no volume adjustment
if (s_backgroundSource != AL_NONE)
{
setBackgroundVolume(volume);
}
} }
} }

View File

@ -247,6 +247,7 @@ void CocosDenshionTest::onExit()
Layer::onExit(); Layer::onExit();
SimpleAudioEngine::sharedEngine()->end(); SimpleAudioEngine::sharedEngine()->end();
delete SimpleAudioEngine::sharedEngine();
} }
void CocosDenshionTest::addButtons() void CocosDenshionTest::addButtons()