/***************************************************************************
 *   Copyright (C) 2004-2005 by                                            *
 *     Paolo Sacconier   <axa1981@tin.it>                                  *
 *     Francesco Tamagni <minchiahead@hacari.org>                          *
 *                                                                         *
 *   This program is free software; you can redistribute it and/or modify  *
 *   it under the terms of the GNU General Public License as published by  *
 *   the Free Software Foundation; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 *   This program is distributed in the hope that it will be useful,       *
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
 *   GNU General Public License for more details.                          *
 *                                                                         *
 *   You should have received a copy of the GNU General Public License     *
 *   along with this program; if not, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
 ***************************************************************************/

#include "context.h"

namespace gillo {

Context::Context(Sound& s)
: states(STA_MAX_STATES), ballPickerPtr(NULL), sound(s), debug(false)
{
	wid = dWorldCreate();
// 	sid = dSimpleSpaceCreate(0);
	sid = dHashSpaceCreate(0);

	this->objPool = new ssgInvisible () ;
	this->scene.addKid(this->objPool);
	
	// ball state
	ssgSimpleState * state = new ssgSimpleState () ;
// 	state -> setTexture        ( TEX_BALL ) ;
	state -> disable           ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
	state -> enable            ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT ) ;
	state -> setShininess      ( 2 ) ;
	this->states.setStep(STA_BALL, state);
	
	state = new ssgSimpleState () ;
	state -> set               ( GL_TEXTURE_2D,       true ) ;
	state -> set               ( GL_CULL_FACE,        true ) ;
	state -> setTexture        ( TEX_GOAL ) ;
// 	state -> setShadeModel     ( GL_SMOOTH ) ;
// 	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
// 	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
// 	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
// 	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
// 	state -> setShininess      ( 2 ) ;
	this->states.setStep(STA_GOAL, state);
	
	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_GOALCENTER ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_GOAL_CENTER, state);
	
	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_GOALAREA ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> disable           ( GL_CULL_FACE ) ;
// 	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_GOAL_AREA, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_PWRUP_BALL_INFLATE ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_PWRUP_BALL_INFLATE, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_GOALKEEPER ) ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setOpaque         () ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
	state -> enable            ( GL_LIGHTING ) ;
// 	state -> setColourMaterial ( GL_AMBIENT ) ;
	state -> setShininess      ( 2 ) ;
	this->states.setStep(STA_GOALKEEPER, state);

// 	state = new ssgSimpleState () ;
// 	state -> setTexture        ( TEX_GOALKEEPERFUR ) ;
// 	state -> setTranslucent    () ;
// 	state -> enable            ( GL_TEXTURE_2D ) ;
// 	state -> setShadeModel     ( GL_SMOOTH ) ;
// 	state -> enable            ( GL_CULL_FACE ) ;
// 	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
// 	state -> setColourMaterial ( GL_AMBIENT ) ;
// 	state -> setShininess      ( 2 ) ;
// 	this->states.setStep(STA_GOALKEEPERFUR, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_BALLEFFECT_RED ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_BALLEFFECT_RED, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_BALLEFFECT_BLUE ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_BALLEFFECT_BLUE, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_ODDBALL ) ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
	state -> enable            ( GL_LIGHTING ) ;
// 	state -> setColourMaterial ( GL_AMBIENT ) ;
	state -> setShininess      ( 2 ) ;
	this->states.setStep(STA_ODDBALL, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_PWRUP_BALL_ADD ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_PWRUP_BALL_ADD, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_PWRUP_GRAVITY_ROTATOR ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_PWRUP_GRAVITY_ROTATOR, state);


	state = new ssgSimpleState () ;
	state -> set               ( GL_TEXTURE_2D,       true ) ;
	state -> set               ( GL_CULL_FACE,        true ) ;
	state -> setTexture        ( TEX_CAR_WHEEL ) ;
	this->states.setStep(STA_CAR_WHEEL, state);

	state = new ssgSimpleState () ;
	state -> setTexture        ( TEX_PWRUP_CHARGE_INVERTER ) ;
	state -> setTranslucent    () ;
	state -> enable            ( GL_TEXTURE_2D ) ;
	state -> setShadeModel     ( GL_SMOOTH ) ;
	state -> enable            ( GL_CULL_FACE ) ;
	state -> enable            ( GL_BLEND ) ;
// 	state -> enable            ( GL_LIGHTING ) ;
	state -> disable           ( GL_LIGHTING ) ;
	state -> setColourMaterial ( GL_AMBIENT_AND_DIFFUSE ) ;
	state -> setMaterial       ( GL_EMISSION, 0, 0, 0, 1 ) ;
	state -> setMaterial       ( GL_SPECULAR, 1, 1, 1, 1 ) ;
	state -> setShininess      (  5 ) ;
	this->states.setStep(STA_PWRUP_CHARGE_INVERTER, state);

// 	state -> set               ( GL_TEXTURE_2D,       true ) ;
// 	state -> set               ( GL_CULL_FACE,        true ) ;
// 	state -> set               ( GL_ALPHA_TEST,       true ) ;
// 	state -> setShadeModel     ( GL_SMOOTH ) ;
// 	state -> enable            ( GL_BLEND ) ;
// 	state -> disable           ( GL_LIGHTING ) ;

//   SSG_GL_TEXTURE_EN
//   SSG_GL_CULL_FACE_EN
//   SSG_GL_COLOR_MATERIAL_EN
//   SSG_GL_BLEND_EN
//   SSG_GL_ALPHA_TEST_EN
//   SSG_GL_LIGHTING_EN
  
// 	state -> setTranslucent    () ;

	printf("Context(%p): created\n",this);
}


Context::~Context()
{
	dSpaceDestroy(sid);
	printf("Context(%p): destroyed\n",this);
}

ssgSimpleState* Context::getState(int stateid)
{
	this->states.getStep(stateid);
}

void Context::addToPool(ssgEntity* obj)
{
	// @todo check for null input
	this->objPool->addKid(obj);
}

ssgEntity* Context::searchInPool(char* name)
{
	ssgEntity* e = this->objPool->getKid(0);
	
	while (e != NULL) {
		if (strcmp(name, e->getName()) == 0) {
			printf("Found %s in pool.\n", name);
			break;
		}
		e = this->objPool->getNextKid();
	}
	
	return e;
}
	
void Context::releaseBall(IBallPicker* bPickPtr) {
	if (this->ballPickerPtr != NULL)
		this->ballPickerPtr->releaseBall();
	if (this->ballPickerPtr != bPickPtr)
		this->ballPickerPtr = bPickPtr;
	else {
		this->ballPickerPtr = NULL;
	}
}

};
