Browse Source

Audio system registration, start-up and shutdown

BearishSun 9 years ago
parent
commit
3cf4301a82

+ 2 - 0
Source/BansheeCore/CMakeSources.cmake

@@ -474,6 +474,7 @@ set(BS_BANSHEECORE_INC_AUDIO
 	"Include/BsAudioSource.h"
 	"Include/BsAudioClipImportOptions.h"
 	"Include/BsAudioUtility.h"
+	"Include/BsAudioManager.h"
 )
 
 set(BS_BANSHEECORE_SRC_AUDIO
@@ -483,6 +484,7 @@ set(BS_BANSHEECORE_SRC_AUDIO
 	"Source/BsAudioSource.cpp"
 	"Source/BsAudioClipImportOptions.cpp"
 	"Source/BsAudioUtility.cpp"
+	"Source/BsAudioManager.cpp"
 )
 
 source_group("Header Files\\Components" FILES ${BS_BANSHEECORE_INC_COMPONENTS})

+ 45 - 0
Source/BansheeCore/Include/BsAudioManager.h

@@ -0,0 +1,45 @@
+//********************************** Banshee Engine (www.banshee3d.com) **************************************************//
+//**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
+#pragma once
+
+#include "BsCorePrerequisites.h"
+#include "BsModule.h"
+
+namespace BansheeEngine
+{
+	/** @addtogroup Audio-Internal
+	 *  @{
+	 */
+
+	/** Creates and destroys a specific audio system implementation. */
+	class BS_CORE_EXPORT AudioFactory
+	{
+	public:
+		virtual ~AudioFactory() { }
+
+		/** Initializes the audio system. */
+		virtual void startUp() = 0;
+
+		/** Shuts down the audio system. */
+		virtual void shutDown() = 0;
+	};
+
+	/** Takes care of loading, initializing and shutting down of a particular audio system implementation. */
+	class BS_CORE_EXPORT AudioManager : public Module<AudioManager>
+	{
+	public:
+		/** 
+		 * Initializes the physics manager and a particular audio system implementation. 
+		 *
+		 * @param[in]	pluginName	Name of the plugin containing a audio system implementation.
+		 */
+		AudioManager(const String& pluginName);
+		~AudioManager();
+
+	private:
+		DynLib* mPlugin;
+		AudioFactory* mFactory;
+	};
+
+	/** @} */
+}

+ 1 - 0
Source/BansheeCore/Include/BsCoreApplication.h

@@ -20,6 +20,7 @@ namespace BansheeEngine
 		String renderAPI; /**< Name of the render system plugin to use. */
 		String renderer; /**< Name of the renderer plugin to use. */
 		String physics; /**< Name of physics plugin to use. */
+		String audio; /**< Name of the audio plugin to use. */
 		String input; /**< Name of the input plugin to use. */
 
 		RENDER_WINDOW_DESC primaryWindowDesc; /**< Describes the window to create during start-up. */

+ 4 - 0
Source/BansheeCore/Include/BsCorePrerequisites.h

@@ -144,6 +144,10 @@
  *	Physics system: colliders, triggers, rigidbodies, joints, scene queries, etc.
  */
 
+/** @defgroup Audio-Internal Audio
+ *	Audio clips, 3D sound and music reproduction.
+ */
+
 /** @} */
 
 /** @} */

+ 43 - 0
Source/BansheeCore/Source/BsAudioManager.cpp

@@ -0,0 +1,43 @@
+//********************************** Banshee Engine (www.banshee3d.com) **************************************************//
+//**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
+#include "BsAudioManager.h"
+#include "BsDynLibManager.h"
+#include "BsDynLib.h"
+
+namespace BansheeEngine
+{
+	AudioManager::AudioManager(const String& pluginName)
+		:mPlugin(nullptr), mFactory(nullptr)
+	{
+		mPlugin = DynLibManager::instance().load(pluginName);
+
+		if(mPlugin != nullptr)
+		{
+			typedef AudioFactory* (*LoadPluginFunc)();
+
+			LoadPluginFunc loadPluginFunc = (LoadPluginFunc)mPlugin->getSymbol("loadPlugin");
+			mFactory = loadPluginFunc();
+
+			if (mFactory != nullptr)
+				mFactory->startUp();
+		}
+	}
+
+	AudioManager::~AudioManager()
+	{
+		if (mPlugin != nullptr)
+		{
+			if (mFactory != nullptr)
+			{
+				typedef void (*UnloadPluginFunc)(AudioFactory*);
+
+				UnloadPluginFunc unloadPluginFunc = (UnloadPluginFunc)mPlugin->getSymbol("unloadPlugin");
+
+				mFactory->shutDown();
+				unloadPluginFunc(mFactory);
+			}
+
+			DynLibManager::instance().unload(mPlugin);
+		}
+	}
+}

+ 5 - 0
Source/BansheeCore/Source/BsCoreApplication.cpp

@@ -45,6 +45,8 @@
 #include "BsShaderManager.h"
 #include "BsPhysicsManager.h"
 #include "BsPhysics.h"
+#include "BsAudioManager.h"
+#include "BsAudio.h"
 
 namespace BansheeEngine
 {
@@ -77,6 +79,7 @@ namespace BansheeEngine
 		// This must be done after all resources are released since it will unload the physics plugin, and some resources
 		// might be instances of types from that plugin.
 		PhysicsManager::shutDown();
+		AudioManager::shutDown();
 
 		RendererManager::shutDown();
 
@@ -155,6 +158,7 @@ namespace BansheeEngine
 		MaterialManager::startUp();
 		FontManager::startUp();
 		Importer::startUp();
+		AudioManager::startUp(mStartUpDesc.audio);
 		PhysicsManager::startUp(mStartUpDesc.physics, isEditor());
 
 		for (auto& importerName : mStartUpDesc.importers)
@@ -214,6 +218,7 @@ namespace BansheeEngine
 			preUpdate();
 
 			PROFILE_CALL(gCoreSceneManager()._update(), "SceneManager");
+			gAudio().update();
 			gPhysics().update();
 
 			// Update plugins

+ 3 - 3
Source/BansheeEditor/Include/BsEditorApplication.h

@@ -22,11 +22,11 @@ namespace BansheeEngine
 	class BS_ED_EXPORT EditorApplication : public Application
 	{
 	public:
-		EditorApplication(EditorRenderAPI renderAPI);
+		EditorApplication(EditorRenderAPI renderAPI, AudioPlugin audio);
 		virtual ~EditorApplication();
 
-		/**	Starts the editor with the specified render system. */
-		static void startUp(EditorRenderAPI renderAPI);
+		/**	Starts the editor with the specified render and audio systems. */
+		static void startUp(EditorRenderAPI renderAPI, AudioPlugin audio);
 
 		/**	Checks whether the editor currently has a project loaded. */
 		bool isProjectLoaded() const { return mIsProjectLoaded; }

+ 4 - 4
Source/BansheeEditor/Source/BsEditorApplication.cpp

@@ -66,8 +66,8 @@ namespace BansheeEngine
 		return Paths::getRuntimeDataPath() + L"Settings.asset";
 	}
 
-	EditorApplication::EditorApplication(EditorRenderAPI renderAPIPlugin)
-		:Application(createRenderWindowDesc(), toEngineRenderAPI(renderAPIPlugin), RendererPlugin::Default, getImporters()),
+	EditorApplication::EditorApplication(EditorRenderAPI renderAPIPlugin, AudioPlugin audio)
+		:Application(createRenderWindowDesc(), toEngineRenderAPI(renderAPIPlugin), RendererPlugin::Default, audio, getImporters()),
 		mActiveRAPIPlugin(toEngineRenderAPI(renderAPIPlugin)), mIsProjectLoaded(false), mSBansheeEditorPlugin(nullptr)
 	{
 
@@ -147,9 +147,9 @@ namespace BansheeEngine
 		loadPlugin("SBansheeEditor", &mSBansheeEditorPlugin);
 	}
 
-	void EditorApplication::startUp(EditorRenderAPI renderAPI)
+	void EditorApplication::startUp(EditorRenderAPI renderAPI, AudioPlugin audio)
 	{
-		CoreApplication::startUp<EditorApplication>(renderAPI);
+		CoreApplication::startUp<EditorApplication>(renderAPI, audio);
 	}
 
 	void EditorApplication::preUpdate()

+ 1 - 1
Source/BansheeEditorExec/BsEditorExec.cpp

@@ -64,7 +64,7 @@ int CALLBACK WinMain(
 
 	__try
 	{
-		EditorApplication::startUp(EditorRenderAPI::DX11);
+		EditorApplication::startUp(EditorRenderAPI::DX11, AudioPlugin::OpenAudio);
 		EditorApplication::instance().runMainLoop();
 		EditorApplication::shutDown();
 	}

+ 14 - 2
Source/BansheeEngine/Include/BsApplication.h

@@ -26,12 +26,19 @@ namespace BansheeEngine
 		Default
 	};
 
+	/**	Types of available audio systems. */
+	enum class AudioPlugin
+	{
+		OpenAudio, /**< Open-source audio implementation using OpenAL. */
+		FMOD /**< Audio system implementation using FMOD. */
+	};
+
 	/**	Primary entry point for Banshee engine. Handles startup and shutdown. */
 	class BS_EXPORT Application : public CoreApplication
 	{
 	public:
 		Application(RENDER_WINDOW_DESC primaryWindowDesc, RenderAPIPlugin renderAPI, RendererPlugin renderer, 
-			const Vector<String>& importers);
+			AudioPlugin audio, const Vector<String>& importers);
 		virtual ~Application();
 
 		/**
@@ -40,10 +47,12 @@ namespace BansheeEngine
 		 * @param[in]	primaryWindowDesc	Description of the primary render window that will be created on startup.
 		 * @param[in]	renderAPI			Render API plugin to use.
 		 * @param[in]	renderer			Renderer plugin to use.
+		 * @param[in]	audio				Audio plugin to use.
 		 * @param[in]	importers			A list of importer plugins to load on startup.
 		 */
 		static void startUp(RENDER_WINDOW_DESC& primaryWindowDesc, RenderAPIPlugin renderAPI, 
-			RendererPlugin renderer = RendererPlugin::Default, const Vector<String>& importers = Vector<String>());
+			RendererPlugin renderer = RendererPlugin::Default, AudioPlugin audio = AudioPlugin::OpenAudio, 
+			const Vector<String>& importers = Vector<String>());
 
 		/**	Returns the absolute path to the builtin managed engine assembly file. */
 		Path getEngineAssemblyPath() const;
@@ -88,6 +97,9 @@ namespace BansheeEngine
 		/**	Translates renderer type into library name. */
 		static String getLibNameForRenderer(RendererPlugin plugin);
 
+		/**	Translates audio system type into library name. */
+		static String getLibNameForAudio(AudioPlugin plugin);
+
 		DynLib* mMonoPlugin;
 		DynLib* mSBansheeEnginePlugin;
 	};

+ 24 - 6
Source/BansheeEngine/Source/BsApplication.cpp

@@ -23,11 +23,12 @@
 namespace BansheeEngine
 {
 	START_UP_DESC createStartUpDesc(RENDER_WINDOW_DESC& primaryWindowDesc, const String& renderAPI, const String& renderer, 
-		const Vector<String>& importers)
+		const String& audio, const Vector<String>& importers)
 	{
 		START_UP_DESC desc;
 		desc.renderAPI = renderAPI;
 		desc.renderer = renderer;
+		desc.audio = audio;
 		desc.physics = "BansheePhysX";
 		desc.input = "BansheeOISInput";
 
@@ -38,9 +39,10 @@ namespace BansheeEngine
 	}
 
 	Application::Application(RENDER_WINDOW_DESC primaryWindowDesc, RenderAPIPlugin renderAPI, RendererPlugin renderer, 
-		const Vector<String>& importers)
-		:CoreApplication(createStartUpDesc(primaryWindowDesc, getLibNameForRenderAPI(renderAPI), 
-		getLibNameForRenderer(renderer), importers)), mMonoPlugin(nullptr), mSBansheeEnginePlugin(nullptr)
+		AudioPlugin audio, const Vector<String>& importers)
+		: CoreApplication(createStartUpDesc(primaryWindowDesc, getLibNameForRenderAPI(renderAPI)
+		, getLibNameForRenderer(renderer), getLibNameForAudio(audio), importers)), mMonoPlugin(nullptr)
+		, mSBansheeEnginePlugin(nullptr)
 	{
 
 	}
@@ -98,9 +100,9 @@ namespace BansheeEngine
 	}
 
 	void Application::startUp(RENDER_WINDOW_DESC& primaryWindowDesc, RenderAPIPlugin renderAPI, 
-		RendererPlugin renderer, const Vector<String>& importers)
+		RendererPlugin renderer, AudioPlugin audio, const Vector<String>& importers)
 	{
-		CoreApplication::startUp<Application>(primaryWindowDesc, renderAPI, renderer, importers);
+		CoreApplication::startUp<Application>(primaryWindowDesc, renderAPI, renderer, audio, importers);
 	}
 
 	void Application::preUpdate()
@@ -218,6 +220,22 @@ namespace BansheeEngine
 		return StringUtil::BLANK;
 	}
 
+	String Application::getLibNameForAudio(AudioPlugin plugin)
+	{
+		static String OpenAudioName = "BansheeOpenAudio";
+		static String FMODName = "BansheeFMOD";
+
+		switch (plugin)
+		{
+		case AudioPlugin::OpenAudio:
+			return OpenAudioName;
+		case AudioPlugin::FMOD:
+			return FMODName;
+		}
+
+		return StringUtil::BLANK;
+	}
+
 	Application& gApplication()
 	{
 		return static_cast<Application&>(Application::instance());

+ 10 - 0
Source/BansheeOpenAudio/Include/BsOAAudio.h

@@ -62,6 +62,16 @@ namespace BansheeEngine
 		/** @} */
 
 	private:
+		/** @copydoc Audio::createClip */
+		SPtr<AudioClip> createClip(const SPtr<DataStream>& samples, UINT32 streamSize, UINT32 numSamples,
+			const AUDIO_CLIP_DESC& desc) override;
+
+		/** @copydoc Audio::createListener */
+		SPtr<AudioListener> createListener() override;
+
+		/** @copydoc Audio::createSource */
+		SPtr<AudioSource> createSource() override;
+
 		void rebuildContexts();
 		void clearContexts();
 

+ 1 - 2
Source/BansheeOpenAudio/Include/BsOAAudioClip.h

@@ -15,6 +15,7 @@ namespace BansheeEngine
 	class BS_OA_EXPORT OAAudioClip : public AudioClip
 	{
 	public:
+		OAAudioClip(const SPtr<DataStream>& samples, UINT32 streamSize, UINT32 numSamples, const AUDIO_CLIP_DESC& desc);
 		virtual ~OAAudioClip();
 
 		/** @copydoc AudioClip::getSamples */
@@ -38,8 +39,6 @@ namespace BansheeEngine
 		/** @copydoc AudioClip::getSourceFormatData */
 		SPtr<DataStream> getSourceStream(UINT32& size) override;
 	private:
-		OAAudioClip(const SPtr<DataStream>& samples, UINT32 streamSize, UINT32 numSamples, const AUDIO_CLIP_DESC& desc);
-
 		mutable Mutex mMutex;
 		mutable OAOggVorbisReader mVorbisReader;
 		bool mNeedsDecompression;

+ 17 - 0
Source/BansheeOpenAudio/Source/BsOAAudio.cpp

@@ -1,6 +1,7 @@
 //********************************** Banshee Engine (www.banshee3d.com) **************************************************//
 //**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
 #include "BsOAAudio.h"
+#include "BsOAAudioClip.h"
 #include "BsOAAudioListener.h"
 #include "BsOAAudioSource.h"
 #include "BsMath.h"
@@ -154,6 +155,22 @@ namespace BansheeEngine
 		mSources.erase(source);
 	}
 
+	SPtr<AudioClip> OAAudio::createClip(const SPtr<DataStream>& samples, UINT32 streamSize, UINT32 numSamples,
+		const AUDIO_CLIP_DESC& desc)
+	{
+		return bs_shared_ptr_new<OAAudioClip>(samples, streamSize, numSamples, desc);
+	}
+
+	SPtr<AudioListener> OAAudio::createListener()
+	{
+		return bs_shared_ptr_new<OAAudioListener>();
+	}
+
+	SPtr<AudioSource> OAAudio::createSource()
+	{
+		return bs_shared_ptr_new<OAAudioSource>();
+	}
+
 	void OAAudio::rebuildContexts()
 	{
 		clearContexts();

+ 22 - 2
Source/BansheeOpenAudio/Source/BsOAPlugin.cpp

@@ -1,9 +1,25 @@
 //********************************** Banshee Engine (www.banshee3d.com) **************************************************//
 //**************** Copyright (c) 2016 Marko Pintera ([email protected]). All rights reserved. **********************//
 #include "BsOAPrerequisites.h"
+#include "BsAudioManager.h"
+#include "BsOAAudio.h"
 
 namespace BansheeEngine
 {
+	class BS_OA_EXPORT OAFactory : public AudioFactory
+	{
+	public:
+		void startUp() override
+		{
+			Audio::startUp<OAAudio>();
+		}
+
+		void shutDown() override
+		{
+			Audio::shutDown();
+		}
+	};
+
 	/**	Returns a name of the plugin. */
 	extern "C" BS_OA_EXPORT const char* getPluginName()
 	{
@@ -14,8 +30,12 @@ namespace BansheeEngine
 	/**	Entry point to the plugin. Called by the engine when the plugin is loaded. */
 	extern "C" BS_OA_EXPORT void* loadPlugin()
 	{
-		// TODO
+		return bs_new<OAFactory>();
+	}
 
-		return nullptr;
+	/**	Exit point of the plugin. Called by the engine before the plugin is unloaded. */
+	extern "C" BS_OA_EXPORT void unloadPlugin(OAFactory* instance)
+	{
+		bs_delete(instance);
 	}
 }