//===========================================================================//
// File:	renderer.hpp                                                        //
// Project: MUNGA           Brick: Renderer Manager	                       //
// Contents: Interface specification Renderer and Renderer Manager			  //
//---------------------------------------------------------------------------//
//   Date    Who  Modification                                               //
// --------  ---  ---------------------------------------------------------- //
// 11/21/94  ECH  Initial coding.                                            //
// 01/22/95	 ECH	Added NotifyOfBecomingUninterestingEntity						  //
// 05/25/95	 CPB	Moved GetLinkedEntity into public accessability for gauges //
//---------------------------------------------------------------------------//
// Copyright (C) 1994-1995, Virtual World Entertainment, Inc.                //
// All Rights reserved worldwide                                             //
// This unpublished sourcecode is PROPRIETARY and CONFIDENTIAL               //
//===========================================================================//

#pragma once

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

namespace Adept {

	class DamageZone;
	class RendererManager;
	class RendererComponentWeb;
	class Entity__ClassData;

	typedef Receiver__ClassData	Renderer__ClassData;
	typedef Receiver__Message		Renderer__Message;

	//##########################################################################
	//###########################    Renderer    ###############################
	//##########################################################################

	class _declspec(novtable) Renderer:
		public Receiver
	{
		friend RendererManager;

	public:
		static void
			InitializeClass();
		static void
			TerminateClass();

	//##########################################################################
	// Inheritance support
	//
	public:
		typedef Renderer__ClassData	ClassData;
		typedef Renderer__Message		Message;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Destruction, and Testing
	//
	public:
		void
			TestInstance();

		~Renderer();

	protected:
		Renderer(
			ClassData *class_data,
			int renderer_type,
			const char *renderer_name
		);

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Class Data Support
	//
	public:
		static ClassData
			*DefaultData;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Accessors
	//
	public:
		enum RendererStatus
		{
			InactiveRendererStatus,
			LoadingRendererStatus,
			ActiveRendererStatus
		};

		int
			GetRendererType()
				{Check_Object(this); return rendererType;}

		const char*
			GetRendererName()
				{Check_Object(this); return rendererName;}

	protected:
		virtual void
			SetRendererStatus(RendererStatus status)
				{Check_Object(this); rendererStatus = status;}

		RendererStatus
			rendererStatus;
		int
			rendererType;
		Stuff::MString
			rendererName;
		Stuff::Time
			lastRenderTime;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Control and processing
	//
	public:
		void
			Execute(Stuff::Time target_render_time);

   protected:
		virtual void
			ExecuteImplementation(Stuff::Time target_time);

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Component management
	//
	public:
		enum
		{
			TranslationChangedCommandID = 0,
			RotationChangedCommandID,
			ScaleChangedCommandID,
			ZScaleChangedCommandID,
			StartEffectCommandID,
			StopEffectCommandID,
			KillEffectCommandID,
			RendererCommandIDCount
		};

		virtual Component*
			CreateComponent(
				ClassID component_class,
				Stuff::MemoryStream *stream,
				RendererComponentWeb *web,
				Entity *entity
			);

		Component*
			FindSharedComponent(const ComponentID &component_id);
		Component*
			AddSharedComponent(Component *component);

		void
			AddComponentWeb(RendererComponentWeb *web);

		void
			AddExecutableComponent(Component* component);

	protected:
		Stuff::ChainOf<Component*>
			executableComponents;
		Stuff::HashOf<Component*,ComponentID>
			sharedComponents;
		Stuff::ChainOf<RendererComponentWeb*>
			componentWebs;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Interest Manager support
	//
	public:
		virtual void
			EntityIsInteresting(
				Entity *entity,
				bool render_me
			)=0;
		virtual void
			EntityIsUninteresting(Entity *entity)=0;

	//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
	// Tool functions
	//
	public:
		static Component::ClassData*
			CreateFactoryRequest(
				const char* component_type,
				Component::FactoryRequestParameters *parameters,
				Entity__ClassData *class_data
			);

		static int
			CommandEncoder(const char* command_name);
	};

}

#if 1
#define LOAD_LOGIC(string) LOGIC("Load Renderers::" string)
#else
#define LOAD_LOGIC(string)
#endif
