//
// Asura_Platform_RenderStates.cpp
//
// Created by KOR - 10 October 2006
//
// Copyright (C) 2006 Rebellion, All Rights Reserved.
//

#include "Core/Asura.h"

// This file's header.
#include "Rendering/Asura_RenderStates.h"

// Asura headers
#include "Rendering/Asura_Render.h"

// Platform headers
#include "Rendering/Asura_GX.h"
#include "Rendering/Asura_GX_TextureManagement.h"

// Library headers
#include <revolution/gx.h>

void Asura_Render_States::SetTextureIndex(int t, int i)
{
	if(TextureIndex[t] == i)
	{
		// This texture is already loaded
		return;
	}
	TextureIndex[t]=i;

	Asura_GX_Texture_Management::SetTextureIndex(t, i);
}

void Asura_Render_States::SetWireFrameMode(bool b)
{
}


void Asura_Render_States::SetDitheringMode(bool b)
{
	DitheringMode=b;
	GXSetDither(b);
}


void Asura_Render_States::SetZBufferEnabled(bool b)
{
	ZBufferEnabled=b;
	Asura_GX::SetZBufferMode(ZBufferEnabled, ZBufferCompareMode, ZBufferWriteEnabled);
}

void Asura_Render_States::SetZBufferCompareMode(enum ASURA_ZBUFFERCMP_ID mode)
{
	ZBufferCompareMode = mode;
	Asura_GX::SetZBufferMode(ZBufferEnabled, ZBufferCompareMode, ZBufferWriteEnabled);
}

void Asura_Render_States::SetZBufferWriteEnabled(bool b)
{
	ZBufferWriteEnabled=b;
	Asura_GX::SetZBufferMode(ZBufferEnabled, ZBufferCompareMode, ZBufferWriteEnabled);
}

void Asura_Render_States::SetAlphaBlending(bool b)
{
	/// Kim Randell - 05/02/2003 17:05:22 - Gamecube has one command for blending on/off and blending states,
	/// so this just toggles AlphaBlending member variable.
	AlphaBlendingEnabled=b;
}

void Asura_Render_States::SetTranslucencyMode(enum ASURA_TRANSLUCENCY_MODE mode)
{
	TranslucencyMode=mode;

	switch(TranslucencyMode)
	{
	 	case ASURA_TRANSLUCENCY_OFF:
		{
			if (AlphaBlendingEnabled) SetAlphaBlending(false);
			GXSetBlendMode(GX_BM_NONE, GX_BL_ONE, GX_BL_ZERO, GX_LO_NOOP);
			break;
		}
	 	case ASURA_TRANSLUCENCY_NORMAL:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_SRCALPHA, GX_BL_INVSRCALPHA, GX_LO_NOOP);
			break;
		}
	 	case ASURA_TRANSLUCENCY_COLOUR:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_DSTCLR, GX_BL_ZERO, GX_LO_NOOP);
			break;
		}
		case ASURA_TRANSLUCENCY_DOUBLECOLOUR:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_DSTCLR, GX_BL_SRCCLR, GX_LO_NOOP);
			break;
		}
	 	case ASURA_TRANSLUCENCY_INVCOLOUR:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_ZERO, GX_BL_INVSRCCLR, GX_LO_NOOP);
			break;
		}
  		case ASURA_TRANSLUCENCY_GLOWING:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_SRCALPHA, GX_BL_ONE, GX_LO_NOOP);
			break;
		}
  		case ASURA_TRANSLUCENCY_DARKENINGCOLOUR:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_INVDSTCLR, GX_BL_ZERO, GX_LO_NOOP);
			break;
		}
		case ASURA_TRANSLUCENCY_JUSTSETZ:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_ZERO, GX_BL_ONE, GX_LO_NOOP);
			break;
		}
		case ASURA_TRANSLUCENCY_ALPHACOMPARE:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_DSTALPHA, GX_BL_ZERO, GX_LO_NOOP);
			break;
		}
		case ASURA_TRANSLUCENCY_UGH:
		{
			if (!AlphaBlendingEnabled) SetAlphaBlending(true);
			GXSetBlendMode(GX_BM_BLEND, GX_BL_DSTCLR, GX_BL_ONE, GX_LO_NOOP);
			break;
		}
		default:
			break;
	}
}

void Asura_Render_States::SetTextureOpMode(enum ASURA_TEXTUREOP_ID mode)
{
}

void Asura_Render_States::SetAlphaTest(bool bAlphaTest)
{
	Asura_Assert(0 <= m_iAlphaTestRef && m_iAlphaTestRef <= 0xff, "Alpha test reference value out of range");
	AlphaTest = bAlphaTest;
	if(bAlphaTest)
	{
		GXSetAlphaCompare( GX_GREATER, m_iAlphaTestRef, GX_AOP_AND, GX_ALWAYS, 0 );
		GXSetZCompLoc( GX_FALSE );
	}
	else
	{
		GXSetAlphaCompare( GX_ALWAYS, 0, GX_AOP_AND, GX_ALWAYS, 0 );
		GXSetZCompLoc( GX_TRUE );
	}
}

void Asura_Render_States::SetDynamicLights(bool b)
{
}

void Asura_Render_States::SetCullMode(enum ASURA_CULLMODE_ID eMode)
{
	switch(eMode)
	{
		case ASURA_CULLMODE_CW:
			if (Asura_Render::ShouldRenderMirrored())	GXSetCullMode(GX_CULL_FRONT);
			else										GXSetCullMode(GX_CULL_BACK);
			break;
		case ASURA_CULLMODE_CCW:
			if (Asura_Render::ShouldRenderMirrored())	GXSetCullMode(GX_CULL_BACK);
			else										GXSetCullMode(GX_CULL_FRONT);
			break;
		case ASURA_CULLMODE_NONE:
		default:
			GXSetCullMode(GX_CULL_NONE);
			break;
	}
	m_eCullMode = eMode;
}

void Asura_Render_States::SetStencilEnabled( bool b) 
{ 
#if 0
	StencilEnabled = b;
#endif
}

