/*
 * ShaderEngine.cpp
 *
 *  Created on: Jul 18, 2008
 *      Author: pete
 */
#include <fstream>
#include "PerlinNoise.hpp"
#include "ShaderEngine.hpp"
#include "BeatDetect.hpp"

ShaderEngine::ShaderEngine()
{
#ifdef USE_CG
	SetupCg();
#endif
}

ShaderEngine::~ShaderEngine()
{
	// TODO Auto-generated destructor stub
}

#ifdef USE_CG

void ShaderEngine::setParams(const int texsize, const unsigned int texId, const float aspect, BeatDetect *beatDetect,
		TextureManager *textureManager)
{
	mainTextureId = texId;
	this->beatDetect = beatDetect;
	this->textureManager = textureManager;
	this->aspect = aspect;
	this->texsize = texsize;

	textureManager->setTexture("main", texId, texsize, texsize);

	glGenTextures(1, &blur1_tex);
	glBindTexture(GL_TEXTURE_2D, blur1_tex);
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, texsize/2, texsize/2, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL );
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

	glGenTextures(1, &blur2_tex);
	glBindTexture(GL_TEXTURE_2D, blur2_tex);
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, texsize / 4, texsize / 4, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL );
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

	glGenTextures(1, &blur3_tex);
	glBindTexture(GL_TEXTURE_2D, blur3_tex);
	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, texsize / 8, texsize / 8, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL );
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);

	blur1_enabled = false;
	blur2_enabled = false;
	blur3_enabled = false;

	//std::cout << "Generating Noise Textures" << std::endl;

	PerlinNoise noise;

	glGenTextures(1, &noise_texture_lq_lite);
	glBindTexture(GL_TEXTURE_2D, noise_texture_lq_lite);
	glTexImage2D(GL_TEXTURE_2D, 0, 4, 32, 32, 0, GL_LUMINANCE, GL_FLOAT, noise.noise_lq_lite);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	textureManager->setTexture("noise_lq_lite", noise_texture_lq_lite, 32, 32);

	glGenTextures(1, &noise_texture_lq);
	glBindTexture(GL_TEXTURE_2D, noise_texture_lq);
	glTexImage2D(GL_TEXTURE_2D, 0, 4, 256, 256, 0, GL_LUMINANCE, GL_FLOAT, noise.noise_lq);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	textureManager->setTexture("noise_lq", noise_texture_lq, 256, 256);

	glGenTextures(1, &noise_texture_mq);
	glBindTexture(GL_TEXTURE_2D, noise_texture_mq);
	glTexImage2D(GL_TEXTURE_2D, 0, 4, 256, 256, 0, GL_LUMINANCE, GL_FLOAT, noise.noise_mq);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	textureManager->setTexture("noise_mq", noise_texture_mq, 256, 256);

	glGenTextures(1, &noise_texture_hq);
	glBindTexture(GL_TEXTURE_2D, noise_texture_hq);
	glTexImage2D(GL_TEXTURE_2D, 0, 4, 256, 256, 0, GL_LUMINANCE, GL_FLOAT, noise.noise_hq);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	textureManager->setTexture("noise_hq", noise_texture_hq, 256, 256);

	glGenTextures(1, &noise_texture_perlin);
	glBindTexture(GL_TEXTURE_2D, noise_texture_perlin);
	glTexImage2D(GL_TEXTURE_2D, 0, 4, 512, 512, 0, GL_LUMINANCE, GL_FLOAT, noise.noise_perlin);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	textureManager->setTexture("noise_perlin", noise_texture_perlin, 512, 512);

	/*
	 glGenTextures( 1, &noise_texture_lq_vol );
	 glBindTexture( GL_TEXTURE_3D, noise_texture_lq_vol );
	 glTexImage3D(GL_TEXTURE_3D,0,4,32,32,32,0,GL_LUMINANCE,GL_FLOAT,noise.noise_lq_vol);
	 glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	 glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	 textureManager->setTexture("noisevol_lq", noise_texture_lq_vol, 256, 256);

	 glGenTextures( 1, &noise_texture_hq_vol );
	 glBindTexture( GL_TEXTURE_3D, noise_texture_hq_vol );
	 glTexImage3D(GL_TEXTURE_3D,0,4,32,32,32,0,GL_LUMINANCE,GL_FLOAT,noise.noise_hq_vol);
	 glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
	 glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
	 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	 textureManager->setTexture("noisevol_hq", noise_texture_hq_vol, 8, 8);
	 */

}

bool ShaderEngine::LoadCgProgram(Shader &shader)
{
	//if (p != NULL) cgDestroyProgram(p);
	//p = NULL;
	std::string program = shader.programSource;

	if (program.length() > 0)
	{
		size_t found = program.rfind('}');
		if (found != std::string::npos)
		{
			//std::cout << "last '}' found at: " << int(found) << std::endl;
			program.replace(int(found), 1, "OUT.color.xyz=ret.xyz;\nOUT.color.w=1;\nreturn OUT;\n}");
		}
		else
			return false;
		found = program.rfind('{');
		if (found != std::string::npos)
		{
			//std::cout << "first '{' found at: " << int(found) << std::endl;
			program.replace(int(found), 1, "{\nfloat rad=getrad;\nfloat ang=getang;\n");
		}
		else
			return false;
		found = program.find("shader_body");
		if (found != std::string::npos)
		{
			//std::cout << "first 'shader_body' found at: " << int(found) << std::endl;
			program.replace(int(found), 11, "outtype projectm(float2 uv : TEXCOORD0)\n");
		}
		else
			return false;

		shader.textures.clear();

		found = 0;
		found = program.find("sampler_", found);
		while (found != std::string::npos)
		{
			found += 8;
			size_t end = program.find_first_of(" ;,\n\r)", found);

			if (end != std::string::npos)
			{

				std::string sampler = program.substr((int) found, (int) end - found);
				UserTexture* texture = new UserTexture(sampler);

				texture->texID = textureManager->getTexture(texture->name);
				if (texture->texID != 0)
				{
					texture->width = textureManager->getTextureWidth(texture->name);
					texture->height = textureManager->getTextureHeight(texture->name);
				}
				else
				{
					if (sampler.substr(0, 4) == "rand")
					{
						std::string random_name = textureManager->getRandomTextureName(texture->name);
						if (random_name.size() > 0)
						{
							texture->texID = textureManager->getTexture(random_name);
							texture->width = textureManager->getTextureWidth(random_name);
							texture->height = textureManager->getTextureHeight(random_name);
						}
					}
					else
					{
						std::string extensions[6];
						extensions[0] = ".jpg";
						extensions[1] = ".dds";
						extensions[2] = ".png";
						extensions[3] = ".tga";
						extensions[4] = ".bmp";
						extensions[5] = ".dib";

						for (int x = 0; x < 6; x++)
						{

							std::string filename = texture->name + extensions[x];
							texture->texID = textureManager->getTexture(filename);
							if (texture->texID != 0)
							{
								texture->width = textureManager->getTextureWidth(filename);
								texture->height = textureManager->getTextureHeight(filename);
								break;
							}
						}

					}
				}
				if (texture->texID != 0 && shader.textures.find(texture->qname) == shader.textures.end())
					shader.textures[texture->qname] = texture;

				else
					delete (texture);

			}

			found = program.find("sampler_", found);
		}
		textureManager->clearRandomTextures();

		found = 0;
		found = program.find("texsize_", found);
		while (found != std::string::npos)
		{
			found += 8;
			size_t end = program.find_first_of(" ;.,\n\r)", found);

			if (end != std::string::npos)
			{
				std::string tex = program.substr((int) found, (int) end - found);
				if (shader.textures.find(tex) != shader.textures.end())
				{
					UserTexture* texture = shader.textures[tex];
					texture->texsizeDefined = true;
					//std::cout << "texsize_" << tex << " found" << std::endl;
				}
			}
			found = program.find("texsize_", found);
		}

		found = program.find("GetBlur3");
		if (found != std::string::npos)
			blur1_enabled = blur2_enabled = blur3_enabled = true;
		else
		{
			found = program.find("GetBlur2");
			if (found != std::string::npos)
				blur1_enabled = blur2_enabled = true;
			else
			{
				found = program.find("GetBlur1");
				if (found != std::string::npos)
					blur1_enabled = true;
			}
		}

		std::string temp;

		temp.append(cgTemplate);
		temp.append(program);

		//std::cout << "Cg: Compilation Results:" << std::endl << std::endl;
		//std::cout << program << std::endl;

		CGprogram p = cgCreateProgram(myCgContext, CG_SOURCE, temp.c_str(),//temp.c_str(),
				myCgProfile, "projectm", NULL);

		checkForCgCompileError("creating shader program");
		if (p == NULL)
			return false;

		cgGLLoadProgram(p);

		if (checkForCgCompileError("loading shader program"))
		{
			p = NULL;
			return false;
		}

		programs[&shader] = p;

		return true;
	}
	else
		return false;
}

bool ShaderEngine::checkForCgCompileError(const char *situation)
{
	CGerror error;
	const char *string = cgGetLastErrorString(&error);
	error = cgGetError();
	if (error != CG_NO_ERROR)
	{
		std::cout << "Cg: Compilation Error" << std::endl;
		std::cout << "Cg: %" << situation << " - " << string << std::endl;
		if (error == CG_COMPILER_ERROR)
		{
			std::cout << "Cg: " << cgGetLastListing(myCgContext) << std::endl;

		}
		return true;
	}

	return false;
}

void ShaderEngine::checkForCgError(const char *situation)
{
	CGerror error;
	const char *string = cgGetLastErrorString(&error);

	if (error != CG_NO_ERROR)
	{
		std::cout << "Cg: %" << situation << " - " << string << std::endl;
		if (error == CG_COMPILER_ERROR)
		{
			std::cout << "Cg: " << cgGetLastListing(myCgContext) << std::endl;
		}
		exit(1);
	}
}

void ShaderEngine::SetupCg()
{
	std::string line;
	std::ifstream myfile(CMAKE_INSTALL_PREFIX "/share/projectM/shaders/projectM.cg");
	if (myfile.is_open())
	{
		while (!myfile.eof())
		{
			std::getline(myfile, line);
			cgTemplate.append(line + "\n");
		}
		myfile.close();
	}

	else
		std::cout << "Unable to load shader template \"" << CMAKE_INSTALL_PREFIX "/share/projectM/shaders/projectM.cg\"" << std::endl;

	std::ifstream myfile2(CMAKE_INSTALL_PREFIX "/share/projectM/shaders/blur.cg");
	if (myfile2.is_open())
	{
		while (!myfile2.eof())
		{
			std::getline(myfile2, line);
			blurProgram.append(line + "\n");
		}
		myfile2.close();
	}

	else
		std::cout << "Unable to load blur template" << std::endl;

	myCgContext = cgCreateContext();
	checkForCgError("creating context");
	cgGLSetDebugMode(CG_FALSE);
	cgSetParameterSettingMode(myCgContext, CG_DEFERRED_PARAMETER_SETTING);

	myCgProfile = cgGLGetLatestProfile(CG_GL_FRAGMENT);
	
	// HACK breaks with buggy ati video drivers such as my own
	// -carmelo.piccione@gmail.com 7/26/2010
	//cgGLSetOptimalOptions(myCgProfile);
	checkForCgError("selecting fragment profile");

	profileName = cgGetProfileString(myCgProfile);
	std::cout << "Cg: Initialized profile: " << profileName << std::endl;
//std::cout<< blurProgram.c_str()<<std::endl;
	blur1Program = cgCreateProgram(myCgContext, CG_SOURCE, blurProgram.c_str(), myCgProfile, "blur1", NULL);

	checkForCgCompileError("creating blur1 program");
	if (blur1Program == NULL)
		exit(1);
	cgGLLoadProgram(blur1Program);

	checkForCgError("loading blur1 program");

	blur2Program = cgCreateProgram(myCgContext, CG_SOURCE, blurProgram.c_str(), myCgProfile, "blurVert", NULL);

	checkForCgCompileError("creating blur2 program");
	if (blur2Program == NULL)
		exit(1);
	cgGLLoadProgram(blur2Program);

	checkForCgError("loading blur2 program");

}

void ShaderEngine::SetupCgVariables(CGprogram program, const Pipeline &pipeline, const PipelineContext &context)
{

	float slow_roam_cos[4] =	{ 0.5 + 0.5 * cos(context.time * 0.005), 0.5 + 0.5 * cos(context.time * 0.008), 0.5 + 0.5 * cos(context.time * 0.013), 0.5 + 0.5 * cos(context.time * 0.022) };
	float roam_cos[4] =	{ 0.5 + 0.5 * cos(context.time * 0.3), 0.5 + 0.5 * cos(context.time * 1.3), 0.5 + 0.5 * cos(context.time * 5), 0.5	+ 0.5 * cos(context.time * 20) };
	float slow_roam_sin[4] =	{ 0.5 + 0.5 * sin(context.time * 0.005), 0.5 + 0.5 * sin(context.time * 0.008), 0.5 + 0.5 * sin(context.time * 0.013), 0.5 + 0.5 * sin(context.time * 0.022) };
	float roam_sin[4] =	{ 0.5 + 0.5 * sin(context.time * 0.3), 0.5 + 0.5 * sin(context.time * 1.3), 0.5 + 0.5 * sin(context.time * 5), 0.5	+ 0.5 * sin(context.time * 20) };

	cgGLSetParameter4fv(cgGetNamedParameter(program, "slow_roam_cos"), slow_roam_cos);
	cgGLSetParameter4fv(cgGetNamedParameter(program, "roam_cos"), roam_cos);
	cgGLSetParameter4fv(cgGetNamedParameter(program, "slow_roam_sin"), slow_roam_sin);
	cgGLSetParameter4fv(cgGetNamedParameter(program, "roam_sin"), roam_sin);

	cgGLSetParameter1f(cgGetNamedParameter(program, "time"), context.time);
	cgGLSetParameter4f(cgGetNamedParameter(program, "rand_preset"), rand_preset[0], rand_preset[1], rand_preset[2],	rand_preset[3]);
	cgGLSetParameter4f(cgGetNamedParameter(program, "rand_frame"), (rand() % 100) * .01, (rand() % 100) * .01, (rand()% 100) * .01, (rand() % 100) * .01);
	cgGLSetParameter1f(cgGetNamedParameter(program, "fps"), context.fps);
	cgGLSetParameter1f(cgGetNamedParameter(program, "frame"), context.frame);
	cgGLSetParameter1f(cgGetNamedParameter(program, "progress"), context.progress);

	cgGLSetParameter1f(cgGetNamedParameter(program, "blur1_min"), pipeline.blur1n);
	cgGLSetParameter1f(cgGetNamedParameter(program, "blur1_max"), pipeline.blur1x);
	cgGLSetParameter1f(cgGetNamedParameter(program, "blur2_min"), pipeline.blur2n);
	cgGLSetParameter1f(cgGetNamedParameter(program, "blur2_max"), pipeline.blur2x);
	cgGLSetParameter1f(cgGetNamedParameter(program, "blur3_min"), pipeline.blur3n);
	cgGLSetParameter1f(cgGetNamedParameter(program, "blur3_max"), pipeline.blur3x);

	cgGLSetParameter1f(cgGetNamedParameter(program, "bass"), beatDetect->bass);
	cgGLSetParameter1f(cgGetNamedParameter(program, "mid"), beatDetect->mid);
	cgGLSetParameter1f(cgGetNamedParameter(program, "treb"), beatDetect->treb);
	cgGLSetParameter1f(cgGetNamedParameter(program, "bass_att"), beatDetect->bass_att);
	cgGLSetParameter1f(cgGetNamedParameter(program, "mid_att"), beatDetect->mid_att);
	cgGLSetParameter1f(cgGetNamedParameter(program, "treb_att"), beatDetect->treb_att);
	cgGLSetParameter1f(cgGetNamedParameter(program, "vol"), beatDetect->vol);
	cgGLSetParameter1f(cgGetNamedParameter(program, "vol_att"), beatDetect->vol);

	cgGLSetParameter4f(cgGetNamedParameter(program, "texsize"), texsize, texsize, 1 / (float) texsize, 1
			/ (float) texsize);
	cgGLSetParameter4f(cgGetNamedParameter(program, "aspect"), 1 / aspect, 1, aspect, 1);

	if (blur1_enabled)
	{
		cgGLSetTextureParameter(cgGetNamedParameter(program, "sampler_blur1"), blur1_tex);
		cgGLEnableTextureParameter(cgGetNamedParameter(program, "sampler_blur1"));
	}
	if (blur2_enabled)
	{
		cgGLSetTextureParameter(cgGetNamedParameter(program, "sampler_blur2"), blur2_tex);
		cgGLEnableTextureParameter(cgGetNamedParameter(program, "sampler_blur2"));
	}
	if (blur3_enabled)
	{
		cgGLSetTextureParameter(cgGetNamedParameter(program, "sampler_blur3"), blur3_tex);
		cgGLEnableTextureParameter(cgGetNamedParameter(program, "sampler_blur3"));
	}

}

void ShaderEngine::SetupUserTexture(CGprogram program, const UserTexture* texture)
{
	std::string samplerName = "sampler_" + texture->qname;

	CGparameter param = cgGetNamedParameter(program, samplerName.c_str());
	checkForCgError("getting parameter");
	cgGLSetTextureParameter(param, texture->texID);
	checkForCgError("setting parameter");
	cgGLEnableTextureParameter(param);
	checkForCgError("enabling parameter");
	//std::cout<<texture->texID<<" "<<samplerName<<std::endl;

	if (texture->texsizeDefined)
	{
		std::string texsizeName = "texsize_" + texture->name;
		cgGLSetParameter4f(cgGetNamedParameter(program, texsizeName.c_str()), texture->width, texture->height, 1
				/ (float) texture->width, 1 / (float) texture->height);
		checkForCgError("setting parameter texsize");
	}
}

void ShaderEngine::SetupUserTextureState( const UserTexture* texture)
{
	    glBindTexture(GL_TEXTURE_2D, texture->texID);
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, texture->bilinear ? GL_LINEAR : GL_NEAREST);
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, texture->bilinear ? GL_LINEAR : GL_NEAREST);
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, texture->wrap ? GL_REPEAT : GL_CLAMP);
		glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, texture->wrap ? GL_REPEAT : GL_CLAMP);
}

void ShaderEngine::SetupCgQVariables(CGprogram program, const Pipeline &q)
{
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qa"), q.q[0], q.q[1], q.q[2], q.q[3]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qb"), q.q[4], q.q[5], q.q[6], q.q[7]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qc"), q.q[8], q.q[9], q.q[10], q.q[11]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qd"), q.q[12], q.q[13], q.q[14], q.q[15]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qe"), q.q[16], q.q[17], q.q[18], q.q[19]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qf"), q.q[20], q.q[21], q.q[22], q.q[23]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qg"), q.q[24], q.q[25], q.q[26], q.q[27]);
		cgGLSetParameter4f(cgGetNamedParameter(program, "_qh"), q.q[28], q.q[29], q.q[30], q.q[31]);
}

void ShaderEngine::setAspect(float aspect)
{
	this->aspect = aspect;
}
void ShaderEngine::RenderBlurTextures(const Pipeline &pipeline, const PipelineContext &pipelineContext,
		const int texsize)
{
	if (blur1_enabled || blur2_enabled || blur3_enabled)
	{
		float tex[4][2] =
		{
		{ 0, 1 },
		{ 0, 0 },
		{ 1, 0 },
		{ 1, 1 } };

		glBlendFunc(GL_ONE, GL_ZERO);
		glColor4f(1.0, 1.0, 1.0, 1.0f);

		glBindTexture(GL_TEXTURE_2D, mainTextureId);
		glEnable(GL_TEXTURE_2D);

		glEnableClientState(GL_VERTEX_ARRAY);
		glDisableClientState(GL_COLOR_ARRAY);
		glEnableClientState(GL_TEXTURE_COORD_ARRAY);
		glTexCoordPointer(2, GL_FLOAT, 0, tex);

		cgGLEnableProfile(myCgProfile);
		checkForCgError("enabling profile");

		if (blur1_enabled)
		{
			cgGLSetParameter4f(cgGetNamedParameter(blur1Program, "srctexsize"), texsize/2, texsize/2, 2 / (float) texsize,
					2 / (float) texsize);
			cgGLSetParameter4f(cgGetNamedParameter(blur2Program, "srctexsize"), texsize/2 , texsize/2, 2 / (float) texsize,
								2 / (float) texsize);



			float pointsold[4][2] =
			{
			{ 0, 1 },
			{ 0, 0 },
			{ 1, 0 },
			{ 1, 1 } };
			float points[4][2] =
						{
						{ 0, 0.5 },
						{ 0, 0 },
						{ 0.5, 0 },
						{ 0.5, 0.5 } };

			cgGLBindProgram(blur1Program);
						checkForCgError("binding blur1 program");

			glVertexPointer(2, GL_FLOAT, 0, points);
			glBlendFunc(GL_ONE,GL_ZERO);
			glDrawArrays(GL_TRIANGLE_FAN, 0, 4);


			glBindTexture(GL_TEXTURE_2D, blur1_tex);
			glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 0, 0, texsize/2, texsize/2);


		}

		if (blur2_enabled)
		{
			cgGLSetParameter4f(cgGetNamedParameter(blur1Program, "srctexsize"), texsize/2, texsize/2, 2 / (float) texsize,
								2 / (float) texsize);
			cgGLSetParameter4f(cgGetNamedParameter(blur2Program, "srctexsize"), texsize/2, texsize/2, 2 / (float) texsize,
					2 / (float) texsize);



			float points[4][2] =
			{
			{ 0, 0.25 },
			{ 0, 0 },
			{ 0.25, 0 },
			{ 0.25, 0.25 } };

			glVertexPointer(2, GL_FLOAT, 0, points);
			glBlendFunc(GL_ONE,GL_ZERO);
			glDrawArrays(GL_TRIANGLE_FAN, 0, 4);



						glBindTexture(GL_TEXTURE_2D, blur2_tex);
						glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 0, 0, texsize/4, texsize/4);


		}

		if (blur3_enabled)
		{
			cgGLSetParameter4f(cgGetNamedParameter(blur2Program, "srctexsize"), texsize/4, texsize/4, 4 / (float) texsize,
								4/ (float) texsize);
			cgGLSetParameter4f(cgGetNamedParameter(blur2Program, "srctexsize"), texsize / 4, texsize / 4, 4
					/ (float) texsize, 4 / (float) texsize);
			float points[4][2] =
			{
			{ 0, 0.125 },
			{ 0, 0 },
			{ 0.125, 0 },
			{ 0.125, 0.125 } };

			glVertexPointer(2, GL_FLOAT, 0, points);
			glBlendFunc(GL_ONE,GL_ZERO);
			glDrawArrays(GL_TRIANGLE_FAN, 0, 4);



						glBindTexture(GL_TEXTURE_2D, blur3_tex);
						glCopyTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, 0, 0, texsize/8, texsize/8);


		}


			cgGLUnbindProgram(myCgProfile);
			checkForCgError("unbinding blur2 program");


		cgGLDisableProfile(myCgProfile);
		checkForCgError("disabling blur profile");

		glDisable(GL_TEXTURE_2D);
		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

	}
}

void ShaderEngine::loadShader(Shader &shader)
{
	if (shader.enabled)
	{
		cgDestroyProgram(programs[&shader]);
		programs.erase(&shader);
	}
	shader.enabled = LoadCgProgram(shader);
}

void ShaderEngine::disableShader()
{
	if (enabled)
	{
		cgGLUnbindProgram(myCgProfile);
		checkForCgError("disabling fragment profile");
		cgGLDisableProfile(myCgProfile);
		checkForCgError("disabling fragment profile");
	}
	enabled = false;
}

void ShaderEngine::enableShader(Shader &shader, const Pipeline &pipeline, const PipelineContext &pipelineContext)
{
	enabled = false;
	if (shader.enabled)
	{

		for (std::map<std::string, UserTexture*>::const_iterator pos = shader.textures.begin(); pos	!= shader.textures.end(); ++pos)
							SetupUserTextureState( pos->second);


		CGprogram program = programs[&shader];
		for (std::map<std::string, UserTexture*>::const_iterator pos = shader.textures.begin(); pos
						!= shader.textures.end(); ++pos)
					SetupUserTexture(program, pos->second);

		cgGLEnableProfile(myCgProfile);
		checkForCgError("enabling warp profile");

		cgGLBindProgram(program);
		checkForCgError("binding warp program");

		SetupCgVariables(program, pipeline, pipelineContext);
		SetupCgQVariables(program, pipeline);

		enabled = true;
	}
}

void ShaderEngine::reset()
{
	rand_preset[0] = (rand() % 100) * .01;
	rand_preset[1] = (rand() % 100) * .01;
	rand_preset[2] = (rand() % 100) * .01;
	rand_preset[3] = (rand() % 100) * .01;
}

#endif
