The final(?) edition of el14jbed's ELEC2645 project

Dependencies:   N5110 SDFileSystem mbed

Jacob Markl 200852678

Revision:
0:cba7494d5dff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Main.cpp	Thu May 05 13:33:38 2016 +0000
@@ -0,0 +1,1371 @@
+/*
+ELEC2645 Project Jacob Markl 200852678
+
+Week 19 - Tested display, started writing arrays
+
+Week 20 - More arrays, started writing map builders
+
+Week 21 - nothing, did PCB
+
+Sometime During Easter - reworked some bits, More Sprites, Map builder, Map writer, started on player builder and player movement
+
+Week 22 - Reworked player builder and movement. added map interaction
+
+Week 23 - added mobs, music, saving highscores, reading music from the sd card, added a tutorial, added settings, fixed up some bits and bobs.
+
+Week 24 - rounded off all parts of the code, expanded game slightly.
+*/
+#include "mbed.h"
+#include "N5110.h"
+#include "Arrays.h"
+#include "Variables.h"
+#include "Mobs.h"
+#include "Tickersandmore.h"
+#include "SDcard.h"
+#include <vector>
+
+
+
+void init_K64F();
+void BUI_isr();
+void BRI_isr();
+void BDI_isr();
+void BLI_isr();
+void BAI_isr();
+void BBI_isr();
+void map_builder(int mapnumber);
+void player_builder();
+void screen_builder();
+void player_movement();
+void Attack();
+void stats();
+void timer1_isr();
+void timer2_isr();
+void buttons();
+void init_game();
+void outidle();
+void win();
+void lose();
+void main_menu();
+void game();
+void settings();
+void addtopscore();
+void highscores();
+void tutorial();
+void timeoutsound();
+void startscreen();
+void drawlines();
+void level2screen();
+
+//###################### CODE #####################
+
+int main()
+{
+    while(1) {
+        init_K64F();
+        lcd.init();
+        startscreen();
+        main_menu();
+    }
+}
+
+
+void init_K64F()
+{
+    BUI.fall(&BUI_isr);
+    BUI.mode(PullDown);
+    BRI.fall(&BRI_isr);
+    BRI.mode(PullDown);
+    BDI.fall(&BDI_isr);
+    BDI.mode(PullDown);
+    BLI.fall(&BLI_isr);
+    BLI.mode(PullDown);
+    BAI.fall(&BAI_isr);
+    BAI.mode(PullDown);
+    BBI.fall(&BBI_isr);
+    BBI.mode(PullDown);
+
+    g_BUI_flag = 0;
+    g_BRI_flag = 0;
+    g_BDI_flag = 0;
+    g_BLI_flag = 0;
+    g_BAI_flag = 0;
+    g_BBI_flag = 0;
+    g_timer1_flag = 0;
+    g_timer2_flag = 0;
+
+}
+
+
+void BUI_isr()
+{
+    g_BUI_flag = 1;   // set flag in ISR
+}
+
+void BRI_isr()
+{
+    g_BRI_flag = 1;   // set flag in ISR
+}
+
+void BDI_isr()
+{
+    g_BDI_flag = 1;   // set flag in ISR
+}
+
+void BLI_isr()
+{
+    g_BLI_flag = 1;   // set flag in ISR
+}
+
+void BAI_isr()
+{
+    g_BAI_flag = 1;   // set flag in ISR
+}
+
+void BBI_isr()
+{
+    g_BBI_flag = 1;   // set flag in ISR
+}
+
+void map_builder(int mapnumber)
+{
+    int mapx = 0;
+    int mapy = 0;
+    int spritex = 0;
+    int spritey = 0;
+
+    switch(mapnumber) {
+        case 1:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_1[x][y];
+                }
+            }
+            break;
+        case 2:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_2[x][y];
+                }
+            }
+            break;
+        case 3:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_3[x][y];
+                }
+            }
+            break;
+        case 4:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_4[x][y];
+                }
+            }
+            break;
+        case 5:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_5[x][y];
+                }
+            }
+            break;
+        case 6:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_6[x][y];
+                }
+            }
+            break;
+        case 7:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_7[x][y];
+                }
+            }
+            break;
+        case 8:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_8[x][y];
+                }
+            }
+            break;
+        case 9:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_9[x][y];
+                }
+            }
+            break;
+        case 10:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_10[x][y];
+                }
+            }
+            break;
+        case 11:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_11[x][y];
+                }
+            }
+            break;
+        case 12:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_12[x][y];
+                }
+            }
+            break;
+        case 13:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_13[x][y];
+                }
+            }
+            break;
+        default:
+            for(int x = 0; x < 8; x++) {
+                for (int y = 0; y < 8 ; y++) {
+                    g_layout[x][y] = g_map_1[x][y];
+                }
+            }
+            break;
+    }
+
+    for(int x = 0 ; x < 8;  x++) {
+        mapy = 0;
+        for ( int y = 0; y < 8 ; y++) {
+            switch(g_layout[x][y]) {
+                case 0:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 0;
+                        }
+                    }
+
+                    break;
+                case 1:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = g_rock[spritex][spritey];
+                        }
+                    }
+                    break;
+                case 2:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 2+g_exit[spritex][spritey];
+                        }
+                    }
+
+                    break;
+                case 4:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 4+g_door[spritex][spritey];
+                        }
+                    }
+
+                    break;
+                case 5:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 6+g_door[spritex][spritey];
+                        }
+                    }
+                    break;
+                case 6:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 8+g_door[spritex][spritey];
+                        }
+                    }
+                    break;
+                case 7:
+                    for(spritex = 0; spritex < 6; spritex++) {
+                        for (spritey = 0; spritey < 6 ; spritey++) {
+                            g_screen[mapy+spritey][mapx+spritex] = 10+g_door[spritex][spritey];
+                        }
+                    }
+                    break;
+            }
+            mapy = mapy + 6;
+        }
+        mapx = mapx + 6;
+    }
+
+}
+
+void screen_builder()
+{
+    for( int x = 0; x < 48; x++) {
+        for (int y = 0; y < 48 ; y++) {
+            if (((g_screen[x][y])%2)==0) {
+                lcd.clearPixel(x,y);
+            } else {
+                lcd.setPixel(x,y);
+            }
+        }
+    }
+}
+
+void player_builder()
+{
+    int mapx = g_playerlocationy*6;
+    int mapy = g_playerlocationx*6;
+    int csprite[6][6];
+    int player[6][6];
+    if (g_playersprite == true) {
+        for(int x = 0; x < 6; x++) {
+            for (int y = 0; y < 6 ; y++) {
+                csprite[x][y] = g_playerA[x][y];
+            }
+        }
+    } else {
+        for(int x = 0; x < 6; x++) {
+            for (int y = 0; y < 6 ; y++) {
+                csprite[x][y] = g_player[x][y];
+            }
+        }
+    }
+    switch (g_playerfacing) {
+        case 0:
+            for(int x = 0; x < 6; x++) {
+                for (int y = 0; y < 6 ; y++) {
+                    player[x][y] =  csprite[y][5-x];
+                }
+            }
+
+            break;
+
+        case 1:
+            for(int x = 0; x < 6; x++) {
+                for (int y = 0; y < 6 ; y++) {
+                    player[x][y] =  csprite[x][y];
+                }
+            }
+            break;
+
+        case 2:
+            for(int x = 0; x < 6; x++) {
+                for (int y = 0; y < 6 ; y++) {
+                    player[x][y] =  csprite[5-y][x];
+                }
+            }
+
+            break;
+        case 3:
+            for(int x = 0; x < 6; x++) {
+                for (int y = 0; y < 6 ; y++) {
+                    player[x][y] =  csprite[5-x][5-y];
+                }
+            }
+            break;
+
+    }
+    for(int x = 0; x < 6; x++) {
+        for (int y = 0; y < 6 ; y++) {
+            g_screen[mapy+y][mapx+x] = 12+player[x][y];
+
+        }
+    }
+}
+
+void player_movement()
+{
+    bool stop = false;
+    switch(g_playerdirection) {
+        case 0:
+            g_playerfacing = 0;
+            for(int y = 0; y < 6; y++) {
+                if ((g_playerlocationy-1 == g_mobs[y][2])and(g_playerlocationx== g_mobs[y][1])) {
+                    stop=true;
+                }
+            }
+            if (g_layout[g_playerlocationy-1][g_playerlocationx]==4) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=3;
+                    g_playerlocationy=6;
+                    g_state = cfsm[g_state].next_state[0];
+                    mobs();
+                }
+            } else if (stop==true )  {
+            } else if (g_layout[g_playerlocationy-1][g_playerlocationx]==2) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=3;
+                    g_playerlocationy=6;
+                    g_gamewon = true;
+                }
+            } else if (g_layout[g_playerlocationy-1][g_playerlocationx]!=1) {
+                g_playerlocationy--;
+            }
+            break;
+
+        case 1:
+            g_playerfacing = 1;
+            for(int y = 0;
+                    y < 6;
+                    y++) {
+                if ((g_playerlocationy == g_mobs[y][2])and(g_playerlocationx+1== g_mobs[y][1])) {
+                    stop=true;
+                }
+            }
+            if (g_layout[g_playerlocationy][g_playerlocationx+1]==5) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=1;
+                    g_playerlocationy=4;
+                    g_state = cfsm[g_state].next_state[1];
+                    mobs();
+                }
+            } else if (stop==true )  {
+            } else if (g_layout[g_playerlocationy][g_playerlocationx+1]==2) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=1;
+                    g_playerlocationy=4;
+                    g_gamewon = true;
+                }
+            } else if (g_layout[g_playerlocationy][g_playerlocationx+1]!=1) {
+                g_playerlocationx++;
+            }
+
+            break;
+
+        case 2:
+            g_playerfacing = 2;
+            for(int y = 0; y < 6; y++) {
+                if ((g_playerlocationy+1 == g_mobs[y][2])and(g_playerlocationx== g_mobs[y][1])) {
+                    stop=true;
+                }
+            }
+            if (g_layout[g_playerlocationy+1][g_playerlocationx]==6) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=3;
+                    g_playerlocationy=1;
+                    g_state = cfsm[g_state].next_state[2];
+                    mobs();
+                }
+            } else if (stop==true )  {
+            } else if (g_layout[g_playerlocationy+1][g_playerlocationx]==2) {
+                if (cfsm[g_state].cleared==1) {
+                    g_gamewon = true;
+                    g_playerlocationx=3;
+                    g_playerlocationy=1;
+                }
+            } else if (g_layout[g_playerlocationy+1][g_playerlocationx]!=1) {
+                g_playerlocationy++;
+            }
+
+            break;
+
+        case 3:
+            g_playerfacing = 3;
+            for(int y = 0; y < 6; y++) {
+                if ((g_playerlocationy == g_mobs[y][2])and(g_playerlocationx-1== g_mobs[y][1])) {
+                    stop=true;
+                }
+            }
+            if (g_layout[g_playerlocationy][g_playerlocationx-1]==7) {
+                if (cfsm[g_state].cleared==1) {
+                    g_playerlocationx=6;
+                    g_playerlocationy=4;
+                    g_state = cfsm[g_state].next_state[3];
+                    mobs();
+                }
+            } else if (stop==true )  {
+            } else if (g_layout[g_playerlocationy][g_playerlocationx-1]==2) {
+                if (cfsm[g_state].cleared==1) {
+                    g_gamewon = true;
+                    g_playerlocationx=6;
+                    g_playerlocationy=4;
+                }
+            } else if (g_layout[g_playerlocationy][g_playerlocationx-1]!=1)  {
+                g_playerlocationx--;
+            }
+
+
+            break;
+
+        case 4:
+            break;
+    }
+}
+
+void Attack()
+{
+    g_playersprite= true;
+    switch(g_playerfacing) {
+
+        case 0:
+            for(int y = 0; y < 5; y++) {
+                if ((g_playerlocationy-1 == g_mobs[y][2])and(g_playerlocationx== g_mobs[y][1])) {
+                    if (g_mobs[y][0] == 6 ) {
+                        g_playerhp++;
+                    }
+                    g_mobs[y][0]=0;
+                    g_mobs[y][1]=0;
+                    g_mobs[y][2]=0;
+                    g_mobs[y][3]=0;
+                    g_score= g_score+10;
+                }
+            }
+            break;
+        case 1:
+            for(int y = 0; y < 5; y++) {
+                if ((g_playerlocationy == g_mobs[y][2])and(g_playerlocationx+1== g_mobs[y][1])) {
+                    if (g_mobs[y][0] == 6 ) {
+                        g_playerhp++;
+                    }
+                    g_mobs[y][0]=0;
+                    g_mobs[y][1]=0;
+                    g_mobs[y][2]=0;
+                    g_mobs[y][3]=0;
+                    g_score= g_score+10;
+                }
+            }
+            break;
+        case 2:
+            for(int y = 0; y < 5; y++) {
+                if ((g_playerlocationy+1 == g_mobs[y][2])and(g_playerlocationx== g_mobs[y][1])) {
+                    if (g_mobs[y][0] == 6 ) {
+                        g_playerhp++;
+                    }
+                    g_mobs[y][0]=0;
+                    g_mobs[y][1]=0;
+                    g_mobs[y][2]=0;
+                    g_mobs[y][3]=0;
+                    g_score= g_score+10;
+                }
+            }
+            break;
+        case 3:
+            for(int y = 0; y < 5; y++) {
+                if ((g_playerlocationy == g_mobs[y][2])and(g_playerlocationx-1== g_mobs[y][1])) {
+                    if (g_mobs[y][0] == 6 ) {
+                        g_playerhp++;
+                    }
+                    g_mobs[y][0]=0;
+                    g_mobs[y][1]=0;
+                    g_mobs[y][2]=0;
+                    g_mobs[y][3]=0;
+                    g_score= g_score+10;
+                }
+            }
+            break;
+
+    }
+    int clear = 0;
+    for(int y = 0; y < 5; y++) {
+        if (g_mobs[y][0]!=0) {
+            clear++;
+        }
+    }
+    if (clear == 0) {
+        cfsm[g_state].cleared=1;
+    }
+
+
+}
+
+void stats()
+{
+    int startx = 51;
+    int starty = 8;
+    int nx = 0;
+    int ny = 0;
+    for(int H = 0; H < g_playerhp; H++) {
+        for( int x = startx; x < startx+6; x++) {
+            for (int y = starty; y < starty+6 ; y++) {
+                if (((g_heart[ny][nx])%2)==0) {
+                    lcd.clearPixel(x,y);
+                } else {
+                    lcd.setPixel(x,y);
+                }
+                ny++;
+            }
+            ny=0;
+            nx++;
+        }
+        nx=0;
+        startx=startx+6;
+    }
+    lcd.printString("Health",48,0);
+    lcd.printString("Time",54,2);
+    char buffer[14];
+    sprintf(buffer,"%d",g_playtime);
+
+    int newx=63;
+    if (g_playtime>9) {
+        newx= 60;
+    }
+    if (g_playtime>99) {
+        newx= 57;
+    }
+    lcd.printString(buffer,newx,3);
+
+}
+
+void timer1_isr()
+{
+    g_timer1_flag++;
+}
+
+void timer2_isr()
+{
+    g_timer2_flag++;
+}
+
+void buttons()
+{
+    if (g_BUI_flag == 1) {
+        g_BUI_flag = 0;
+        g_playerdirection=0;
+        idle.detach();
+        g_isidle = 0;
+    } else if (g_BRI_flag == 1) {
+        g_BRI_flag = 0;
+        g_playerdirection=1;
+        idle.detach();
+        g_isidle = 0;
+    } else if (g_BDI_flag == 1) {
+        g_BDI_flag = 0;
+        g_playerdirection=2;
+        idle.detach();
+        g_isidle = 0;
+    } else if (g_BLI_flag == 1) {
+        g_BLI_flag = 0;
+        g_playerdirection=3;
+        idle.detach();
+        g_isidle = 0;
+    } else if (g_BAI_flag == 1) {
+        g_BAI_flag = 0;
+        g_playerdirection=4;
+        idle.detach();
+        g_isidle = 0;
+        Attack();
+    } else {
+        g_playerdirection=4;
+    }
+}
+
+void init_game()
+{
+    g_playersprite = false;
+    g_gamewon = false;
+
+    g_level = 1;
+    g_score = 0;
+    g_playerfacing = 0;
+    g_playerhp=3;
+    g_playtime=0;
+    g_direction = 0;
+    g_playerinvun = 0;
+    g_playerdirection = 4;
+    g_playerlocationy = 4;
+    g_playerlocationx = 2;
+    g_state = 0;
+    g_isidle=0;
+    g_BBI_flag=0;
+    g_BAI_flag=0;
+    for(int x = 0; x < 4; x++) {
+        for (int y = 0; y < 5 ; y++) {
+            g_mobs[y][x] = 0;
+        }
+    }
+    memcpy(cfsm,fsm,sizeof(cfsm));
+    readsong();
+
+}
+
+void win()
+{
+    int newx=36;
+    lcd.clear();
+    for (int y = 0; y < g_playerhp ; y++) {
+        g_score=g_score+20;
+    }
+    if (g_playtime>250) {
+    } else {
+        g_score=g_score+(250-g_playtime);
+    }
+
+    char buffer[14];
+    sprintf(buffer,"%d",g_score);
+    addtopscore();
+    writesd();
+    lcd.printString("You Won!",18,1);
+    lcd.printString("Score",27,2);
+    if (g_score>99) {
+        newx= 30;
+    }
+    lcd.printString(buffer,newx,3);
+    lcd.refresh();
+
+
+}
+
+void lose()
+{
+    int newx=36;
+    lcd.clear();
+    char buffer[14];
+    sprintf(buffer,"%d",g_score);
+    lcd.printString("You Died!",15,1);
+    lcd.printString("Score",27,2);
+    if (g_score>99) {
+        newx= 30;
+    }
+    lcd.printString(buffer,newx,3);
+    lcd.printString("Try Again",15,5);
+    lcd.refresh();
+    addtopscore();
+    writesd();
+}
+
+void main_menu()
+{
+    ticker1.detach();
+    lcd.clear();
+    g_options = 4;
+    g_select = 0;
+    g_BAI_flag = 0;
+
+    while(1) {
+        lcd.clear();
+        for(int x = 0; x < 84; x++) {
+            for (int y = 0; y < 15 ; y++) {
+                if (((g_menuscreen[y][x])%2)==0) {
+                    lcd.clearPixel(x,y);
+                } else {
+                    lcd.setPixel(x,y);
+                }
+            }
+        }
+        lcd.printString("LoZ",33,0);
+        lcd.printString("Play",30,2);
+        lcd.printString("Settings",18,3);
+        lcd.printString("Tutorial",18,4);
+        lcd.printString("Highscores",12,5);
+        if (g_BUI_flag == 1) {
+            g_BUI_flag = 0;
+            if (g_select>0) {
+                g_select--;
+            }
+        } else if (g_BDI_flag == 1) {
+            g_BDI_flag = 0;
+            if (g_select<g_options-1) {
+                g_select++;
+            }
+        } else {
+        }
+
+        int nx = 0;
+        int ny = 0;
+
+        for(int x = 3; x < 9; x++) {
+            for (int y = (g_select*8)+17; y < ((g_select*8)+23);
+                    y++) {
+                if (((g_sword[ny][nx])%2)==0) {
+                    lcd.clearPixel(x,y);
+                } else {
+                    lcd.setPixel(x,y);
+                }
+
+                ny++;
+            }
+            ny=0;
+            nx++;
+
+        }
+        nx=0;
+        lcd.refresh();
+        sleep();
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            wait(0.1);
+
+            switch(g_select) {
+                case 0:
+                    init_game();
+                    game();
+                    break;
+
+                case 1:
+                    settings();
+                    break;
+
+                case 2:
+                    tutorial();
+                    break;
+
+                case 3:
+                    highscores();
+                    break;
+
+                default:
+
+                    break;
+            }
+            return;
+        }
+    }
+}
+
+void game()
+{
+    int n=1;
+    ticker1.attach(&timer1_isr,0.5);
+    ticker2.attach(&timer2_isr,g_musicarray[0]);
+    while (1) {
+
+
+        lcd.clear();
+        if (g_playerhp !=0) {
+            if (g_playerinvun > 0) {
+                g_playerinvun--;
+            }
+            g_playersprite= false;
+            buttons();
+            player_movement();
+            map_builder(cfsm[g_state].mapno);
+            player_builder();
+            mobturn();
+            screen_builder();
+            stats();
+            lcd.refresh();
+
+//############################ ATTACK ONLY  ###########
+// if the player has attacked, this section will run and the players attack will be animated.
+
+            if (g_playersprite==true) {
+                lcd.clear();
+                player_builder();
+                screen_builder();
+                stats();
+                lcd.refresh();
+                g_playersprite = false;
+            }
+//#####################################################
+
+
+            if (g_timer1_flag) {
+                g_timer1_flag = 0;
+                g_playtime++;
+            }
+            if (g_timer2_flag) {
+                g_timer2_flag = 0;
+                if (g_music) {
+
+                    tout.attach(&timeoutsound, (g_musicarray[0]/2));
+                    Buzz.period(1.0/1000);
+                    Buzz.write(0.0);
+                    if (g_musicarray[n]!=0) {
+                        Buzz.period(1/(g_musicarray[n]));
+                        Buzz.write(0.5);
+                    }
+
+                    if (n==(g_musicarray.size()-1)) {
+                        n=1;
+                    } else {
+                        n++;
+                    }
+
+
+                }
+            }
+            if (g_gamewon) {
+                if (g_level == 1) {
+                    level2screen();
+                    g_gamewon = 0;
+                    g_level++;
+                    memcpy(cfsm,lvl2fsm,sizeof(cfsm));
+                    g_state = 0;
+                } else {
+                    win();
+                    ticker1.detach();
+                    ticker2.detach();
+                    tout.detach();
+                    idle.detach();
+                    while(1) {
+                        if (g_BAI_flag==1) {
+                            g_BAI_flag==0;
+                            break;
+                        }
+                        sleep();
+                    }
+                    return;
+                }
+            }
+            if (g_BBI_flag) {
+                g_BBI_flag = 0;
+                lcd.clear();
+                lcd.printString("Are you sure",6,0);
+                lcd.printString("you want to",9,1);
+                lcd.printString("quit?",27,2);
+                lcd.printString(" No       Yes ",0,5);
+                lcd.refresh();
+                while(1) {
+                    if (g_BAI_flag==1) {
+                        g_BAI_flag=0;
+                        g_playerhp=0;
+                        break;
+                    } else if (g_BBI_flag==1) {
+                        g_BBI_flag=0;
+                        break;
+
+                    }
+                    sleep();
+                }
+            }
+        } else {
+            lose();
+            ticker1.detach();
+            ticker2.detach();
+            tout.detach();
+            idle.detach();
+
+            while(1) {
+                if (g_BAI_flag==1) {
+                    g_BAI_flag==0;
+                    break;
+                }
+                sleep();
+            }
+            return;
+        }
+        if (g_idle_flag) {
+            g_idle_flag=0;
+            lose();
+            ticker1.detach();
+            ticker2.detach();
+            tout.detach();
+            idle.detach();
+            while(1) {
+                if (g_BAI_flag==1) {
+                    g_BAI_flag==0;
+                    break;
+                }
+                sleep();
+            }
+            return;
+        }
+        if (g_isidle==0) {
+            g_isidle=1;
+            idle.attach(&outidle,100);
+        }
+        sleep();
+    }
+}
+
+void settings()
+{
+    lcd.clear();
+    g_options = 2;
+    g_select = 0;
+    while(1) {
+        g_BAI_flag = 0;
+        g_BBI_flag = 0;
+        lcd.clear();
+        lcd.printString("Settings",18,0);
+        lcd.printString("Music",27,2);
+        lcd.printString("Reset",27,3);
+        if (g_BUI_flag == 1) {
+            g_BUI_flag = 0;
+            if (g_select>0) {
+                g_select--;
+            }
+        } else if (g_BDI_flag == 1) {
+            g_BDI_flag = 0;
+            if (g_select<g_options-1) {
+                g_select++;
+            }
+        } else {
+        }
+
+        int nx = 0;
+        int ny = 0;
+
+        for(int x = 3; x < 9; x++) {
+            for (int y = (g_select*8)+17; y < ((g_select*8)+23);
+                    y++) {
+                if (((g_sword[ny][nx])%2)==0) {
+                    lcd.clearPixel(x,y);
+                } else {
+                    lcd.setPixel(x,y);
+                }
+
+                ny++;
+            }
+            ny=0;
+            nx++;
+
+        }
+        nx=0;
+        lcd.refresh();
+        sleep();
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            switch(g_select) {
+                case 0:
+                    g_music=!g_music;
+                    if (g_music == 1) {
+                        lcd.clear();
+                        lcd.printString("Music On",18,3);
+                        lcd.refresh();
+                        wait(1);
+                    } else {
+                        lcd.clear();
+                        lcd.printString("Music Off",15,3);
+                        lcd.refresh();
+                        wait(1);
+                    }
+
+                    break;
+
+                case 1:
+                    while(1) {
+                        lcd.clear();
+                        lcd.printString("Are",33,1);
+                        lcd.printString("You",33,2);
+                        lcd.printString("Sure?",27,3);
+                        lcd.printString(" No       Yes ",0,5);
+                        lcd.refresh();
+                        sleep();
+                        if (g_BAI_flag==1) {
+                            g_BAI_flag=0;
+                            clearsd();
+                            break;
+                        } else if (g_BBI_flag==1) {
+                            g_BBI_flag=0;
+                            break;
+
+                        }
+                    }
+
+            }
+            break;
+
+        }
+        if (g_BBI_flag == 1) {
+            g_BBI_flag =0;
+            return;
+        }
+    }
+}
+
+
+
+void addtopscore()
+{
+    for(int i = 0; i <= 2; i++) {
+        if (g_score>=g_topscores[i]) {
+            if (i<2) {
+                if (i==0) {
+                    g_topscores[i+2]=g_topscores[i+1];
+                }
+                g_topscores[i+1]=g_topscores[i];
+            }
+            g_topscores[i]=g_score;
+
+            return;
+        }
+    }
+}
+
+
+void highscores()
+{
+    readsd();
+    while(1) {
+        char score1[14];
+        char score2[14];
+        char score3[14];
+        sprintf(score1,"1st %d",g_topscores[0]);
+        sprintf(score2,"2nd %d",g_topscores[1]);
+        sprintf(score3,"3rd %d",g_topscores[2]);
+        lcd.clear();
+        lcd.printString("Highscores",12,0);
+        lcd.printString(score1,21,2);
+        lcd.printString(score2,21,3);
+        lcd.printString(score3,21,4);
+        lcd.printString("back",60,5);
+        lcd.refresh();
+        sleep();
+        if (g_BBI_flag==1) {
+            g_BBI_flag=0;
+            break;
+        }
+    }
+}
+
+void tutorial()
+{
+    g_BAI_flag = 0;
+    lcd.clear();
+    drawlines();
+    lcd.printString("Use the D-pad",3,0);
+    lcd.printString("to control",12,1);
+    lcd.printString("Zordo",27,2);
+
+    ticker1.attach(&timer1_isr,0.5);
+    int startx=39;
+    int starty=30;
+    int ny=0;
+    int nx=0;
+    int loop=0;
+    while(1) {
+
+        if (g_timer1_flag == 1) {
+            g_timer1_flag = 0;
+            switch(loop) {
+
+                case 0:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_player[ny][nx])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop++;
+                    break;
+
+                case 1:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_player[5-nx][ny])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop++;
+                    break;
+
+                case 2:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_player[5-ny][5-nx])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop++;
+                    break;
+
+                case 3:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_player[nx][5-ny])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop=0;
+                    break;
+            }
+        }
+        sleep();
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            wait(0.1);
+            break;
+        }
+    }
+    g_BAI_flag = 0;
+    lcd.clear();
+    drawlines();
+    lcd.printString("The A button",6,0);
+    lcd.printString("will attack",9,1);
+    lcd.printString("with Zordo's",6,2);
+    lcd.printString("Sword",27,3);
+
+    startx=39;
+    starty=36;
+    loop = 0;
+    while(1) {
+        if (g_timer1_flag == 1) {
+            g_timer1_flag = 0;
+            switch(loop) {
+                case 0:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_player[ny][nx])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop++;
+                    break;
+
+                case 1:
+                    for( int x = startx; x < startx+6; x++) {
+                        for (int y = starty; y < starty+6 ; y++) {
+                            if (((g_playerA[ny][nx])%2)==0) {
+                                lcd.clearPixel(x,y);
+                            } else {
+                                lcd.setPixel(x,y);
+                            }
+                            ny++;
+                        }
+                        ny=0;
+                        nx++;
+                    }
+                    nx=0;
+                    lcd.refresh();
+                    lcd.drawRect(startx,starty,6,6,2);
+                    loop=0;
+                    break;
+
+            }
+        }
+        sleep();
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            wait(0.1);
+            break;
+        }
+    }
+    lcd.clear();
+    drawlines();
+    lcd.printString("You must kill",3,0);
+    lcd.printString("all hostiles",6,1);
+    lcd.printString("on a map to",9,2);
+    lcd.printString("go through",12,3);
+    lcd.printString("the door",18,4);
+
+    startx=39;
+    starty=41;
+    while(1) {
+        for( int x = startx; x < startx+6; x++) {
+            for (int y = starty; y < starty+6 ; y++) {
+                if (((g_door[ny][nx])%2)==0) {
+                    lcd.clearPixel(x,y);
+                } else {
+                    lcd.setPixel(x,y);
+                }
+                ny++;
+            }
+            ny=0;
+            nx++;
+        }
+        nx=0;
+        lcd.refresh();
+        sleep();
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            wait(0.1);
+            break;
+        }
+
+    }
+    g_BAI_flag = 0;
+    lcd.clear();
+    lcd.printString("Be Swift,",15,0);
+    lcd.printString("Be Brave,",15,1);
+    lcd.printString("Dont Die.",15,2);
+    lcd.printString("Praise the sun",0,3);
+    lcd.printString("love from",15,4);
+    lcd.printString("-Prince Lonk",6,5);
+    while(1) {
+        if (g_BAI_flag == 1) {
+            g_BAI_flag = 0;
+            wait(0.1);
+            break;
+        }
+    }
+    ticker1.detach();
+}
+void timeoutsound()
+{
+    Buzz.write(0.0);
+}
+
+
+void outidle()
+{
+    g_idle_flag = 1;
+}
+
+void startscreen()
+{
+    for( int x = 0; x < 84; x++) {
+        for (int y = 0; y < 48 ; y++) {
+            if (((g_LoZ[y][x])%2)==0) {
+                lcd.clearPixel(x,y);
+            } else {
+                lcd.setPixel(x,y);
+            }
+        }
+    }
+    lcd.refresh();
+    wait(2);
+
+}
+void drawlines()
+{
+    lcd.drawLine(0,0,0,47,1);
+    lcd.drawLine(1,4,1,43,1);
+    lcd.drawLine(2,10,2,37,1);
+    lcd.drawLine(3,17,3,30,1);
+    lcd.drawLine(83,0,83,47,1);
+    lcd.drawLine(82,4,82,43,1);
+    lcd.drawLine(81,10,81,37,1);
+    lcd.drawLine(80,17,80,30,1);
+}
+
+void level2screen()
+{
+    while(1) {
+        lcd.clear();
+        lcd.printString("Level 2",21,1);
+        lcd.printString("Press A",21,4);
+        lcd.refresh();
+        if (g_BAI_flag) {
+            g_BAI_flag = 0;
+            break;
+        }
+        sleep();
+    }
+}
\ No newline at end of file