Index: code/branches/pickup/src/orxonox/sound/SoundManager.cc
===================================================================
--- code/branches/pickup/src/orxonox/sound/SoundManager.cc	(revision 5815)
+++ code/branches/pickup/src/orxonox/sound/SoundManager.cc	(revision 5935)
@@ -31,63 +31,60 @@
 #include <AL/alut.h>
 
+#include "util/Exception.h"
 #include "util/Math.h"
-#include "CameraManager.h"
-#include "graphics/Camera.h"
-#include "SoundBase.h"
+#include "util/ScopeGuard.h"
+#include "core/GameMode.h"
+#include "core/ScopedSingletonManager.h"
 
 namespace orxonox
 {
     SoundManager* SoundManager::singletonPtr_s = NULL;
+    ManageScopedSingleton(SoundManager, ScopeID::Graphics, true);
 
-    /**
-     * Default constructor
-     */
     SoundManager::SoundManager()
     {
-        this->device_ = NULL;
-        this->soundavailable_ = true;
-        if(!alutInitWithoutContext(NULL,NULL))
+        if (!alutInitWithoutContext(NULL,NULL))
+            ThrowException(InitialisationFailed, "OpenAL ALUT error: " << alutGetErrorString(alutGetError()));
+        Loki::ScopeGuard alutExitGuard = Loki::MakeGuard(&alutExit);
+
+        COUT(3) << "OpenAL: Opening sound device..." << std::endl;
+        this->device_ = alcOpenDevice(NULL);
+        if (this->device_ == NULL)
         {
-            COUT(2) << "Sound: OpenAL ALUT: " << alutGetErrorString(alutGetError()) << std::endl;
-            this->soundavailable_ = false;
+            COUT(0) << "OpenaAL: Could not open sound device. Have you installed OpenAL?" << std::endl;
+#ifdef ORXONOX_PLATFORM_WINDOWS
+            COUT(0) << "Just getting the DLL with the dependencies is not enough for Windows (esp. Windows 7)!" << std::endl;
+#endif
+            ThrowException(InitialisationFailed, "OpenAL error: Could not open sound device.");
         }
+        Loki::ScopeGuard closeDeviceGuard = Loki::MakeGuard(&alcCloseDevice, this->device_);
+
+        COUT(3) << "OpenAL: Sound device opened" << std::endl;
+        this->context_ = alcCreateContext(this->device_, NULL);
+        if (this->context_ == NULL)
+            ThrowException(InitialisationFailed, "OpenAL error: Could not create sound context");
+        Loki::ScopeGuard desroyContextGuard = Loki::MakeGuard(&alcDestroyContext, this->context_);
+
+        if (alcMakeContextCurrent(this->context_) == AL_TRUE)
+            COUT(3) << "OpenAL: Context " << this->context_ << " loaded" << std::endl;
+
+        COUT(4) << "Sound: OpenAL ALUT version: " << alutGetMajorVersion() << "." << alutGetMinorVersion() << std::endl;
+
+        const char* str = alutGetMIMETypes(ALUT_LOADER_BUFFER);
+        if (str == NULL)
+            COUT(2) << "OpenAL ALUT error: " << alutGetErrorString(alutGetError()) << std::endl;
         else
-        {
-            assert(this->device_ == NULL);
-            COUT(3) << "Sound: OpenAL: Open sound device..." << std::endl;
-            this->device_ = alcOpenDevice(NULL);
+            COUT(4) << "OpenAL ALUT supported MIME types: " << str << std::endl;
 
-            if(this->device_ == NULL)
-            {
-                COUT(2) << "Sound: OpenAL: Could not open sound device" << std::endl;
-                this->soundavailable_ = false;
-            }
-            else
-            {
-                COUT(3) << "Sound: OpenAL: Sound device opened" << std::endl;
-                this->context_ = alcCreateContext(this->device_, NULL);
-                if(this->context_ == NULL)
-                {
-                    COUT(2) << "Sound: OpenAL: Could not create sound context" << std::endl;
-                    this->soundavailable_ = false;
-                }
-                else
-                {
-                    if(alcMakeContextCurrent(this->context_) == AL_TRUE)
-                        COUT(3) << "Sound: OpenAL: Context " << this->context_ << " loaded" << std::endl;
-
-                    COUT(4) << "Sound: OpenAL ALUT version: " << alutGetMajorVersion() << "." << alutGetMinorVersion() << std::endl;
-                    const char* str = alutGetMIMETypes(ALUT_LOADER_BUFFER);
-                    if (str == NULL)
-                        COUT(2) << "Sound: OpenAL ALUT: " << alutGetErrorString(alutGetError()) << std::endl;
-                    else
-                        COUT(4) << "Sound: OpenAL ALUT supported MIME types: " << str << std::endl;
-                }
-            }
-        }
+        GameMode::setPlaysSound(true);
+        // Disarm guards
+        alutExitGuard.Dismiss();
+        closeDeviceGuard.Dismiss();
+        desroyContextGuard.Dismiss();
     }
 
     SoundManager::~SoundManager()
     {
+        GameMode::setPlaysSound(false);
         alcDestroyContext(this->context_);
         alcCloseDevice(this->device_);
@@ -95,74 +92,25 @@
     }
 
-    /**
-     * Add a SoundBase object to the list. Every SoundBase object should be in
-     * this list.
-     *
-     * @param sound Pointer to the SoundBase object to add
-     */
-    void SoundManager::addSound(SoundBase* sound)
+    void SoundManager::setListenerPosition(const Vector3& position)
     {
-        this->soundlist_.push_back(sound);
+        alListener3f(AL_POSITION, position.x, position.y, position.z);
+        ALenum error = alGetError();
+        if (error == AL_INVALID_VALUE)
+            COUT(2) << "Sound: OpenAL: Invalid listener position" << std::endl;
     }
 
-    /**
-     * Remove a SoundBase object from the list and destroy it.
-     */
-    void SoundManager::removeSound(SoundBase* sound)
+    void SoundManager::setListenerOrientation(const Quaternion& orientation)
     {
-        std::list<SoundBase*>::iterator pos = this->soundlist_.end();
-        for(std::list<SoundBase*>::iterator i = this->soundlist_.begin(); i != this->soundlist_.end(); i++)
-        {
-            if((*i) == sound)
-                pos = i;
-        }
+        // update listener orientation
+        Vector3 up = orientation.xAxis(); // just a wild guess
+        Vector3 at = orientation.zAxis();
 
-        delete (*pos);
-        this->soundlist_.erase(pos);
-    }
+        ALfloat orient[6] = { at.x, at.y, at.z,
+                              up.x, up.y, up.z };
 
-    /**
-     * Tick function, updates listener and registred SoundBase objects
-     *
-     * @param dt @see Orxonox::Tickable
-     */
-    void SoundManager::tick(float dt)
-    {
-        if (!CameraManager::getInstancePtr())
-            return;
-
-        // update listener position
-        Camera* camera = CameraManager::getInstance().getActiveCamera();
-        if(camera == NULL) return;
-        Vector3 pos = camera->getPosition();
-        alListener3f(AL_POSITION, pos.x, pos.y, pos.z);
+        alListenerfv(AL_POSITION, orient);
         ALenum error = alGetError();
-        if(error == AL_INVALID_VALUE)
-            COUT(2) << "Sound: OpenAL: Invalid listener position" << std::endl;
-
-        // update listener orientation
-        const Quaternion& orient = camera->getOrientation();
-        Vector3 up = orient.xAxis(); // just a wild guess
-        Vector3 at = orient.zAxis();
-
-        ALfloat orientation[6] = { at.x, at.y, at.z,
-                                 up.x, up.y, up.z };
-
-        alListenerfv(AL_POSITION, orientation);
-        error = alGetError();
-        if(error == AL_INVALID_VALUE)
+        if (error == AL_INVALID_VALUE)
             COUT(2) << "Sound: OpenAL: Invalid listener orientation" << std::endl;
-
-        // update sounds
-        for(std::list<SoundBase*>::iterator i = this->soundlist_.begin(); i != this->soundlist_.end(); i++)
-            (*i)->update();
-    }
-
-    /**
-    * Check if sound is available
-    */
-    bool SoundManager::isSoundAvailable()
-    {
-        return this->soundavailable_;
     }
 }
