#include "main.h"

#define FONT "                 ##  ##      ##  # #                                                                              ##             ### #   #   ######   #   # ### #  # ## #  #     ## #### ##              ## ##      ####                ##  ##     #  #  #  #   #########  ##### ##   #   #  ### ## #  #  #  #######   #  #######  #####   #   ######   ############### #  #########   #  #  #  #####  ##############  # ###   # ##          ##  ##      ## ###  #  #### #      ####    ####      # ####  #     ####   # ### #  #####  ######  # ## #  ######  #### # # #  ##########   #   ####### #  ##  #### #####   ### #########   ##  #   #####   # #######  ##########  ##### ##  ## ####  ##   ##  # #### ##### ### # ###   #   #   #####  ######  ##  ### ## ###  ##  ######  ##  ##########  ######   #####  ## ########### ##### # ## ######  ###### #### ##  ##  ## #  ##  ##  ######  ##  # ##  ## #  ##  ######  ##  # ##  ## #  ##  # ##  ##  ## ####  ####  ####"

short initfmod(void);

int resizeWindow( int width, int height )
{
  GLfloat ratio;

  if ( height == 0 )
    height = 1;

  ratio = ( GLfloat )width / ( GLfloat )height;

  glViewport( 0, 0, ( GLsizei )width, ( GLsizei )height );

  glMatrixMode( GL_PROJECTION );
  glLoadIdentity( );
  gluPerspective( 45.0f, ratio, 0.1f, 150.0f );

  glMatrixMode( GL_MODELVIEW );
  glLoadIdentity( );
  return(1);
}

void initfont(void){
  /*int tmp[65][4][4];*/
  int letter=0,x=0,y=0,i=0;

  for(letter=0;letter<65;letter++){
    for( x = 0;x<4;x++){
      for( y=0;y<4;y++){
	if( FONT[i] =='#')
	  font[letter][x][y] = 1;
	else
	  font[letter][x][y] = 0;
	i++;
      }
    }
  }

  return;
  
}


int LoadTextures(){
  SDL_Surface *TextureImage[9];
  /*int i;
  char file[7];*/
  
  if( (TextureImage[0] = SDL_LoadBMP("gfx/texture.bmp"))){
    glGenTextures(1, &sphere.texture[0]);

    glBindTexture( GL_TEXTURE_2D, sphere.texture[0]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[0]->w, TextureImage[0]->h,0,GL_BGR,
		  GL_UNSIGNED_BYTE, TextureImage[0]->pixels);
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
  if( TextureImage[0] )
    SDL_FreeSurface( TextureImage[0] );

  if( (TextureImage[1] = SDL_LoadBMP("gfx/reflect.bmp"))){
    glGenTextures(1, &skysphere.texture[0]);
    glBindTexture( GL_TEXTURE_2D, skysphere.texture[0]);
    
    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[1]->w, TextureImage[1]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[1]->pixels);
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
 
  if( TextureImage[1] )
    SDL_FreeSurface( TextureImage[1] );
  

  if( (TextureImage[2] = SDL_LoadBMP("gfx/plasma.bmp"))){
    glGenTextures(1, &btexture[0]);
    glBindTexture( GL_TEXTURE_2D, btexture[0]);
    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[2]->w, TextureImage[2]->h,0,GL_BGR,
		  GL_UNSIGNED_BYTE, TextureImage[2]->pixels);
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
  if( TextureImage[2] )
    SDL_FreeSurface( TextureImage[2] );

   
  if( (TextureImage[3] = SDL_LoadBMP("gfx/asdf.bmp"))){
    glGenTextures(1, &texture[0]);
    glBindTexture( GL_TEXTURE_2D, texture[0]);
    
    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[3]->w, TextureImage[3]->h,0,GL_BGR,
		  GL_UNSIGNED_BYTE, TextureImage[3]->pixels);
	
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
  
  if( TextureImage[3] )
    SDL_FreeSurface( TextureImage[3] );
/*
  for( i = 0; i < 5; i++ ){
    sprintf( file, "%d.bmp", i+1 );
    if( (TextureImage[i+4] = SDL_LoadBMP(file))){
      glGenTextures(1, &credits[i]);
      glBindTexture( GL_TEXTURE_2D, credits[i]);
      glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[i+4]->w, TextureImage[i+4]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[i+4]->pixels);
      glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
      glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
    }
    if( TextureImage[i+4] )
      SDL_FreeSurface( TextureImage[i+4] );
  }
  */
  
  
  if( (TextureImage[4] = SDL_LoadBMP("gfx/1.bmp"))){
    glGenTextures(1, &credits[0]);
    glBindTexture( GL_TEXTURE_2D, credits[0]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[4]->w, TextureImage[4]->h,0,GL_BGR,   GL_UNSIGNED_BYTE, TextureImage[4]->pixels);

    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
  if( TextureImage[4] )
    SDL_FreeSurface( TextureImage[4] );

  
  if( (TextureImage[5] = SDL_LoadBMP("gfx/2.bmp"))){
    glGenTextures(1, &credits[1]);
    glBindTexture( GL_TEXTURE_2D, credits[1]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[5]->w, TextureImage[5]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[5]->pixels);

    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }
  if( TextureImage[5] )
    SDL_FreeSurface( TextureImage[5] );

  
  if( (TextureImage[6] = SDL_LoadBMP("gfx/3.bmp"))){
    glGenTextures(1, &credits[2]);
    glBindTexture( GL_TEXTURE_2D, credits[2]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[6]->w, TextureImage[6]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[6]->pixels);
    
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }

  if( TextureImage[6] )
    SDL_FreeSurface( TextureImage[6] );

  
  if( (TextureImage[7] = SDL_LoadBMP("gfx/4.bmp"))){
    glGenTextures(1, &credits[3]);
    glBindTexture( GL_TEXTURE_2D, credits[3]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[7]->w, TextureImage[7]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[7]->pixels);

    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }

  if( TextureImage[7] )
    SDL_FreeSurface( TextureImage[7] );

  
  if( (TextureImage[8] = SDL_LoadBMP("gfx/5.bmp"))){
    glGenTextures(1, &credits[4]);
    glBindTexture( GL_TEXTURE_2D, credits[4]);

    glTexImage2D( GL_TEXTURE_2D, 0,3, TextureImage[8]->w, TextureImage[8]->h,0,GL_BGR, GL_UNSIGNED_BYTE, TextureImage[8]->pixels);

    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
  }

  if( TextureImage[8] )
    SDL_FreeSurface( TextureImage[8] );
    
  glBindTexture( GL_TEXTURE_2D, 0 );
  return 0;
}

void initsphere(){
  sphere.x0 = sphere.y0 = sphere.z0 = 0.0f;
  sphere.radius = 2.0f;
  sphere.step = 15; /* 20 */
  sphere.facets = (360/sphere.step);

  sphere.vertices = renderSphere( sphere );

  skysphere.x0 = skysphere.y0= skysphere.z0 = 0.0f;
  skysphere.radius = 60.0f;
  skysphere.step = 20;
  skysphere.facets = (360/skysphere.step );

  skysphere.vertices = renderSphere(skysphere );

  LoadTextures();
}

void genLists(){
  spheredl = glGenLists(1);
  
  glNewList( spheredl, GL_COMPILE);
  	drawSphere(sphere,1);
  glEndList();

  return;
}


int initGL( GLvoid )
{
  GLfloat LightAmbient[]  = { 0.5f, 0.5f, 0.5f, 1.0f };
  GLfloat LightDiffuse[]  = { 1.0f, 1.0f, 1.0f, 1.0f };
  GLfloat light_position[] = { 10.0, 10.0, 2.0, 0.0 };
  
  glShadeModel( GL_SMOOTH );
  glClearColor( 0.0f, 0.0f, 0.0f, 0.0f );
  glClearDepth( 1.0f );
  glEnable( GL_DEPTH_TEST );
  glDepthFunc( GL_LEQUAL );
  glHint( GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST );


  glLightfv( GL_LIGHT0, GL_AMBIENT, LightAmbient );
  glLightfv( GL_LIGHT0, GL_DIFFUSE, LightDiffuse );
      
  glLightfv(GL_LIGHT0, GL_POSITION, light_position);
  glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
  /*
  glEnable(GL_COLOR_MATERIAL);
  glEnable(GL_LIGHTING);
  glEnable(GL_LIGHT0);
*/

  /*
  glEnable(GL_CULL_FACE);
  */
  glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
  glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);

  initsphere();

  genLists();
  initfont();

  initobject( "gfx/introx.tri" );
  
  if(initfmod() == -1){
    printf("Failed to initialize FMOD\n");
    exit(1);
  }
  
  dspspect = FSOUND_DSP_GetSpectrum();

  glEnable( GL_TEXTURE_2D );
  return(1);
}

int initSDL( int *videoFlags, const SDL_VideoInfo *videoInfo )
{

  atexit( SDL_Quit);

  if ( SDL_Init( SDL_INIT_VIDEO ) < 0 ){
    fprintf( stderr, "Video initialization failed: %s\n",
             SDL_GetError( ) );
    return(0);
  }

  videoInfo = SDL_GetVideoInfo( );

  if ( !videoInfo ){
    fprintf( stderr, "Video query failed: %s\n",
             SDL_GetError( ) );
    return(0);
  }

  *videoFlags  = SDL_OPENGL;          /* Enable OpenGL in SDL */
  *videoFlags |= SDL_GL_DOUBLEBUFFER; /* Enable double buffering */
  *videoFlags |= SDL_HWPALETTE;       /* Store the palette in hardware */
  *videoFlags |= SDL_RESIZABLE;       /* Enable window resizing */
#ifdef FULLSCREEN
  *videoFlags |= SDL_FULLSCREEN;
#endif

  if ( videoInfo->hw_available )
    *videoFlags |= SDL_HWSURFACE;
  else
    *videoFlags |= SDL_SWSURFACE;

  if ( videoInfo->blit_hw )
    *videoFlags |= SDL_HWACCEL;

  /* Sets up OpenGL double buffering */

  SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, 1 );

  screen = SDL_SetVideoMode( SCREEN_W, SCREEN_H, SCREEN_BPP,
                             *videoFlags );

  if(!screen){
    fprintf( stderr,  "Video mode set failed: %s\n", SDL_GetError( ) );
    return( 0 );
  }

  if ( ( SDL_EnableKeyRepeat( 100, SDL_DEFAULT_REPEAT_INTERVAL ) ) ){
    fprintf( stderr, "Setting keyboard repeat failed: %s\n",
             SDL_GetError( ) );
    return( 0 );
  }

#ifdef FULLSCREEN
  SDL_ShowCursor(SDL_DISABLE);
#endif
  initGL( );
  resizeWindow( SCREEN_W, SCREEN_H );

  return(1);
}

