/*  Copyright (C) 2000 Anil Shrestha and Adam Hiatt
*   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, 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., 675 Mass Ave, Cambridge, MA 02139, USA.*/



 // these must be declared volatile so the optimiser doesn't mess up
 volatile int timer = 0;

#include <iostream.h>				// for standard I/O routines used in debugging
#include "allegro.h"			  		//	libraries for graphics and sound
#include "constants.h"				// constants for program
#include "collision.h"        	// fucnctions for collision detection
#include "util.h"						// additional functions for program
#include "animationtype.h"			// for keeping track of images
#include "bullettype.h"				// structure for plane's bullets
#include "planetype.h"				// the plane structure
#include "enemytype.h"				// the enemy list structure
#include "scorelisttype.h"       // For high score menu
#include "sound.h"					// sound functions
#include "star.h"						// functions for stars
#include <stdio.h>    		 		// for rand()
#define VERSION 0.7         		// Keep Track of the Version


//****************************************************************************
// Necessary globals
   BITMAP   * buffer = NULL;
   BITMAP  	* menu_buffer = NULL;
   PALETTE    GamePal;             // Pallete For Plane
   PALLETE    MenuPal;
   bool       GAME_STARTED = false;
   AnimationTYPE  plane_images;
   PlaneTYPE 		plane_object;
   EnemyTYPE * enemies;
   int level_index;
   apvector <apstring> level_names;


//****************************************************************************
// Function Prototypes

	void Program_Init  			( );
	void Game_Init 				( );
	void Game_Shutdown 			( );
	void Check_Input   			( );
	void Menu_Init 	 			( AnimationTYPE  * menu_images );

	void Active_Menu 	 			(  );
	void Display_Menu  			( );
	void Display_High_Scores 	( );
   void Get_High_Score 			( );
	void Display_Options 		( );

   void Begin_Game 				( );
	void Run_Game 		 			( );
	void Display_Info_Bar		( );
	void Init_Plane    			( );
   void Col_Detect	 			( EnemyTYPE & enemies,SAMPLE * bullet_strike,SAMPLE * enemy_explode );

//****************************************************************************
// Functions

int main()
{
   Program_Init ();
   Active_Menu ( );
	Game_Shutdown ();
   return 0;
}
END_OF_MAIN();
//****************************************************************************
/* timer interrupt handler */
void inc_x(void)
{
   timer++;
}
END_OF_FUNCTION(inc_x);
//****************************************************************************
void Program_Init ()
{
	// turn on Allegro, initialize, set graphics mode
   allegro_init();
   set_gfx_mode( GFX_AUTODETECT, SCREEN_WIDTH, SCREEN_HEIGHT, 0, 0);
   install_keyboard();

   // allocate the memory buffer -- double buffering, load palette
   buffer = create_bitmap (SCREEN_W, SCREEN_H);
   menu_buffer = create_bitmap (SCREEN_W, SCREEN_H);
	install_sound (DIGI_AUTODETECT ,MIDI_AUTODETECT,"");
	install_mouse();
}
//****************************************************************************
void Game_Shutdown ()
{
	#ifdef ALLEGRO_DOS
	   destroy_bitmap(menu_buffer);
	   destroy_bitmap(buffer);
	#endif
   delete enemies;
   allegro_exit();
}
//****************************************************************************
void Check_Input ()
{
	poll_keyboard();
}
//****************************************************************************
void Menu_Init ( AnimationTYPE  & menu_images )
{
   clear( menu_buffer );
   menu_images.LoadImages ( "images/menu.dat");
   RGB * menu_pal = menu_images.GetPallete ();
   set_pallete ( menu_pal );
   get_pallete ( MenuPal );
   draw_sprite(menu_buffer, menu_images.GetImage ( 0 ), 70, 0);
   draw_sprite(menu_buffer, menu_images.GetImage ( 5 ), 325, 335);
}
//****************************************************************************
void Active_Menu (  )
{
	AnimationTYPE  menu_images;
   Menu_Init ( menu_images);
   SAMPLE * menu_bg = load_sample ("sound/flight.wav");
   play_sample(menu_bg , 127, 127, 1000, 1);
   SAMPLE *menu_beep = load_sample ("sound/menuitem.wav");
   bool entering_menu = true;
	LoadStrings (level_names,"levels/level_names.dat");

	while ( TRUE )
   {
  		if ( entering_menu )
         set_pallete ( black_palette );

      poll_mouse ();
      poll_keyboard ();
      show_mouse ( menu_buffer );
      Display_Menu ();

  		if ( entering_menu )
      {
         fade_in ( MenuPal,5 );
         entering_menu = false;
      }
		// bitmask to determine if 1st mouse button is pressed
   	if ( mouse_x >= BUTTON_LEFT && mouse_x <= BUTTON_RIGHT)
		{
			if ( mouse_y >= BUTTON_1_TOP && mouse_y <= BUTTON_1_BOTTOM )
         {
	         draw_sprite(menu_buffer, menu_images.GetImage ( 1 ), 70, 0);
            if (mouse_b & 1)
  				{
            	play_sample(menu_beep , 127, 127, 1000, 0);
					fade_out ( 5 );
               clear (screen);
            	destroy_sample ( menu_bg );

               Run_Game ();

               if ( !GAME_STARTED )   //  high score input
						Get_High_Score ();

         		menu_bg = load_sample ("sound/flight.wav");
					play_sample(menu_bg , 127, 127, 1000, 1);
					entering_menu = true;
            }
         }
  			else if ( mouse_y >= BUTTON_2_TOP && mouse_y <= BUTTON_2_BOTTOM )
         {
	         draw_sprite(menu_buffer, menu_images.GetImage ( 2 ), 70, 0);
            if (mouse_b & 1)
            {
	           play_sample(menu_beep , 127, 127, 1000, 0);
				  fade_out ( 5 );
              clear (screen);
 			     Display_Options ();
	           entering_menu = true;
				}
			}
  			else if ( mouse_y >= BUTTON_3_TOP && mouse_y <= BUTTON_3_BOTTOM )
         {
	         draw_sprite(menu_buffer, menu_images.GetImage ( 3 ), 70, 0);
           	if (mouse_b & 1)
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
               fade_out ( 5 );
               clear (screen);
           		Display_High_Scores ();
               entering_menu = true;
				}
			}
         else if ( mouse_y >= BUTTON_4_TOP && mouse_y <= BUTTON_4_BOTTOM )
         {
            draw_sprite(menu_buffer, menu_images.GetImage ( 4 ), 70, 0);
	         if (mouse_b & 1)
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
            	if (Confirm ( menu_buffer,"Quit?", 220, 190 ))
               {
   	         	destroy_sample ( menu_bg );
	           	   destroy_sample ( menu_beep );
    					break;
					}
				}
			}
         else
         	draw_sprite(menu_buffer, menu_images.GetImage ( 0 ), 70, 0);
      }
      else
         draw_sprite(menu_buffer, menu_images.GetImage ( 0 ), 70, 0);
	}
   fade_out ( 5 );
}
//****************************************************************************
void Display_High_Scores ()
{
 	clear_keybuf();
   set_pallete ( MenuPal );
	bool changed = false;
	ScoreListTYPE score_list;
   score_list.ReadFromFile ("scores.dat");
   SAMPLE *menu_beep;
   menu_beep = load_sample ("sound/menuitem.wav");

   AnimationTYPE  HS_Images;
   HS_Images.LoadImages ( "images/hsimages.dat");
   BITMAP * score_menu_buffer = NULL;
   BITMAP * title_sprite = load_bmp ( "images/hstitle.bmp", MenuPal );
   score_menu_buffer = create_bitmap (SCREEN_W, SCREEN_H);
   clear (score_menu_buffer);

   draw_sprite(score_menu_buffer, HS_Images.GetImage ( 0 ), 36, 230);
   draw_sprite(score_menu_buffer, HS_Images.GetImage ( 3 ),22, 100);

   while ( TRUE )
   {
      poll_mouse ();
      poll_keyboard ();
      score_list.DisplayList ( score_menu_buffer );
      show_mouse ( score_menu_buffer );
		blit(score_menu_buffer, screen, 0, 0, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT);

      if ( key [KEY_ESC] )
      {
	     	play_sample(menu_beep , 127, 127, 1000, 0);
	      if (changed)
		   	score_list.WriteToFile ("scores.dat");
			clear_keybuf();
			break;
      }

      if ( mouse_x >= HS_BUTTON_LEFT && mouse_x <= HS_BUTTON_RIGHT)
		{
         if ( mouse_y >= HS_BUTTON_1_TOP && mouse_y <= HS_BUTTON_1_BOTTOM )
         {
				draw_sprite(score_menu_buffer, HS_Images.GetImage ( 1 ), 36, 230);
            if ( mouse_b & 1 )
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
               if ( Confirm ( score_menu_buffer,"Reset scores?", 220, 190 ) )
               {
			         score_list.ResetList ();
	     	      	changed = true;
					}
				}
         }
         else if ( mouse_y >= HS_BUTTON_2_TOP && mouse_y <= HS_BUTTON_2_BOTTOM )
         {
         	draw_sprite(score_menu_buffer, HS_Images.GetImage ( 2 ), 36, 230);
            if ( mouse_b & 1 )
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
		         if (changed)
				   	score_list.WriteToFile ("scores.dat");
					clear_keybuf();
        			break;
				}
	      }
         else
	      	draw_sprite(score_menu_buffer, HS_Images.GetImage ( 0 ), 36, 230);
      }
      else
      	draw_sprite(score_menu_buffer, HS_Images.GetImage ( 0 ), 36, 230);
	}
   destroy_sample ( menu_beep );
   fade_out( 5 );
}

//****************************************************************************
 void Get_High_Score ( )
 {
 	clear (screen);
   set_palette (MenuPal);
 	ScoreListTYPE score_list;
   score_list.ReadFromFile ("scores.dat");

   if ( plane_object.GetScore() < score_list.Lowest_Score () )
   	return;

   apstring name = GetText ( buffer,"High Score!","Enter name: " ,220, 190,10 );
   if ( name.length() == 0 )
   	name = "anonymous";
   score_list.InsertNewEntry ( name, plane_object.GetScore() );
   score_list.WriteToFile ("scores.dat");
   set_pallete ( MenuPal );
	Display_High_Scores ();
 }
//****************************************************************************
 void Display_Options ()
 {
 	clear_keybuf();
   set_pallete ( MenuPal );
   SAMPLE *menu_beep = load_sample ("sound/menuitem.wav");

   AnimationTYPE  Option_Images;
   Option_Images.LoadImages ( "images/oimages.dat");
   BITMAP * option_menu_buffer = NULL;
   BITMAP * title_sprite = load_bmp ( "images/otitle.bmp", MenuPal );
   option_menu_buffer = create_bitmap (SCREEN_W, SCREEN_H);
   clear (option_menu_buffer);

   draw_sprite(option_menu_buffer, Option_Images.GetImage ( 0 ), 36, 230);
   draw_sprite(option_menu_buffer, Option_Images.GetImage ( 5 ),22, 100);

   while ( TRUE )
   {
      poll_mouse ();
      poll_keyboard ();
      char temp [10];
      textprintf(option_menu_buffer, font, 320 , 250, 15, strcpy (temp,NumToString (sample_vol).c_str()));
      textprintf(option_menu_buffer, font, 320 , 280, 15, strcpy (temp,NumToString (stream_vol).c_str()));
      show_mouse ( option_menu_buffer );
		blit(option_menu_buffer, screen, 0, 0, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT);

      if ( key [KEY_ESC] )
      {
	     	play_sample(menu_beep , 127, 127, 1000, 0);
			clear_keybuf();
			break;
      }

      if ( mouse_x >= O_BUTTON_LEFT && mouse_x <= O_BUTTON_RIGHT)
		{
         if ( mouse_y >= O_BUTTON_1_TOP && mouse_y <= O_BUTTON_1_BOTTOM )
         {
				draw_sprite(option_menu_buffer, Option_Images.GetImage ( 1 ), 36, 230);
            if ( mouse_b & 1 )
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
               do {
        	       sample_vol = GetNum ( option_menu_buffer,"Sound Effects Volume","Enter number 0-255: " ,220, 190,3 );
               } while ( sample_vol > 255 || sample_vol < 0 );
				}
         }
         else if ( mouse_y >= O_BUTTON_2_TOP && mouse_y <= O_BUTTON_2_BOTTOM )
         {
         	draw_sprite(option_menu_buffer, Option_Images.GetImage ( 2 ), 36, 230);
            if ( mouse_b & 1 )
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
					do {
               	stream_vol = GetNum ( option_menu_buffer,"Music Volume","Enter number 0-255: " ,220, 190,3 );
					} while ( stream_vol > 255 || stream_vol < 0 );
				}
	      }
         else if ( mouse_y >= O_BUTTON_3_TOP && mouse_y <= O_BUTTON_3_BOTTOM )
         {
         	draw_sprite(option_menu_buffer, Option_Images.GetImage ( 3 ), 36, 230);
            if ( mouse_b & 1 )
            {
            	play_sample(menu_beep , 127, 127, 1000, 0);
               if ( Confirm ( option_menu_buffer,"Set defaults?", 220, 190 ) )
               {
	               stream_vol = DEFAULT_STREAM_VOL;
						sample_vol = DEFAULT_SAMPLE_VOL;
					}
				}
	      }
         else if ( mouse_y >= O_BUTTON_4_TOP && mouse_y <= O_BUTTON_4_BOTTOM )
         {
         	draw_sprite(option_menu_buffer, Option_Images.GetImage ( 4 ), 36, 230);
            if ( mouse_b & 1 )
	         {
   		     	play_sample(menu_beep , 127, 127, 1000, 0);
					clear_keybuf();
					break;
	   		}
			}
         else
	      	draw_sprite(option_menu_buffer, Option_Images.GetImage ( 0 ), 36, 230);
      }
      else
      	draw_sprite(option_menu_buffer, Option_Images.GetImage ( 0 ), 36, 230);
	}
   destroy_sample ( menu_beep );
   fade_out( 5 );
 }
//****************************************************************************
void Game_Init ()
{
	GAME_STARTED = true;
   level_index = 0;
   Init_Stars ( );
   Init_Plane ( );
   enemies = new EnemyTYPE; // make this so it reinitializes every level
   enemies->LoadEnemies ( (char *)level_names[level_index].c_str() , "images/enemy.dat","images/enemy_bullets.dat","images/explode.dat" );
   Begin_Game ();
}
//****************************************************************************
void Begin_Game ( )
{
	install_stream();
	stream_select_mfx( "sound/icecube.wfx" );
	stream_start();

   LOCK_VARIABLE(timer);
   LOCK_FUNCTION(inc_x);
   install_int(inc_x, 1);


	int sound_counter = 3;
   apvector <SAMPLE *> begin_sounds ( 4 );
   begin_sounds [0] = load_sample ("sound/go.wav");
   begin_sounds [1] = load_sample ("sound/one.wav");
   begin_sounds [2] = load_sample ("sound/two.wav");
   begin_sounds [3] = load_sample ("sound/three.wav");

   int startTimer = 0;
	int intro_counter = BEGIN_GAME_PAUSE;
   while ( intro_counter != 33 )
   {
   	if ( intro_counter % 35 == 0 && sound_counter >= 0 )
      {
			play_sample(begin_sounds [sound_counter] , sample_vol, 127, 1000, 0);
         sound_counter--;
		}


   	clear( buffer );
      Draw_Stars( buffer );
   	intro_counter --;
		Move_Stars ();
	   plane_object.Display ( buffer );
     	char temp [3];
      textprintf (buffer, font, 300 , 250, 15, "Level 1");

      blit(buffer, screen, 0, 0, 0, 0, SCREEN_W, SCREEN_H); // Copy Buffer to VRam
      while (( timer - startTimer <= 15 ));
	      startTimer = timer;
   }
}
//****************************************************************************
void Run_Game ( )
{

   bool ok_to_add = false;
   int pause_counter = NEW_LEVEL_PAUSE;
	int rand_attackers;
   int startTimer = 0;
   int add_enemy_timer = 0;
   int add_group_timer = 0;

   SAMPLE *bullet_strike = load_sample ("sound/bullethit.wav");
   SAMPLE *enemy_explode = load_sample ("sound/enemydie.wav");
   SAMPLE *die_sound     = load_sample ("sound/die.wav");

   apvector <SAMPLE *> shoot_sounds ( NUM_WEAPONS );

   shoot_sounds [laser] = load_sample ("sound/laser.wav");
   shoot_sounds [minigun] = load_sample ("sound/minigun.wav");
   shoot_sounds [plasma] = load_sample ("sound/plasma.wav");
   shoot_sounds [torpedo] = load_sample ("sound/torpedo.wav");
   SAMPLE *fire_sound = shoot_sounds [plane_object.GetWeapon()];

	if ( !GAME_STARTED )
		Game_Init ( );
	else
	   set_pallete ( GamePal );

   while ( TRUE )
   {
   	startTimer = timer;
   	clear( buffer );
   	poll_keyboard();

      if ( enemies -> GetNumEnemiesLeft () == 0 )
      {
         if ( level_index == NUM_LEVELS - 1 )
         {
         	GAME_STARTED = false;
         	break;
			}

         if ( pause_counter == 0 )
         {
         	pause_counter = NEW_LEVEL_PAUSE;
	         level_index++;
   	      delete enemies;
      	   enemies = new EnemyTYPE;
				enemies->LoadEnemies ( (char *)level_names[level_index].c_str(), "images/enemy.dat","images/enemy_bullets.dat","images/explode.dat" );
			}
         else
         {
         	char temp [3];
         	pause_counter --;
		      textprintf (buffer, font, 300 , 250, 15, "Level ");
		      textprintf (buffer, font, 300 + text_length(font, "Level ") , 250, 15, strcpy (temp,NumToString (level_index + 2).c_str()));
			}

		}
      else
      {
	      if ( timer - add_group_timer >= 2000 && ! ok_to_add)
   	   {
      		ok_to_add = true;
        		add_group_timer = timer;
				rand_attackers = (rand() % 3) + 1;
   	   }
      	if ( ok_to_add && timer - add_enemy_timer > 100 )
   	   {
		      if ( enemies -> GetNumEnemiesLeft ( ) != 0 && enemies -> GetNumAttackers () <= 4 )
				{
         	  	add_enemy_timer = timer;
            	enemies -> AddAttacker();
	            rand_attackers--;
   	         if ( rand_attackers == 0 )
      	        ok_to_add = false;
         	   else
            	  add_group_timer = timer;
	   		}
   	   }
		}         

      if ( plane_object.GetHealth () <= 0 )
      {
      	plane_object.SetDead (true);
	      play_sample(die_sound , sample_vol, 127, 1000, 0);
      	plane_object.SetNumLives ( plane_object.GetNumLives () - 1 );
			plane_object.SetHealth (DEFAULT_HEALTH);
         fire_sound = shoot_sounds [laser];
		}

      if ( plane_object.GetNumLives () == 0 )
      {
       	clear_keybuf ();
      	GAME_STARTED = false;
   		SAMPLE *game_over = load_sample ("sound/gameover.wav");
         play_sample(game_over , sample_vol, 127, 1000, 0);
			textprintf_centre (screen, font,320 ,240,15, "Game Over" );
         clear_keybuf ();
         while ( ! keypressed () );
         destroy_sample ( game_over );
			break;
		}

    	if ( key[KEY_ESC] )
         break;

      if (!(key[KEY_LEFT] || key[KEY_RIGHT]) || (key[KEY_LEFT] && key[KEY_RIGHT] ))
         plane_object.Normalize ( );

      if ( key[KEY_1] )
      {
			plane_object.SetWeapon ( laser );
         fire_sound = shoot_sounds [laser];
		}
      if ( key[KEY_2] )
      {
			plane_object.SetWeapon ( minigun );
         fire_sound = shoot_sounds [minigun];
		}
      if ( key[KEY_3] )
		{
			plane_object.SetWeapon ( plasma );
         fire_sound = shoot_sounds [plasma];
		}
      if ( key[KEY_4] )
      {
			plane_object.SetWeapon ( torpedo );
         fire_sound = shoot_sounds [torpedo];
		}

		if ( !plane_object.GetDead () )
      {
	      if ( key[KEY_UP] )
   	      plane_object.MoveUp ( );

      	if (key[KEY_DOWN] )
      		plane_object.MoveDown ( );

	      if (!(key[KEY_LEFT] && key[KEY_RIGHT]) )
   	     if (key[KEY_LEFT] )
      	     plane_object.MoveLeft ( );
	        else if (key[KEY_RIGHT] )
					plane_object.MoveRight ( );

      	if (key[KEY_LCONTROL] || key[KEY_RCONTROL] )
	      {
				if ( plane_object.Fire ( ) )
      	   	play_sample(fire_sound , sample_vol, 127, 1000, 0);
	  		}

		}
  		Col_Detect ( *enemies,bullet_strike, enemy_explode );
      enemies -> UpdateAI (plane_object.GetXPos(),plane_object.GetYPos());
      Move_Stars( );
      Draw_Stars( buffer );
	   plane_object.Display ( buffer );
      Display_Info_Bar ( );

      enemies->Display ( buffer );
      blit(buffer, screen, 0, 0, 0, 0, SCREEN_W, SCREEN_H); // Copy Buffer to VRam

      // Lock at 60FPS -- 15 represents 15 milliseconds
      while (( timer - startTimer <= 15 ));
	      startTimer = timer;
   }
   stream_stop();
   destroy_sample ( bullet_strike );
   destroy_sample ( enemy_explode );
   destroy_sample ( die_sound );
   for (int i = 0; i < shoot_sounds.length(); i++)
   	destroy_sample ( shoot_sounds [i] );
}
//****************************************************************************
void Display_Info_Bar ( )
{
   char temp [10];
	textprintf (buffer, font, 45 , 462, 15, "Score:" );
   textprintf (buffer, font, 101 , 462, 15, strcpy ( temp,NumToString ( plane_object.GetScore() ).c_str()) );
  	textprintf (buffer, font, 200 , 462, 15, "Lives:" );
   textprintf (buffer, font, 256 , 462, 15, strcpy ( temp,NumToString ( plane_object.GetNumLives() ).c_str()) );
  	textprintf (buffer, font, 330 , 462, 15, "Health:" );
   textprintf (buffer, font, 394 , 462, 15, strcpy ( temp,NumToString ( plane_object.GetHealth() ).c_str()) );
  	textprintf (buffer, font, 485 , 462, 15, "Weapon:" );
   textprintf (buffer, font, 549 , 462, 15, strcpy ( temp,WeaponToString ( plane_object.GetWeapon() ).c_str()) );
}
//****************************************************************************
void Display_Menu ()
{
	blit(menu_buffer, screen, 0, 0, 0, 0, SCREEN_WIDTH, SCREEN_HEIGHT);
}

//****************************************************************************
void Col_Detect ( EnemyTYPE & enemies,SAMPLE * bullet_strike,SAMPLE * enemy_explode )
{
   BulletTYPE *  plane_bullets = plane_object.GetBullets ();
   BulletNodeTYPE * bullet_list = plane_bullets->GetBulletList ();
   EnemyNodeTYPE * enemy_node = enemies.GetEnemyList ();

   for (; enemy_node != NULL; enemy_node = enemy_node -> next )
   {
   	if ( enemy_node -> attacking && enemy_node -> ypos + EnemyHeights [enemy_node->TypeOfEnemy] > 0)
      {
			for ( ; bullet_list != NULL ; bullet_list = bullet_list -> next )
         {
            if (bullet_list ->visible && check_ppcollision ( enemies.myEnemyMasks[enemy_node->TypeOfEnemy],enemy_node->xpos, enemy_node->ypos, *(plane_bullets->GetMask(bullet_list->weapon)), bullet_list->xPos, bullet_list->yPos ) )
            {
            	play_sample(bullet_strike , sample_vol, 127, 1000, 0);
					enemy_node -> health -= DamageValues [bullet_list -> weapon];
               bullet_list -> visible = false;
				}
			}
			bullet_list = plane_bullets->GetBulletList ();
		 	if ( check_ppcollision ( enemies.myEnemyMasks[enemy_node->TypeOfEnemy],enemy_node->xpos, enemy_node->ypos, *(plane_object.GetMask()), plane_object.GetXPos(), plane_object.GetYPos() ))
	      {
				plane_object.SetHealth ( 0 );
      	   enemy_node-> health = 0 ;
         	plane_object.SetScore (plane_object.GetScore()+KillValues [enemy_node->TypeOfEnemy]);
   	   }
         if ( enemy_node -> health <= 0 )
         {
           	enemy_node -> attacking = false;
           	enemy_node -> dead = true;
            plane_object.SetScore (plane_object.GetScore()+KillValues [enemy_node->TypeOfEnemy]);
            play_sample(enemy_explode , sample_vol, 127, 1000, 0);
    		}
		}
	}
   if ( ! plane_object.GetDead () )
   {
	   BulletTYPE * enemy_bullets = enemies.GetBullets ();
   	BulletNodeTYPE * enemy_bullet_list = enemy_bullets->GetBulletList();
	   for ( ; enemy_bullet_list != NULL; enemy_bullet_list = enemy_bullet_list -> next )
   	{
			if (enemy_bullet_list ->visible && check_ppcollision ( *(plane_object.GetMask()), plane_object.GetXPos(), plane_object.GetYPos() , *(enemy_bullets->GetMask(enemy_bullet_list->weapon)), enemy_bullet_list->xPos, enemy_bullet_list->yPos ) )
	      {
   	      play_sample(bullet_strike , sample_vol, 127, 1000, 0);
				plane_object.SetHealth ( plane_object.GetHealth () -  DamageValues [ enemy_bullet_list -> weapon]);
         	enemy_bullet_list -> visible = false;
			}
   	}
	}      
}
//****************************************************************************
void Init_Plane ( )
{
   plane_images.LoadImages  ( "images/plane.dat" );
	plane_object.LoadPlane ( "images/plane.dat", "images/bullets.dat","images/explode.dat");

	RGB * plane_pal = plane_images.GetPallete();
	set_pallete ( plane_pal );
   get_pallete ( GamePal );
	plane_object.Game_Defaults();   
}
//****************************************************************************
