Kostadin Chakarov / Mbed 2 deprecated el17kec

Dependencies:   mbed

Committer:
kocemax
Date:
Thu May 09 10:53:00 2019 +0000
Revision:
10:da5743dfb137
Parent:
9:f720f5d87420
Child:
12:b3ec47d606a5
Added test files and completed any left-overs. Ready to submit.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
kocemax 2:006a2ddfabb6 1 #include "Ball.h"
kocemax 8:9b77eea95088 2 #include "Paddle.h"
kocemax 8:9b77eea95088 3 #include <math.h>
kocemax 2:006a2ddfabb6 4
kocemax 8:9b77eea95088 5 /** Constructor */
kocemax 2:006a2ddfabb6 6 Ball::Ball()
kocemax 2:006a2ddfabb6 7 {
kocemax 8:9b77eea95088 8 reset(); /** initial parameters of ball */
kocemax 2:006a2ddfabb6 9 }
kocemax 2:006a2ddfabb6 10
kocemax 8:9b77eea95088 11 /** Destructor - nothing happens here */
kocemax 2:006a2ddfabb6 12 Ball::~Ball()
kocemax 2:006a2ddfabb6 13 {
kocemax 2:006a2ddfabb6 14 }
kocemax 2:006a2ddfabb6 15
kocemax 8:9b77eea95088 16 /** Ball screen edge detection and movement */
kocemax 7:cd3cafda3dd4 17 void Ball::move()
kocemax 7:cd3cafda3dd4 18 {
kocemax 6:39bda45efeed 19 GameObject::move();
kocemax 10:da5743dfb137 20
kocemax 10:da5743dfb137 21 /** Right edge */
kocemax 7:cd3cafda3dd4 22 if (pos.x > WIDTH-1) {
kocemax 8:9b77eea95088 23 velocity.x = -velocity.x;
kocemax 8:9b77eea95088 24 pos.x = WIDTH-1;
kocemax 10:da5743dfb137 25 }
kocemax 10:da5743dfb137 26 /** Left edge */
kocemax 10:da5743dfb137 27 else if(pos.x < 1) {
kocemax 8:9b77eea95088 28 velocity.x = -velocity.x;
kocemax 8:9b77eea95088 29 pos.x = 1;
kocemax 2:006a2ddfabb6 30 }
kocemax 10:da5743dfb137 31 /** Top edge */
kocemax 7:cd3cafda3dd4 32 if (pos.y < 1) {
kocemax 8:9b77eea95088 33 velocity.y = -velocity.y;
kocemax 8:9b77eea95088 34 pos.y = 1;
kocemax 10:da5743dfb137 35 }
kocemax 10:da5743dfb137 36 /** Bottom edge */
kocemax 10:da5743dfb137 37 else if (pos.y > HEIGHT-1) {
kocemax 8:9b77eea95088 38 velocity.y = -velocity.y;
kocemax 8:9b77eea95088 39 pos.y = HEIGHT-1;
kocemax 2:006a2ddfabb6 40 }
kocemax 3:fe856d0890ee 41 }
kocemax 3:fe856d0890ee 42
kocemax 8:9b77eea95088 43
kocemax 8:9b77eea95088 44 #define PI 3.14159265
kocemax 8:9b77eea95088 45 float Deg2Rad = PI / 180;
kocemax 8:9b77eea95088 46 float Rad2Deg = 180 / PI;
kocemax 8:9b77eea95088 47
kocemax 8:9b77eea95088 48 /** NOTE: This is how our coordinate system is setup. */
kocemax 8:9b77eea95088 49 /** angles go clock-wise, right is zero, up is -pi/2, down is pi/2 */
kocemax 8:9b77eea95088 50 /** printf("angle of down: %.02f\n", atan2(1.f, 0)); */
kocemax 8:9b77eea95088 51 /** printf("angle of right: %.02f\n", atan2(0.f, 1)); */
kocemax 8:9b77eea95088 52 /** printf("angle of up: %.02f\n", atan2(-1.f, 0)); */
kocemax 8:9b77eea95088 53
kocemax 8:9b77eea95088 54 /** Standard rotation of a vector by given degrees */
kocemax 8:9b77eea95088 55 /** Example of this function to play around with: https://repl.it/repls/HopefulTrimWordprocessing */
kocemax 8:9b77eea95088 56 void Rotate(Vector2D& v, float degrees)
kocemax 8:9b77eea95088 57 {
kocemax 8:9b77eea95088 58 float s = (float)sin(degrees * Deg2Rad); /** stores sin value betweem -1 and 1 */
kocemax 8:9b77eea95088 59 float c = (float)cos(degrees * Deg2Rad); /** stores cos value betweem -1 and 1 */
kocemax 8:9b77eea95088 60
kocemax 8:9b77eea95088 61 float tx = v.x; /** 2D Vector (tx, ty) for the velocity */
kocemax 8:9b77eea95088 62 float ty = v.y;
kocemax 8:9b77eea95088 63
kocemax 8:9b77eea95088 64 /** Rotation: Multiply vector by rotation matrix */
kocemax 8:9b77eea95088 65 v.x = (c * tx) - (s * ty);
kocemax 8:9b77eea95088 66 v.y = (s * tx) + (c * ty);
kocemax 8:9b77eea95088 67 }
kocemax 8:9b77eea95088 68
kocemax 8:9b77eea95088 69 /** Sets upper and lower boundary for angle
kocemax 8:9b77eea95088 70 * @return clamped angle between sane boundaries
kocemax 8:9b77eea95088 71 */
kocemax 8:9b77eea95088 72 float clamp(float x, float minn, float maxx)
kocemax 3:fe856d0890ee 73 {
kocemax 8:9b77eea95088 74 return min(max(x, minn), maxx);
kocemax 8:9b77eea95088 75 }
kocemax 8:9b77eea95088 76
kocemax 8:9b77eea95088 77
kocemax 8:9b77eea95088 78
kocemax 8:9b77eea95088 79 /** Collision detection between ball and paddle */
kocemax 8:9b77eea95088 80 void Ball::hitPad(Paddle &paddle)
kocemax 8:9b77eea95088 81 {
kocemax 8:9b77eea95088 82 const Vector2D& posPad = paddle.getPos();
kocemax 9:f720f5d87420 83 if (pos.y >= posPad.y - 1 && (pos.x >= posPad.x && pos.x <= posPad.x + paddle.getW())) {
kocemax 8:9b77eea95088 84 /** We hit the pad */
kocemax 8:9b77eea95088 85
kocemax 8:9b77eea95088 86 /** First: rotate about paddle's surface normal (flip upward) */
kocemax 8:9b77eea95088 87 velocity.y = -velocity.y;
kocemax 8:9b77eea95088 88
kocemax 8:9b77eea95088 89 /** Change angle based on distance to center */
kocemax 8:9b77eea95088 90 float distanceSensitivity = 120; /** Add at most this many degrees */
kocemax 8:9b77eea95088 91 float maxDx = paddle.getW()/2; /** Maximum distance from centre */
kocemax 8:9b77eea95088 92 float cx = posPad.x + paddle.getW()/2.0f; /** Maximum distance from current paddle centre */
kocemax 8:9b77eea95088 93 float dx = pos.x - cx; /** Positive dx means right of center, 0 means at center */
kocemax 8:9b77eea95088 94
kocemax 8:9b77eea95088 95 float dangle = dx/maxDx * distanceSensitivity; /** Delta angle, meaning change in angle */
kocemax 8:9b77eea95088 96 float currentAngle = atan2(velocity.y, velocity.x)*Rad2Deg; /** Angle of our original outgoing velocity vector */
kocemax 8:9b77eea95088 97 float newAngle = currentAngle + dangle; /** The current angle + the change in the angle */
kocemax 8:9b77eea95088 98
kocemax 8:9b77eea95088 99 //printf("angle: %.02f %.02f, %.02f\n", dx, currentAngle, newAngle);
kocemax 8:9b77eea95088 100
kocemax 8:9b77eea95088 101
kocemax 8:9b77eea95088 102 /** Always clamp angle in sane boundaries */
kocemax 8:9b77eea95088 103 newAngle = clamp(newAngle, -160, -20); /** Clamp to the range of an upward facing cone (NOTE: -90 degrees is up) */
kocemax 8:9b77eea95088 104
kocemax 8:9b77eea95088 105 /** Rotate the outgoing vector by the clamped dangle */
kocemax 8:9b77eea95088 106 dangle = newAngle - currentAngle;
kocemax 8:9b77eea95088 107 Rotate(velocity, dangle);
kocemax 8:9b77eea95088 108
kocemax 2:006a2ddfabb6 109 }
kocemax 2:006a2ddfabb6 110
kocemax 6:39bda45efeed 111 }
kocemax 6:39bda45efeed 112
kocemax 8:9b77eea95088 113 /** Randomizes the initial x-direction of the ball */
kocemax 6:39bda45efeed 114 int Ball::randomize()
kocemax 4:0e01cbb95434 115 {
kocemax 8:9b77eea95088 116 AnalogIn noisy(PTB0); /** Disconnected pin so will have random noise */
kocemax 8:9b77eea95088 117 srand(1000000*noisy.read()); /** Read the random noise and seed */
kocemax 8:9b77eea95088 118 int direction = rand() % 2; /** Randomise initial direction */
kocemax 8:9b77eea95088 119 int movement; /** Int to store the x-direction */
kocemax 7:cd3cafda3dd4 120 if (direction == 0) {
kocemax 6:39bda45efeed 121 movement = -1;
kocemax 7:cd3cafda3dd4 122 } else if (direction == 1) {
kocemax 6:39bda45efeed 123 movement = 1;
kocemax 6:39bda45efeed 124 }
kocemax 7:cd3cafda3dd4 125 return movement;
kocemax 6:39bda45efeed 126 }
kocemax 6:39bda45efeed 127
kocemax 8:9b77eea95088 128 /** Resets ball's initial parameters when game is over / lost */
kocemax 7:cd3cafda3dd4 129 void Ball::reset()
kocemax 6:39bda45efeed 130 {
kocemax 8:9b77eea95088 131 pos.x = WIDTH/2; /** initial position of ball on x-axis */
kocemax 8:9b77eea95088 132 pos.y = HEIGHT - GAP - 2; /** initial position of ball on y-axis */
kocemax 8:9b77eea95088 133 velocity.x = randomize(); /** initial x-velocity of ball */
kocemax 8:9b77eea95088 134 velocity.y = -1; /** initial y-velocity of ball */
kocemax 8:9b77eea95088 135 w = 1; /** width of the ball */
kocemax 8:9b77eea95088 136 h = 1; /** height of the ball */
kocemax 2:006a2ddfabb6 137 }