#pragma once

#include "Adept.hpp"
#include "Component.hpp"
#include "AudioComponentWeb.hpp"

namespace Adept {

	class AttributeEntry;
	class Entity__ClassData;
	class SpatializedCommand;

	//#########################################################################
	//######################  AudioFXComponent   ##########################
	//#########################################################################

	class AudioFXComponent:
		public Component
	{
	public:
		static void InitializeClass(Stuff::NotationFile *startup_ini);
		static void TerminateClass(Stuff::NotationFile *startup_ini);

		static ClassData *DefaultData;

		typedef Component BaseClass;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Constructor/Destructor
	//
	protected:
		AudioFXComponent(
			ClassData *class_data,
			Stuff::MemoryStream *stream,
			AudioComponentWeb *owning_web
		);

	public:
		static AudioFXComponent* Make(
			MemoryStream *stream,
			AudioComponentWeb *owning_web
		);
		~AudioFXComponent();

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Component support
	//
	public:
		void Execute();
		void ChannelChanged(Channel *channel);

		AudioComponentWeb* GetComponentWeb()
			{
				Check_Object(this);
				AudioComponentWeb* renderer =
					Cast_Object(
						AudioComponentWeb*,
						Component::GetComponentWeb()
					);
				Verify(renderer->GetClassID() == AudioComponentWebClassID);
				return renderer;
			}

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Variables
	//
	protected:
		Stuff::Time m_nextExecute;
		Entity *m_entity;
		AttributeEntry *m_status;
		int m_type;
		gosAudio_PlayMode m_playMode;
		ResourceID m_handleResourceID, m_lowEndHandleResourceID;
		Stuff::Scalar
			m_priority,
			m_volume,
			m_minRestartDelay,
			m_minReplaceDelay,
			m_minDeviation,
			m_nearClip,
			m_minRange,
			m_maxRange,
			m_farClip,
			m_executeDelay;
		Stuff::SlotOf<SpatializedCommand*> m_command;

		void PlaySound();

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Test support
	//
	public:
		void TestInstance() const;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Tool-related Functions
	//
	public:
		static ClassData* CreateFactoryRequest(
			FactoryRequestParameters *parameters,
			Entity__ClassData *class_data
		);
	};

}

