Arturs Kozlovskis 201253737

Dependencies:   mbed

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers Functions.cpp Source File

Functions.cpp

00001 //includes
00002 #include "mbed.h"
00003 #include "N5110.h"
00004 #include "Gamepad.h"
00005 #include "Objects.h"
00006 #include "Functions.h"
00007 #include "math.h"
00008 
00009 //creates struct objects
00010 Ball ball;//
00011 Ball_linear ball1;
00012 
00013 //variables for melody
00014 const int _note_array[] = {
00015     NOTE_B0,NOTE_C1
00016 };
00017 const int _note_duration[] = {
00018     3,3
00019 };
00020 
00021 Functions::Functions()
00022 {
00023     //initialises values
00024     _initial_radiuss = 2;
00025     _cannon_y_pos = 40;
00026     _score = 0;
00027     _counter = 1;
00028     _previous = 0;
00029     _now = 0;
00030     _note_count = sizeof(_note_array)/sizeof(int);
00031     _bpm = 160.0;
00032 
00033     for (int i = 0; i < 10; i++) {
00034         ///////////////////////////struct ball parabolic
00035         ball.delta_r[i] = i;
00036         ball.ball_y_pos[i] = _initial_radiuss + i + 1;//the +1 just makes so that the ball does not hit the ceiling but leaves 1 pixel
00037         ball.movement_y_counter[i] = -1;
00038         ball.time_incrementer[i] = 1;
00039         ball.ball_x_pos[i] = 0;
00040         ball.time[i] = 0;
00041         ball.ball_x_incrementer[i] = 1;
00042         ball.ball_trajectory_width[i] = 1;
00043         ///////////////////////////////////struc ball linear
00044         ball1.delta_r[i] = i;
00045         ball1.ball_y_pos[i] = i + 5;
00046         ball1.time_incrementer[i] = 1;
00047         ball1.ball_x_pos[i] = 0;
00048         ball1.movement_y_counter[i] = 1;
00049         ball1.ball_x_incrementer[i] = 1;
00050         ///////////////////////////////////
00051     }
00052 }
00053 
00054 void Functions::ball_position_parabolic(N5110 &lcd, Objects &objects,Gamepad &pad, int c )
00055 {
00056     //increments the time
00057     ball.time[c] += ball.time_incrementer[c];
00058     //while the previous and time value is not the same continu until they do
00059     //creates parabolic movement for the ball
00060     while(_previous != ball.time[c]) {
00061         if (_counter == 1) {
00062             if(ball.ball_y_pos[c] - _initial_radiuss - ball.delta_r[c] - 2 < 0) {
00063                 _previous = 0;
00064             } else {
00065                 _previous = round(pow((ball.ball_y_pos[c] - _initial_radiuss - ball.delta_r[c] - 2)/ball.ball_trajectory_width[c],0.5));
00066             }
00067             _now = round(pow((ball.ball_y_pos[c] - _initial_radiuss - ball.delta_r[c] - 1)/ball.ball_trajectory_width[c],0.5));
00068             //checks if x incrementation has to happen
00069             if (!(_previous == _now)) {
00070                 //checks if ball has reached the end of the screen
00071                 if (ball.ball_x_pos[c] >= (83 - 2 * (_initial_radiuss + ball.delta_r[c])) ) {
00072                     ball.ball_x_incrementer[c] = -1 ;
00073                 }
00074                 if (ball.ball_x_pos[c] <= 0 ) {
00075                     ball.ball_x_incrementer[c] = 1;
00076                 }
00077                 ball.ball_x_pos[c] += ball.ball_x_incrementer[c];
00078             }
00079 
00080             //lcd,x,y,delta_r;
00081             objects.draw_ball(lcd,_initial_radiuss + ball.delta_r[c] + ball.ball_x_pos[c],ball.ball_y_pos[c], ball.delta_r[c]);
00082             //checks if ball has to change direction of movment in y direction
00083             if(ball.ball_y_pos[c] == 45 - _initial_radiuss - ball.delta_r[c] && _counter == 1) {
00084                 ball.time_incrementer[c] = -1;
00085                 _counter = -1;
00086                 // printf("%d \n", _counter);
00087                 break;
00088             }
00089             //increments the balls y position
00090             ball.ball_y_pos[c] += 1;
00091         }
00092         if (_counter == -1) {
00093             _previous = round(pow((ball.ball_y_pos[c] - _initial_radiuss - ball.delta_r[c])/ball.ball_trajectory_width[c],0.5));
00094             _now = round(pow((ball.ball_y_pos[c] - _initial_radiuss - ball.delta_r[c] - 1)/ball.ball_trajectory_width[c],0.5));
00095             //checks if x position has to be incremented
00096             if(!(_previous == _now)) {
00097                 if (ball.ball_x_pos[c] >= (83 - 2 * (_initial_radiuss + ball.delta_r[c])) ) {
00098                     ball.ball_x_incrementer[c] = -1 ;
00099                 }
00100                 if (ball.ball_x_pos[c] <= 0 ) {
00101                     ball.ball_x_incrementer[c] = 1;
00102                 }
00103                 ball.ball_x_pos[c] += ball.ball_x_incrementer[c];
00104             }
00105             //lcd,x,y,delta_r;
00106             objects.draw_ball(lcd,_initial_radiuss + ball.delta_r[c] + ball.ball_x_pos[c],ball.ball_y_pos[c], ball.delta_r[c]);
00107             //checks if movement in y direction has to be changed
00108             if(ball.ball_y_pos[c] == 1 + _initial_radiuss + ball.delta_r[c] && _counter == -1) {
00109                 ball.time_incrementer[c] = 1;
00110                 _counter = 1;
00111                 break;
00112             }
00113             //decrements y position
00114             ball.ball_y_pos[c] += -1;
00115         }
00116         //checks for ball and shot collisions
00117         collision_checker(lcd,objects,pad);
00118     }
00119     lcd.clear();
00120     //lcd,x,y,delta_r;
00121     objects.draw_ball(lcd,_initial_radiuss + ball.delta_r[c] + ball.ball_x_pos[c],ball.ball_y_pos[c], ball.delta_r[c]);
00122 }
00123 
00124 void Functions::ball_position_linear(N5110 &lcd, Objects &objects,Gamepad &pad, int c )
00125 {
00126     //draws the ball
00127     for (int i = 0; i < ball1.movement_y_counter[c]; i++) {
00128         ball1.ball_y_pos[c] =  ball1.ball_y_pos[c] + ball1.time_incrementer[c];
00129         objects.draw_ball(lcd,_initial_radiuss + ball1.delta_r[c] + ball1.ball_x_pos[c],ball1.ball_y_pos[c], ball1.delta_r[c]);
00130         collision_checker(lcd,objects,pad);
00131     }
00132     //clears the after image of the ball
00133     lcd.clear();
00134     //lcd,x,y,delta_r;
00135     //creates just the ball at the end position
00136     objects.draw_ball(lcd,_initial_radiuss + ball1.delta_r[c] + ball1.ball_x_pos[c],ball1.ball_y_pos[c], ball1.delta_r[c]);
00137     //increments in  the x direction
00138     ball1.ball_x_pos[c] += ball1.ball_x_incrementer[c];
00139 }
00140 
00141 void Functions::collision_checker(N5110 &lcd,Objects &objects,Gamepad &pad)
00142 {
00143     //checks for all shots if they have collided
00144     for (int i = 0; i < objects.get_size(); i++) {
00145         //if a pixel in front is black collision has occured
00146         //checks for both pixels that are in front if the shot
00147         for (int j = 0; j < 2; j++) {
00148             //if pixel is black call ball finder function to determine which ball it is
00149             if (lcd.getPixel(objects.get_x_value(i) + j,  objects.get_y_value(i)) == 1) {
00150                 //creates a sound when a shot is created
00151                 pad.tone(150.0,0.005);
00152                 ball1_finder(objects.get_x_value(i) + j,objects.get_y_value(i));
00153                 ball_finder(objects.get_x_value(i) + j,objects.get_y_value(i));
00154                 //erase the shot that has collided
00155                 objects.erase_shot(i);
00156                 break;
00157             }
00158         }
00159     }
00160 }
00161 
00162 void Functions::ball1_finder(int x, int y)
00163 {
00164     int delta_y;
00165     int delta_x;
00166     float delta_r;
00167     float radiuss;
00168     //checks for all the balls if the radiuss of it is in range of the shot
00169     for (int i = 0; i < 10; i++) {
00170         delta_y = ball1.ball_y_pos[i] - y;
00171         delta_x = ball1.ball_x_pos[i] - x + ball1.delta_r[i] + _initial_radiuss;
00172         delta_r = pow(delta_x*delta_x + delta_y*delta_y,0.5);
00173         radiuss = ball1.delta_r[i] + _initial_radiuss;
00174         //comapres the two radius values
00175         if ( delta_r > (radiuss - 0.5f) && delta_r < (radiuss + 0.5f)) {
00176             if (ball1.delta_r[i] == 0) {
00177                 ball1.delta_r[i] += -3;// -3 is because even with radiuss of 0 a 1 pixel ball flies around the screen
00178                 break;
00179             } else {
00180                 ball1.delta_r[i] += -1;
00181                 break;
00182             }
00183         }
00184     }
00185 }
00186 
00187 void Functions::ball_finder(int x, int y)
00188 {
00189     int delta_y;
00190     int delta_x;
00191     float delta_r;
00192     float radiuss;
00193     //checks for all the balls
00194     for (int i = 0; i < 10; i++) {
00195         delta_y = ball.ball_y_pos[i] - y;
00196         delta_x = ball.ball_x_pos[i] - x + ball.delta_r[i] + _initial_radiuss;
00197         delta_r = pow(delta_x*delta_x + delta_y*delta_y,0.5);
00198         radiuss = ball.delta_r[i] + _initial_radiuss;
00199         //compares the two raiduss values
00200         if ( delta_r > (radiuss - 0.5f) && delta_r < (radiuss + 0.5f)) {
00201             if (ball.delta_r[i] == 0) {
00202                 ball.delta_r[i] += -3;// -3 is because even with radiuss of 0 a 1 pixel ball flies around
00203                 break;
00204             } else {
00205                 ball.delta_r[i] += -1;
00206                 break;
00207             }
00208         }
00209     }
00210 }
00211 
00212 bool Functions::cannon_smash(N5110 &lcd, Objects &objects)
00213 {
00214     //if a pixel infront of the cannon is black a collision has occured
00215     //each case check different pixel
00216     for (int i = 0; i < 14; i++) {
00217         switch(i) {
00218             case 0:
00219                 if (lcd.getPixel(objects.get_x_cannon() - 1, _cannon_y_pos + 5 ) == 1) {
00220                     return true;
00221                 }
00222                 break;
00223             case 1:
00224                 if (lcd.getPixel(objects.get_x_cannon() - 1, _cannon_y_pos + 4 ) == 1) {
00225                     return true;
00226                 }
00227                 break;
00228             case 2:
00229                 if (lcd.getPixel(objects.get_x_cannon(), _cannon_y_pos + 3 ) == 1) {
00230                     return true;
00231                 }
00232                 break;
00233             case 3:
00234                 if (lcd.getPixel(objects.get_x_cannon(), _cannon_y_pos + 2 ) == 1) {
00235                     return true;
00236                 }
00237                 break;
00238             case 4:
00239                 if (lcd.getPixel(objects.get_x_cannon() + 1, _cannon_y_pos + 1 ) == 1) {
00240                     return true;
00241                 }
00242                 break;
00243             case 5:
00244                 if (lcd.getPixel(objects.get_x_cannon() + 1, _cannon_y_pos  ) == 1) {
00245                     return true;
00246                 }
00247                 break;
00248             case 6:
00249                 if (lcd.getPixel(objects.get_x_cannon() + 2, _cannon_y_pos - 1) == 1) {
00250                     return true;
00251                 }
00252                 break;
00253             case 7:
00254                 if (lcd.getPixel(objects.get_x_cannon() + 3, _cannon_y_pos - 1 ) == 1) {
00255                     return true;
00256                 }
00257                 break;
00258             case 8:
00259                 if (lcd.getPixel(objects.get_x_cannon() + 4, _cannon_y_pos ) == 1) {
00260                     return true;
00261                 }
00262                 break;
00263             case 9:
00264                 if (lcd.getPixel(objects.get_x_cannon() + 4, _cannon_y_pos + 1 ) == 1) {
00265                     return true;
00266                 }
00267                 break;
00268             case 10:
00269                 if (lcd.getPixel(objects.get_x_cannon() + 5, _cannon_y_pos + 2 ) == 1) {
00270                     return true;
00271                 }
00272                 break;
00273             case 11:
00274                 if (lcd.getPixel(objects.get_x_cannon() + 5, _cannon_y_pos + 3 ) == 1) {
00275                     return true;
00276                 }
00277                 break;
00278             case 12:
00279                 if (lcd.getPixel(objects.get_x_cannon() + 6, _cannon_y_pos + 4 ) == 1) {
00280                     return true;
00281                 }
00282                 break;
00283             case 13:
00284                 if (lcd.getPixel(objects.get_x_cannon() + 6, _cannon_y_pos + 5 ) == 1) {
00285                     return true;
00286                 }
00287                 break;
00288         }
00289     }
00290     return false;
00291 }
00292 
00293 int Functions::random(Gamepad &pad)
00294 {
00295     //reads the two pot values
00296     //it uses the thermal nosise as the random generator
00297     float pot1 = pad.read_pot1();
00298     float pot2 = pad.read_pot2();
00299     while(pot1 > 0.1f) {
00300         pot1 += -0.1;
00301     }
00302     while(pot1 > 0.01f) {
00303         pot1 += -0.01;
00304     }
00305     while(pot1 > 0.001f) {
00306         pot1 += -0.001;
00307     }
00308     while(pot1 > 0.0001f) {
00309         pot1 += -0.0001;
00310     }
00311     while(pot1 > 0.00001f) {
00312         pot1 += -0.00001;
00313     }
00314     while(pot1 > 0.000001f) {
00315         pot1 += -0.000001;
00316     }
00317     while(pot2 > 0.1f) {
00318         pot2 += -0.1;
00319     }
00320     while(pot2 > 0.01f) {
00321         pot2 += -0.01;
00322     }
00323     while(pot2 > 0.001f) {
00324         pot2 += -0.001;
00325     }
00326     while(pot2 > 0.0001f) {
00327         pot2 += -0.0001;
00328     }
00329     while(pot2 > 0.00001f) {
00330         pot2 += -0.00001;
00331     }
00332     while(pot2 > 0.000001f) {
00333         pot2 += -0.000001;
00334     }
00335 
00336     pot1 = pot1 * 100000000;
00337     pot2 = pot2 * 100000000;
00338 
00339     int number = 0;
00340 
00341     if (((pot1 + pot2) / 2) >= 100) {
00342         number = (int)floor((pot1 + pot2) / 20);
00343     } else {
00344         number = (int)floor((pot1 + pot2) / 2);
00345     }
00346     return number;
00347 }
00348 
00349 void Functions::ball_creater_linear(N5110 &lcd, Objects &objects,Gamepad &pad)
00350 {
00351     //creates 3 random values
00352     int random0_99 = random(pad);
00353     int random0_9 = random(pad)%10;
00354     int random0_5 = random(pad)%5;
00355 
00356     //generates a random ball value
00357     if (created_balls.size() == 0) {
00358         created_balls.push_back(random0_9);
00359     } else if (created_balls.size() < 2 ) {
00360         if(_score > 20 &&_score < 40) {
00361             created_balls.push_back(random0_9);
00362         }
00363         if(_score > 100) {
00364             created_balls.push_back(random0_5);
00365         }
00366     }
00367 
00368     //runs for each created ball
00369     for (int i = 0; i < created_balls.size(); i++) {
00370         //sets boundries for balls x position so does not go out of screen
00371         if (ball1.ball_x_pos[created_balls[i]] >= (82 - 2*(_initial_radiuss + ball1.delta_r[created_balls[i]])) ) {
00372             ball1.ball_x_incrementer[created_balls[i]] = -1;
00373             //changes the speed ofo the ball
00374             ball1.movement_y_counter[created_balls[i]] = random0_5 + 1;
00375         }
00376         if (ball1.ball_x_pos[created_balls[i]] <= 0 ) {
00377             ball1.ball_x_incrementer[created_balls[i]] = 1;
00378             //changes the speed of the ball
00379             ball1.movement_y_counter[created_balls[i]] = random0_5 + 1;
00380         }
00381 
00382         //sets boundries for balls y position so does not go out of screen
00383         if((ball1.ball_y_pos[created_balls[i]] + _initial_radiuss + ball1.delta_r[created_balls[i]] ) == 45 ) {
00384             ball1.time_incrementer[created_balls[i]] = -1 ;
00385         }
00386         if((ball1.ball_y_pos[created_balls[i]] + _initial_radiuss + ball1.delta_r[created_balls[i]] + ball1.movement_y_counter[created_balls[i]]) > 45 ) {
00387             ball1.ball_y_pos[created_balls[i]]  = 45 - _initial_radiuss - ball1.delta_r[created_balls[i]] - ball1.movement_y_counter[created_balls[i]];
00388         }
00389         if((ball1.ball_y_pos[created_balls[i]] - _initial_radiuss - ball1.delta_r[created_balls[i]] ) == 0) {
00390             ball1.time_incrementer[created_balls[i]] = 1;
00391         }
00392         if((ball1.ball_y_pos[created_balls[i]] - _initial_radiuss - ball1.delta_r[created_balls[i]] - ball1.movement_y_counter[created_balls[i]] ) < 0) {
00393             ball1.ball_y_pos[created_balls[i]] =  _initial_radiuss + ball1.delta_r[created_balls[i]] + ball1.movement_y_counter[created_balls[i]];
00394         }
00395         //draws the actual ball
00396         ball_position_linear(lcd, objects,pad, created_balls[i]);
00397     }
00398 
00399     //draws the balls again since in each draw lcd.clear() has been used
00400     for(int i = 0; i < created_balls.size(); i++) {
00401         objects.draw_ball(lcd,_initial_radiuss + ball1.delta_r[created_balls[i]] + ball1.ball_x_pos[created_balls[i]],ball1.ball_y_pos[created_balls[i]], ball1.delta_r[created_balls[i]]);
00402     }
00403 
00404     //erases the balls which have been destroyed
00405     for(int i = 0; i < created_balls.size(); i++) {
00406         if(ball1.delta_r[created_balls[i]] == -3) {
00407             created_balls.erase(created_balls.begin() + i);
00408         }
00409     }
00410 
00411     //checks if any of the balls have been destroyed and restores their delta_r
00412     for (int i = 0; i < 10; i++) {
00413         if(ball1.delta_r[i] == -3) {
00414             ball1.delta_r[i] = i;
00415             ball1.ball_y_pos[i] = _initial_radiuss + i;
00416             ball1.ball_x_pos[i] = 0;//_initial_radiuss + i;
00417             pad.play_melody(_note_count,_note_array,_note_duration,_bpm,false);
00418             //scores here
00419             _score += i;
00420         }
00421     }
00422 }
00423 void Functions ::ball_creater_parabolic(N5110 &lcd, Objects &objects, Gamepad &pad)
00424 {
00425     //creates a randmo value
00426     int random0_9 = random(pad)%10;
00427 
00428     //generates a random ball size
00429     if (created_ball.size() == 0 && _score > 40) {
00430         created_ball.push_back(random0_9);
00431     }
00432 
00433     //creates the ball
00434     if(created_ball.size() != 0) {
00435         ball_position_parabolic(lcd, objects,pad, created_ball[0]);
00436 
00437         //draws the linear balls again
00438         for(int i = 0; i < created_balls.size(); i++) {
00439             objects.draw_ball(lcd,_initial_radiuss + ball1.delta_r[created_balls[i]] + ball1.ball_x_pos[created_balls[i]],ball1.ball_y_pos[created_balls[i]], ball1.delta_r[created_balls[i]]);
00440         }
00441         //resets the destroyed ball
00442         if (ball.delta_r[created_ball[0]] == -3) {
00443             pad.play_melody(_note_count,_note_array,_note_duration,_bpm,false);
00444             ball.delta_r[created_ball[0]] = created_ball[0];
00445             ball.ball_x_pos[created_ball[0]] = 0;
00446             ball.ball_y_pos[created_ball[0]] = _initial_radiuss + created_ball[0] + 1;
00447             //scores when a balll is destroyed
00448             _score += created_ball[0] * 2;
00449             created_ball.erase(created_ball.begin());
00450         }
00451     }
00452 }
00453 int Functions::round(float number)
00454 {
00455     //round the passed value
00456     float decimal = number;
00457     while(decimal > 1) {
00458         decimal += -1;
00459     }
00460     if (decimal < 0.5f) {
00461         return floor(number);
00462     } else {
00463         return ceil(number);
00464     }
00465 }
00466 int Functions::get_score()
00467 {
00468     return _score;
00469 }