iPhone Game Development - Chris Craft [105]
// calculate a normal vector from the paddle to the puck
CGPoint vector = normalVector(bottomPaddleData.puckLocation.x,
bottomPaddleData.paddleLocation.x, bottomPaddleData.puckLocation.y,
bottomPaddleData.paddleLocation.y);
double speed = paddleSpeed(bottomPaddleData);
vector.x = vector.x * speed;
vector.y = vector.y * speed;
// update the velocity of the puck
bottomPaddleData.puckVelocity.x = vector.x;
bottomPaddleData.puckVelocity.y = vector.y;
bottomPaddleData.intersect = true;
}
else
bottomPaddleData.intersect = false;
dist = distance(bottomPaddleData.puckLocation.x,
topPaddleData.paddleLocation.x, bottomPaddleData.puckLocation.y,
topPaddleData.paddleLocation.y);
if (!topPaddleData.intersect & dist < (PADDLE_RADIUS + PUCK_RADIUS)) {
// calculate a normal vector from the paddle to the puck
CGPoint vector = normalVector(bottomPaddleData.puckLocation.x,
topPaddleData.paddleLocation.x, bottomPaddleData.puckLocation.y,
topPaddleData.paddleLocation.y);
double speed = paddleSpeed(topPaddleData);
vector.x = vector.x * speed;
vector.y = vector.y * speed;
// update the velodity of the puck
bottomPaddleData.puckVelocity.x = vector.x;
bottomPaddleData.puckVelocity.y = vector.y;
bottomPaddleData.intersect = true;
}
else
bottomPaddleData.intersect = false;
// decay the velocity of the puck
if (bottomPaddleData.puckVelocity.x > 0.3)
bottomPaddleData.puckVelocity.x += -PUCK_DECAY_RATE;
else if (bottomPaddleData.puckVelocity.x < -0.3)
bottomPaddleData.puckVelocity.x += PUCK_DECAY_RATE;
if (bottomPaddleData.puckVelocity.y > 0.3)
bottomPaddleData.puckVelocity.y += -PUCK_DECAY_RATE;
else if (bottomPaddleData.puckVelocity.y < -0.3)
bottomPaddleData.puckVelocity.y += PUCK_DECAY_RATE;
// apply terminal velocity.
// the puck should not be traveling so fast that it can pass
// through the paddle without intersecting with it
if (bottomPaddleData.puckVelocity.x > PADDLE_RADIUS)
bottomPaddleData.puckVelocity.x = PADDLE_RADIUS;
else if (bottomPaddleData.puckVelocity.x < -PADDLE_RADIUS)
bottomPaddleData.puckVelocity.x = PADDLE_RADIUS;
if (bottomPaddleData.puckVelocity.y > PADDLE_RADIUS)
bottomPaddleData.puckVelocity.y = PADDLE_RADIUS;
else if (bottomPaddleData.puckVelocity.y < -PADDLE_RADIUS)
bottomPaddleData.puckVelocity.y = PADDLE_RADIUS;
// decay the rotation of the puck
if (bottomPaddleData.puckRotation > 0.001)
bottomPaddleData.puckRotation += -PUCK_SPIN_DECAY_RATE;
else if (bottomPaddleData.puckRotation < -0.001)
bottomPaddleData.puckRotation += PUCK_SPIN_DECAY_RATE;
// move the puck as prescribed by the rotation
bottomPaddleData.puckAngle += bottomPaddleData.puckRotation;
if (bottomPaddleData.puckAngle > 360.0)
bottomPaddleData.puckAngle = bottomPaddleData.puckAngle - 360.0;
// move the puck as prescribed by the velocity
bottomPaddleData.puckLocation.x += bottomPaddleData.puckVelocity.x;
bottomPaddleData.puckLocation.y += bottomPaddleData.puckVelocity.y;
// bounce the puck off left and right walls
if ((bottomPaddleData.puckLocation.x + PUCK_RADIUS) > 320) {
// invert the velocity
bottomPaddleData.puckVelocity.x = -bottomPaddleData.puckVelocity.x;
// move the puck back inbounds before it is drawn
bottomPaddleData.puckLocation.x = 320 - PUCK_RADIUS;
// change the rotation of the puck according to the angle and speed
// that it strikes the wall
bottomPaddleData.puckRotation +=
-(bottomPaddleData.puckVelocity.y * 0.005);
}
if ((bottomPaddleData.puckLocation.x - PUCK_RADIUS) < 0) {
bottomPaddleData.puckVelocity.x = -bottomPaddleData.puckVelocity.x;
bottomPaddleData.puckLocation.x = PUCK_RADIUS;
bottomPaddleData.puckRotation +=
(bottomPaddleData.puckVelocity.y * 0.005);
}
// bounce the puck off the top and bottom walls
if (!messageView) {
if ((bottomPaddleData.puckLocation.y + PUCK_RADIUS) > 480) {
// let the puck go if it is headed through the goal
if ((bottomPaddleData.puckLocation.x < GOAL_START)
| (bottomPaddleData.puckLocation.x > GOAL_END)) {
bottomPaddleData.puckVelocity.y = -bottomPaddleData.puckVelocity.y;
bottomPaddleData.puckLocation.y