void PlayerState::step(float dt) { GameState::step(dt); g_fpsCamera.update(dt); s_input.update(dt); float axis[2] = { 0, 0 }; LocomotionInput input = { dt, 0, 0 }; hkQsTransform t; t.setIdentity(); hkVector4 dir; hkVector4 fwd; fwd.set(0, 0, 1, 0); hkVector4 up; up.set(0, 1, 0, 0); hkQuaternion rstOut; hkSimdFloat32 angle_out = 0; dir.setRotatedDir(t.m_rotation, fwd); hkVector4 cam_dir; const float *from = g_camera.m_eye; const float *to = g_camera.m_at; cam_dir.set(from[0] - to[0], 0, from[2] - to[2]); cam_dir.normalize3(); Actor *a = g_actorWorld.get_actor(m_player); float camera_angle = hkMath::atan2(cam_dir.getSimdAt(0), cam_dir.getSimdAt(2)) - HK_REAL_PI; camera_angle = clamp_angle(camera_angle); float input_angle = s_input.m_leftAngle; float character_angle = get_up_axis_angle(a->m_transform.m_rotation); float angle_diff = input_angle + camera_angle - character_angle; angle_diff = clamp_angle(angle_diff); input.m_desireAngle = input_angle + camera_angle; input.m_dt = dt; input.m_moveVec = s_input.m_leftInput[2]; s_locomotion.m_turnSpeed = 4.0f; update_locomotion(&s_locomotion, input, m_player); g_debugDrawMgr.add_text(RGBCOLOR(125,100,200), "input_angle=%f camera_angle=%f character_angle=%f angle_diff=%f", input_angle * HK_FLOAT_RAD_TO_DEG, camera_angle * HK_FLOAT_RAD_TO_DEG, character_angle * HK_FLOAT_RAD_TO_DEG, angle_diff * HK_FLOAT_RAD_TO_DEG); debug_draw_locomotion(&s_locomotion, m_player); step_debug_ctrl(dt); g_debugDrawMgr.add_grid(20, 5, RGBCOLOR(175,175,175), true); g_debugDrawMgr.add_axis(hkQsTransform::getIdentity(), 2); }
// JFL 22 Jul 09 // JS 21 Apr 12; Added court, paddles, and ball objects // JS 22 Apr 12; Added many object and collision resolution // JS 24 Apr 12; Implemented winning condition int gameMainLoop() { int errorCode = 0; // in case functions return errors // Game object pointers Camera *cam; HeadsUp *hud; InputController *inpCtrl; Court *court; Paddle *paddles[NUM_PLYRS]; Ball *ball; CollisionController *collCtrl; // // UPDATE // // Get input from Keyboard and QE if(inpCtrl = Game.inpCtrl) { inpCtrl->update(); } // if // Update state of the HUD if(hud = Game.hud) { hud->update(); } // if // Only update game-playing state if currently in play if(Game.inPlay) { // Check collisions if(collCtrl = Game.collCtrl) { collCtrl->update(); } // if // Update and resolve paddles for(int i=0; i<NUM_PLYRS; i++) { if(paddles[i] = Game.paddles[i]) { errorCode = paddles[i]->update(); // Print error if any if (errorCode != 0) { qePrintf("**Error: Paddle%d's *inpCtrl invalid!", i); } // if // Resolve collision of the paddles if(collCtrl && errorCode == 0) { if(collCtrl->phw[i]) { errorCode = collCtrl->resolvePaddle(i); // Print error if any if (errorCode != 0) { qePrintf("**CollCtrl's *xyzPad%d invalid!", i); } // if } // if } // if } // if } // for // Update and resolve ball if(ball = Game.ball) { ball->update(); // Resolve collision of ball if(collCtrl) { if(collCtrl->bhp[IDNX_PLY_1] || // After hitting Player1 collCtrl->bhp[IDNX_PLY_2] || // After hitting Player2 collCtrl->bhhw || // After hitting horizontal walls collCtrl->bhbw) // After hitting side walls { errorCode = collCtrl->resolveBall(); // Print error if any if (errorCode != 0) { qePrintf("**CollCtrl's *xyzBal invalid!"); } // if } // if } // if } // if ball } // if inPlay // // WIN CONDITION CHECK // // Check to see if the game is over (If someone gets 3 points) if(Game.scores[IDNX_PLY_1] == 3 || Game.scores[IDNX_PLY_2] == 3) { // Not the first game anymore, regardless Game.firstGame = false; // Game is not in play anymore (until game is restarted) Game.inPlay = false; // Play game end sound Game.sndId = qeSndPlay(snd[SDR_INDX_STR_END_GAME].name); // Manage scores of each paddle for(int i=0; i<NUM_PLYRS; i++) { // Record last scores Game.lastScores[i] = Game.scores[i]; // Clear scores, to prevent this routine from running concurrently Game.scores[i] = 0; } // for } // if // // RESET CONDITONS // // Implement soft reset (spacebar) if(inpCtrl && inpCtrl->pressedSpace()) { // Play game end sound Game.sndId = qeSndPlay(snd[SDR_INDX_STR_END_GAME].name); // Reposition ball's position if(ball = Game.ball) { ball->xyz.x = 0; ball->xyz.z = 0; } // if // Pause game very briefly qeSleep(0.5); // Manage scores of each paddle for(int i=0; i<NUM_PLYRS; i++) { // Record last scores Game.lastScores[i] = Game.scores[i]; // Clear scores, to prevent this routine from running concurrently Game.scores[i] = 0; // Reset the z-position of each paddle if(paddles[i] = Game.paddles[i]) { paddles[i]->xyz.z = PADDLE_INIT_Z; } // if } // for // Skip rest of game loop goto END_RESET; } // if // Implement hard reset (pressing "1") if(inpCtrl && inpCtrl->pressedOne()) { // Play game end sound Game.sndId = qeSndPlay(snd[SDR_INDX_STR_END_GAME].name); // Pause game qeSleep(1.5); // Reinitialize game gameFinal(); gameInit(); gameSetup(); // Skip rest of game loop goto END_RESET; } // if // // DRAW // // DRAW 3D // set 3D camera if((cam=Game.cam) && !(qeInpButton(QEINPBUTTON_ZERO)&2)) { cam->apply(); // set the camera } // if // DRAW COURT, PADDLES, BALL // Draw court if(court=Game.court) { court->draw(); } // if // Draw paddles for(int i=0; i<NUM_PLYRS; i++) { if(paddles[i] = Game.paddles[i]) { paddles[i]->draw(); } // if } // for // Draw ball if(ball=Game.ball) { ball->draw(); } // if // DRAW HUD qefnSysCamBitmap(); // set camera (also turns off depth testing) if((hud=Game.hud)) { hud->draw(); } // if END_RESET: return 0; } // gameMainLoop()