///////////////////////////////////////////////////////////////////////////////
/// @file deShader_priv.hpp
///
/// @brief Private header file for the deShader class
///
/// @author JesusFreak
///
/// This file is the intellectual property of Novus Delta, LLC.. Usage of the
/// contents of this file is subject to the Destiny3D Member License which
/// can be found at http://www.destiny3d.com.  Any other usage is prohibited.
///
/// This file is distributed "AS IS" without warranty of any kind.  Novus
/// Delta, LLC. does not guarantee the fitness of the contents of this file
/// for any particular purpose.
///
/// Copyright (C) 2001-2003 Novus Delta, LLC. All Rights Reserved.
///
/// <hr>
///                                 Change History
/// <hr>
///
/// @date May 2002
/// @author JesusFreak
/// @remarks Creation
///
///////////////////////////////////////////////////////////////////////////////

#ifndef DEVSHADER_PRIV_HPP
#define DEVSHADER_PRIV_HPP

#include "deDriver.hpp"
#include "deArray.hpp"
#include "deFile.hpp"

#define IdeShader_Argument_X 0x00100000
#define IdeShader_Argument_Y 0x00200000
#define IdeShader_Argument_Z 0x00400000
#define IdeShader_Argument_W 0x00800000
#define IdeShader_Argument_Negate 0x0010000

#define IdeShader_Argument_Swizzle_1X 0x00001000
#define IdeShader_Argument_Swizzle_1Y 0x00002000
#define IdeShader_Argument_Swizzle_1Z 0x00004000
#define IdeShader_Argument_Swizzle_1W 0x00008000

#define IdeShader_Argument_Swizzle_2X 0x00000100
#define IdeShader_Argument_Swizzle_2Y 0x00000200
#define IdeShader_Argument_Swizzle_2Z 0x00000400
#define IdeShader_Argument_Swizzle_2W 0x00000800

#define IdeShader_Argument_Swizzle_3X 0x00000010
#define IdeShader_Argument_Swizzle_3Y 0x00000020
#define IdeShader_Argument_Swizzle_3Z 0x00000040
#define IdeShader_Argument_Swizzle_3W 0x00000080

#define IdeShader_Argument_Swizzle_4X 0x00000001
#define IdeShader_Argument_Swizzle_4Y 0x00000002
#define IdeShader_Argument_Swizzle_4Z 0x00000004
#define IdeShader_Argument_Swizzle_4W 0x00000008

class deShader : public IdeShader, public deRefCountBase
{
	// Constructor and Destructor
protected:
	~deShader();
public:
	deShader();

	// Public member functions
public:
	deBoolean Assemble(char * Code,void (*ErrorCallback)(long LineNumber,char * Error));
	deBoolean Disassemble(deString * Code);
	ShaderType GetShaderType() const;
	long GetInstructionCount() const;
	const deTArray<deShaderInstruction> * GetInstructions() const;
	long GetConstantCount() const;
	const deTArray<deShaderConstant> * GetConstants() const;
	deBoolean Write(IdeFile * File) const;
	deBoolean Read(IdeFile * File);
	deBoolean SetDriverShader(void * Shader);
	void * GetDriverShader() const;
	
	// Private member functions
private:
	void GetNextWord(char ** String,char * Word);
	deBoolean GetArgument(char ** String,deString * Argument);
	deBoolean GetLastArgument(char ** String,deString * Argument);
	long GetArrayArgumentIndex(void (*ErrorCallback)(long LineNumber,char * Error),deString * Argument);
	long GetArgumentOffset(long ArgumentNumber,deString * Argument,deString * OutArgument);
	void GotoNextLine(char ** String);
	void Error(void (*ErrorCallback)(long LineNumber,char * Error),char * Error);
	deBoolean ParseInstruction(void (*ErrorCallback)(long LineNumber,char * Error),char ** Code,char * InstructionName);
	deBoolean ParseConstantDeclaration(void (*ErrorCallback)(long LineNumber,char * Error),char ** Code,deShaderInstructionType Instruction);
	void DisassembleIndexAndOffset(long ArgumentNumber,DWORD IndexBase,DWORD Argument,deString * Code);
	deBoolean DisassembleArgument(long ArgumentNumber,DWORD Argument,deString * Code);
	deBoolean DisassembleInstruction(IdeShader::deShaderInstruction * Instruction,deString * Code);
	deBoolean DisassembleConstant(IdeShader::deShaderConstant * Constant,deString * Code);
	deBoolean SetShaderType();
		
	// Private member variables
private:
	deTArray<deShaderInstruction>	m_Instructions;
	deTArray<deShaderConstant>		m_Constants;
	ShaderType						m_ShaderType;
	long							m_CurrentLine;	
	long							m_InstructionCount;
	long							m_ConstantCount;
	void							*m_DriverShader;
};

#endif
