#include <allegro.h>
#include <cstdlib>
#include <time.h>

class player {
      public:
             int y, ty;
             long score;
             int team; //for drawing code (allows player to play as soviet union or usa)
             }p1;
             
class bot {
      public:
             int y, ty;
             } b1;
             
class projectile {
      public:
             int x, y;
             int tx, ty;
             int shot;
             int hit;
             }bul, rocket;

             
class powerup {
      public:
             int x, y;
             int dis; //for drawing purposes
             int hit; //to determine if player hit it
             int type; //to determine what it does  //1=super speed(bad, lol) //2=speed(good) //3=slowmo  //4=scoreboost
             int away;  //to make it go away if it dosent get hit fast enough/limit use by player
             long lastd; //to compare score to score when last powerup apeared
             }plus1; //love the name
             
class ball {
      public:
             int x, y;
             int tx, ty;
             int dir;
             } bl;
             
int con = 0;
int r = 0;  //for background
int g = 0;  //for background
int b = 0;  //for background
char score[50];

BITMAP *author;
BITMAP *title;
BITMAP *buffer;
BITMAP *usaflag;
BITMAP *ussrflag;
BITMAP *missle;
BITMAP *pwup1;
BITMAP *pwup2;
BITMAP *pwup3;
BITMAP *pwup4;
BITMAP *pwup5;
BITMAP *pwup6;
BITMAP *pwup7;
BITMAP *pwup8;
BITMAP *las;

SAMPLE *back1;
SAMPLE *start;
SAMPLE *paused;
SAMPLE *hitflag;
SAMPLE *lose;
SAMPLE *plsht;
SAMPLE *pow;

void credits() {
     draw_sprite(screen, author, 0, 0);
     textout_ex(screen, font, "Developed by", 300, 50, makecol(0,0,255), makecol(255,0,0));
     rest(3500);
     rectfill(screen, 0, 0, 640, 480, makecol(155,0,0));
     textout_ex(screen, font, "In the Allegro game library", 400, 300, makecol(0,0,255), makecol(255,0,0));
     rest(2500);
     rectfill(screen, 0, 0, 640, 480, makecol(155,0,0));
     textout_ex(screen, font, "Using Dev-Cpp", 200, 100, makecol(0,0,255), makecol(255,0,0));
     rest(2500);
     draw_sprite(screen, title, 0, 0);
     rest(3500); }
     
int instructions() {
     rectfill(screen, 0, 0, 640, 480, makecol(0,0,0));
     
     rect(screen, 10, 45, 600, 195, makecol(255,0,0));
     textout_ex(screen, font, "Game Description:", 100, 50, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "The idea of the game is similar to Pong", 50, 70, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "but there are flags in place of paddles and a missle instead of a ball", 15, 90, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "Try to survive as long as possible to get a high score", 15, 110, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "Sometimes, powerups will appear. Shoot them to activate them", 15, 130, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "As your score gets higher, the missle will get faster", 15, 150, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "The flag you choose will be on the right side of the screen", 15, 170, makecol(223,238,45), makecol(0,0,0));
     
     rect(screen, 35, 245, 135, 475, makecol(255,0,0));
     textout_ex(screen, font, "Powerups:", 40, 250, makecol(223,238,45), makecol(0,0,0));
     draw_sprite(screen, pwup1, 44, 270);
     draw_sprite(screen, pwup2, 44, 300);
     draw_sprite(screen, pwup3, 44, 330);
     draw_sprite(screen, pwup4, 44, 360);
     draw_sprite(screen, pwup5, 44, 390);
     draw_sprite(screen, pwup6, 44, 420);
     draw_sprite(screen, pwup7, 44, 450);
     draw_sprite(screen, pwup8, 74, 270);
     
     rect(screen, 160, 230, 285, 340, makecol(255,0,0));
     textout_ex(screen, font, "Other Objects:", 170, 235, makecol(223,238,45), makecol(0,0,0));
     draw_sprite(screen, usaflag, 165, 255);
     draw_sprite(screen, ussrflag, 185, 255);
     draw_sprite(screen, missle, 205, 255);
     
     rect(screen, 275, 345, 630, 475, makecol(255,0,0));
     textout_ex(screen, font, "Controls:", 320, 350, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "Use the arrow keys to move up and down", 290, 370, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "Press 1 to continue as USA or 2 to be USSR", 280, 390, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "Press SPACE to shoot", 280, 430, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "You can press ESC at any time to quit", 280, 450, makecol(223,238,45), makecol(0,0,0));
     textout_ex(screen, font, "You can press ENTER to pause at any time", 280, 410, makecol(223,238,45), makecol(0,0,0));
     while (p1.team==0) {
           if (key[KEY_ESC])
           return 0;
           if (key[KEY_1])
           p1.team = 1;
           if (key[KEY_2])
           p1.team = 2;
           rest(10); } }
           
void draw_screen() {
     rectfill(buffer, bl.x - 2, bl.y - 2, bl.x + 22, bl.y + 22, makecol(r,g,b));
     if (bl.dir==1)
     draw_sprite(buffer, missle, bl.x, bl.y);
     else if (bl.dir==2)
     draw_sprite_h_flip(buffer, missle, bl.x, bl.y);
     else if (bl.dir==3)
     draw_sprite_vh_flip(buffer, missle, bl.x, bl.y);
     else if (bl.dir==4)
     draw_sprite_v_flip(buffer, missle, bl.x, bl.y);
     rectfill(buffer, 625, p1.ty, 640, p1.ty + 80, makecol(r,g,b));
     
     if (p1.team==1) {
     draw_sprite(buffer, usaflag, 625, p1.y);
     rectfill(buffer, 0, b1.ty, 15, b1.ty + 80, makecol(r,g,b));
     draw_sprite(buffer, ussrflag, 0, b1.y);}
     
     else if (p1.team==2) {
     draw_sprite(buffer, ussrflag, 625, p1.y);
     rectfill(buffer, 0, b1.ty, 15, b1.ty + 80, makecol(r,g,b));
     draw_sprite(buffer, usaflag, 0, b1.y);}
     
     if (plus1.dis==1 && plus1.type==1)
     draw_sprite(buffer, pwup1, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==2)
     draw_sprite(buffer, pwup2, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==3)
     draw_sprite(buffer, pwup3, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==4)
     draw_sprite(buffer, pwup4, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==5)
     draw_sprite(buffer, pwup5, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==6)
     draw_sprite(buffer, pwup6, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==7)
     draw_sprite(buffer, pwup7, plus1.x, plus1.y);
     else if (plus1.dis==1 && plus1.type==8)
     draw_sprite(buffer, pwup8, plus1.x, plus1.y);
     
     if (plus1.away==1){
     rectfill(buffer, plus1.x, plus1.y, plus1.x + 20, plus1.y + 20, makecol(r,g,b));
     rectfill(buffer, 20, 0, 600, 30, makecol(r,g,b));}
     if (plus1.hit==1)
     rectfill(buffer, plus1.x, plus1.y, plus1.x + 20, plus1.y + 20, makecol(r,g,b));
     
     if (bul.shot==1){
     rectfill(buffer, bul.tx - 8, bul.ty - 8, bul.tx + 8, bul.ty + 8, makecol(r,g,b));
     draw_sprite(buffer, las, bul.x-6, bul.y-6);}
     
     if (plus1.hit==1 && plus1.type==1 && plus1.away>1)
     textout_ex(buffer, font, "Mega Speed!!", 280, 15, makecol(255,0,0), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==2 && plus1.away>1)
     textout_ex(buffer, font, "Double Player Speed!!", 280, 15, makecol(0,255,0), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==3 && plus1.away>1)
     textout_ex(buffer, font, "Slow Motion!!", 280, 15, makecol(223,238,45), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==4 && plus1.away>1)
     textout_ex(buffer, font, "Score Boost!!", 280, 15, makecol(0,255,0), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==5 && plus1.away>1)
     textout_ex(buffer, font, "Color Change!!", 280, 15, makecol(30,30,255), makecol(255,255,255));
     else if (plus1.hit==1 && plus1.type==6 && plus1.away>1)
     textout_ex(buffer, font, "Enemy Frozen!!", 280, 15, makecol(10,190,255), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==7 && plus1.away>1)
     textout_ex(buffer, font, "Player Frozen!!", 280, 15, makecol(10,190,255), makecol(r,g,b));
     else if (plus1.hit==1 && plus1.type==8 && plus1.away>1)
     textout_ex(buffer, font, "Score Frozen!!", 280, 15, makecol(10,190,255), makecol(r,g,b));
     
     textprintf(buffer ,font, 80, 470, makecol(223,238,45), "%i", p1.score);
     textout_ex(buffer, font, "Score:", 20, 470, makecol(223,238,45), makecol(r,g,b));
     
     draw_sprite(screen, buffer, 0, 0); }
     
int pause() {
     adjust_sample(back1, 100, 128, 1000, 1);
     play_sample(paused, 255, 128, 1000, 0);
     textout_ex(screen, font, "PAUSED:", 300, 230, makecol(223,238,45), makecol(r,g,b));
     textout_ex(screen, font, "Press C to continue", 300, 245, makecol(223,238,45), makecol(r,g,b));
     textout_ex(screen, font, "Press ESC to quit", 300, 265, makecol(223,238,45), makecol(r,g,b));
     
     while (!key[KEY_C]) {
           rest(3);
           if (key[KEY_ESC])
           return 0; }
           
     adjust_sample(back1, 255, 128, 1000, 1);
     rectfill(screen, 0, 0, 640, 480, makecol(r,g,b)); }
     
void move_player() {
     if (key[KEY_UP] && p1.y-1!=0) {
        p1.ty = p1.y;
        if (plus1.hit==1 && plus1.type==2 && p1.y-2!=0)
        p1.y = p1.y - 2;
        else
        p1.y--;}
        
     else if (key[KEY_DOWN] && p1.y+81!=480) {
          p1.ty = p1.y;
          if (plus1.hit==1 && plus1.type==2 && p1.y+2!=480)
          p1.y = p1.y + 2;
          else
          p1.y++;}}
          
void move_bot() {
     if (bl.y<b1.y+40 && b1.y-1!=0 && bl.dir==2 ^ bl.dir==3 && bl.x<=275) {
        b1.ty = b1.y;
        b1.y--; }
        
     else if (bl.y>b1.y+40 && b1.y+81!=480 && bl.dir==2 ^ bl.dir==3 && bl.x<=275) {
          b1.ty = b1.y;
          b1.y++;} }
          
void move_ball() {
     if (bl.dir==1) {
        bl.ty = bl.y;
        bl.tx = bl.x;
        bl.x++;
        bl.y--; }
        
     else if (bl.dir==2) {
          bl.ty = bl.y;
          bl.tx = bl.x;
          bl.x--;
          bl.y--; }
          
     else if (bl.dir==3) {
          bl.ty = bl.y;
          bl.tx = bl.x;
          bl.x--;
          bl.y++; }
          
     else if (bl.dir==4) {
          bl.ty = bl.y;
          bl.tx = bl.x;
          bl.x++;
          bl.y++; }}
          
void check_ball() {
     if (bl.dir==1) {
        if (bl.y==0) {
        bl.dir = 4;}
        
        if (bl.x+20==625 && bl.y-5>=p1.y && bl.y+5<=p1.y+80) {
        play_sample(hitflag, 150, 128, 1000, 0);
        if (plus1.hit==1 && plus1.type==4)
        p1.score = p1.score + 1000;
        else
        p1.score = p1.score + 100;
        bl.dir = 2;} }
        
     else if (bl.dir==2) {
          if (bl.y==0) {
          bl.dir = 3;}
          
          if (bl.x==15 && bl.y-5<=b1.y+80 && bl.y+5>=b1.y) {
          play_sample(hitflag, 150, 128, 1000, 0); 
          bl.dir = 1;}}
          
     else if (bl.dir==3) {
          if (bl.y+20==480) {
          bl.dir = 2;}
          
          if (bl.x==15 && bl.y-5<=b1.y+80 && bl.y+5>=b1.y){
          play_sample(hitflag, 150, 128, 1000, 0);
          bl.dir = 4;}}
          
     else if (bl.dir==4) {
          if (bl.y+20==480) {
          bl.dir = 1;}
          
          if (bl.x+20==625 && bl.y+5>=p1.y && bl.y-5<=p1.y+80) {
          play_sample(hitflag, 150, 128, 1000, 0);
          if (plus1.hit==1 && plus1.type==4)
          p1.score = p1.score + 1000;
          else
          p1.score = p1.score + 100;
          bl.dir = 3;}} }
          
void check_win() {
     if (bl.x>627)
     con = 1;
     
     if (bl.x<13) {
     p1.score = p1.score + 50000;
     con = 5;}
     
     if (bul.shot==1 && bul.x>=bl.x && bul.x+12<=bl.x+20 && bul.y>=bl.y && bul.y+12<=bl.y+20)
     con = -1; }
     
void check_powerups() {
     if (p1.score>=plus1.lastd + 5000) {
     plus1.lastd = p1.score;
     plus1.hit = 0;
     plus1.away = 2000;
     plus1.dis = 1;
     plus1.type = rand() % 8 + 1;
     plus1.x = 350;
     plus1.y = rand() % 400 + 40;} }
     
void update_powerups() {
     if (plus1.dis==1 && plus1.y>=bl.y-5 && plus1.y+20<=bl.y+25 && bl.x>=348 && bl.x<=372) {
                      play_sample(pow, 255, 128, 1000, 0);
                      plus1.dis = 0;
                      plus1.hit = 1;
                      plus1.away = 1500;
                      if (plus1.type==6 ^ plus1.type==7)
                      plus1.away = 400;}
     
     else if (plus1.dis==1 && plus1.y+25>=bul.y && plus1.y<=bul.y+5 && bul.x>=348 && bul.x<=372) {
          play_sample(pow, 255, 128, 1000, 0);
          plus1.dis = 0;
          plus1.hit = 1;
          plus1.away = 1500;
          if (plus1.type==6 ^ plus1.type==7)
          plus1.away = 400;}
          
     if (plus1.away==0 && plus1.hit==1){
                       plus1.dis = 0;
                       plus1.hit = 0;
                       plus1.type = 0;}
                       
     if (plus1.away!=0)
     plus1.away--;
     
     if (plus1.dis==1 && plus1.away==2)
     plus1.dis = 0;
     
     if (plus1.hit==1 && plus1.type==5 && plus1.away>1498) {
        r = rand() % 255 + 1;
        g = rand() % 255 + 1;
        b = rand() % 255 + 1;
        rectfill(buffer, 0, 0, 640, 480, makecol(r,g,b));}
        
     if (plus1.hit==1 && plus1.type==5 && plus1.away==2){
        r = 0;
        g = 0;
        b = 0;
        rectfill(buffer, 0, 0, 640, 480, makecol(r,g,b));} }
     
void check_shoot() {
     if (key[KEY_SPACE] && bul.shot==0) {
                         play_sample(plsht, 255, 128, 1000, 0);
                         bul.shot = 1;
                         bul.x = 605;
                         bul.y = p1.y + 40;
                         bul.ty = bul.y;
                         bul.tx = bul.x;} }
                         
void update_shot() {
     if (bul.shot==1) {
        bul.tx = bul.x;
        bul.x = bul.x - 5; }
        
     if (bul.x<=320) {
        rectfill(buffer, 310, bul.y - 8, 330, bul.y + 8, makecol(r,g,b));
        bul.x = 0;
        bul.shot = 0;
        bul.tx = bul.x;} }
     
int nap() {
     if (key[KEY_ENTER])
     pause();
     
     if (plus1.away>=1 && plus1.type==1 && plus1.hit==1)
     rest(0);
     else if (plus1.away>=1 && plus1.type==3 && plus1.hit==1)
     rest(10);
     
     else if (p1.score<=30000)
     rest(3);
     else if (p1.score<=70000)
     rest(2);
     else if (p1.score<=100000)
     rest(1);
     else if (p1.score>100000)
     rest(0);}
     
int explode() {
    stop_sample(back1);
    play_sample(lose, 255, 128, 1000, 0);
    
    for (int s = 10; s<=300; s++) {
    circlefill(screen, bul.x, bul.y, s, makecol(223,238,45));
    rest(6);}
    rest(600);
    
    play_sample(start, 200, 128, 1000, 0);
     rectfill(buffer, 0, 0, 640, 480, makecol(255,0,0));
     textout_ex(buffer, font, "You shot the missle dumbass!!!", 230, 140, makecol(0,0,255), makecol(255,0,0));
     textout_ex(buffer, font, "Your score was:", 280, 240, makecol(0,0,255), makecol(255,0,0));
     textprintf(buffer ,font, 400, 240, makecol(223,238,45), "%i", p1.score);
     textout_ex(buffer, font, "Press Q to quit or A to play again", 280, 260, makecol(0,0,255), makecol(255,0,0));
     draw_sprite(screen, buffer, 0, 0);
     while (con!=0) {
           if (key[KEY_A]) 
           con = 0;
           if (key[KEY_Q])
           return 0;
           rest(10);} }
           
int win() {
     stop_sample(back1);
     play_sample(lose, 255, 128, 1000, 0);
     
     for (int s = 10; s<=300; s++) {
     circlefill(screen, bl.x, bl.y, s, makecol(223,238,45));
     rest(6);}
     rest(600);
     
     play_sample(start, 200, 128, 1000, 0);
     rectfill(buffer, 0, 0, 640, 480, makecol(255,0,0));
     textout_ex(buffer, font, "YOU WON!!!", 240, 210, makecol(0,0,255), makecol(255,0,0));
     textout_ex(buffer, font, "Your score was:", 280, 240, makecol(0,0,255), makecol(255,0,0));
     textprintf(buffer ,font, 400, 240, makecol(223,238,45), "%i", p1.score);
     textout_ex(buffer, font, "Press Q to quit or A to play again", 280, 260, makecol(0,0,255), makecol(255,0,0));
     draw_sprite(screen, buffer, 0, 0);
     while (con!=0) {
           if (key[KEY_A]) 
           con = 0;
           if (key[KEY_Q])
           return 0;
           rest(10);} }
           
int after_game() {
     stop_sample(back1);
     play_sample(lose, 255, 128, 1000, 0);
     
     for (int s = 10; s<=300; s++) {
     circlefill(screen, bl.x, bl.y, s, makecol(223,238,45));
     rest(6);}
     rest(600);
     
     play_sample(start, 200, 128, 1000, 0);
     rectfill(buffer, 0, 0, 640, 480, makecol(255,0,0));
     textout_ex(buffer, font, "Your score was:", 280, 240, makecol(0,0,255), makecol(255,0,0));
     textprintf(buffer ,font, 400, 240, makecol(223,238,45), "%i", p1.score);
     textout_ex(buffer, font, "Press Q to quit or A to play again", 280, 260, makecol(0,0,255), makecol(255,0,0));
     draw_sprite(screen, buffer, 0, 0);
     while (con!=0) {
           if (key[KEY_A]) 
           con = 0;
           if (key[KEY_Q])
           return 0;
           rest(10);} }
     


int main() 
{	
	allegro_init();
	install_keyboard();
	install_sound(MIDI_AUTODETECT, DIGI_AUTODETECT, 0);
	
	set_color_depth(32);
	set_gfx_mode(GFX_AUTODETECT, 640, 480, 0, 0);
	
	author = load_bitmap("Graphics/author.bmp", NULL);
	title = load_bitmap("Graphics/title.bmp", NULL);
	usaflag = load_bitmap("Graphics/usaflag.bmp", NULL);
	ussrflag = load_bitmap("Graphics/ussrflag.bmp", NULL);
	missle = load_bitmap("Graphics/missle.bmp", NULL);
	pwup1 = load_bitmap("Graphics/pwup1.bmp", NULL);
	pwup2 = load_bitmap("Graphics/pwup2.bmp", NULL);
	pwup3 = load_bitmap("Graphics/pwup3.bmp", NULL);
	pwup4 = load_bitmap("Graphics/pwup4.bmp", NULL);
	pwup5 = load_bitmap("Graphics/pwup5.bmp", NULL);
	pwup6 = load_bitmap("Graphics/pwup6.bmp", NULL);
	pwup7 = load_bitmap("Graphics/pwup7.bmp", NULL);
	pwup8 = load_bitmap("Graphics/pwup8.bmp", NULL);
	las = load_bitmap("Graphics/laser.bmp", NULL);
	
	back1 = load_sample("Sound_FX/back.wav");
	start = load_sample("Sound_FX/start.wav");
	paused = load_sample("Sound_FX/pause.wav");
	hitflag = load_sample("Sound_FX/hit_flag.wav");
	lose = load_sample("Sound_FX/lose.wav");
	plsht = load_sample("Sound_FX/lazer.wav");
	pow = load_sample("Sound_FX/powerup.wav");
	buffer = create_bitmap(640, 480);
	
	play_sample(start, 200, 128, 1000, 1);
    credits();
    instructions();
    
     start:
    srand (time(NULL));
    bl.x = 320;
    bl.y = 240;
    bl.dir = 3;
    b1.y = 200;
    b1.ty = b1.y;
    p1.y = 200;
    p1.ty = p1.y;
    p1.score = 0;
    bul.shot = 0;
    bul.x = 0;
    plus1.dis = 0;
    plus1.hit = 0;
    plus1.away = 0;
    plus1.lastd = 0;
    r = 0;
    g = 0;
    b = 0;
    
    rectfill(buffer, 0, 0, 640, 480, makecol(0,0,0));
    draw_screen();
    draw_sprite(screen, buffer, 0, 0);
    
    textout_ex(screen, font, "Press P to play", 250, 205, makecol(255,0,0), makecol(0,0,0));
    
    while (!key[KEY_P]) {
          if (key[KEY_ESC])
          return 0;
          rest(10); }
    
    stop_sample(start);
          
          rectfill(buffer, 0, 0, 640, 480, makecol(0,0,0));
          stop_sample(back1);
          play_sample(back1, 255, 128, 1000, 1);
    while (con==0) {
          srand(time(NULL));
          if (plus1.type==7){
             if (plus1.hit==0)
             move_player();}
          else
          move_player();
          if (plus1.type==6){
             if (plus1.hit==0)
             move_bot();}
          else
          move_bot();
          check_ball();
          move_ball();
          draw_screen();
          check_win();
          if (plus1.hit==1 && plus1.away>=1 && plus1.type==4)
          p1.score+=3;
          else if (plus1.type==8){
               if (plus1.hit==0)
                  p1.score++;}
          else
          p1.score++;
          check_shoot();
          update_shot();
          check_powerups();
          update_powerups();
          if (key[KEY_ESC])
          return 0;
          nap();}
          
    if (con==-1)
    explode();
    
    else if (con==5)
    win();
    
    else
    after_game();
    
    if (con==0)
    goto start;
          
	
	return 0;
}
END_OF_MAIN();
