#include "ps_game.hpp" #include "ps_player.hpp" #include "ga_arena.hpp" #include "ga_trig.hpp" #include "ga_chaser.hpp" #include "ga_bullet.hpp" #include "ga_marker.hpp" #include "ga_chaser.hpp" #include #include extern void ResetMatrix(short m[3][3]); extern unsigned long PadStatus[2]; extern unsigned long PLAYING; extern long gameMode; extern short VAB; int gunHeat = 0; int gunDelay = 0; void AsPSGameManager::UpdateGameState() { AsBullet *bullet; AsMarker *marker; int stopChaser = 0; // if (( PadStatus[AS_PLAYER_ONE] & PADstart ) || ( PadStatus[AS_PLAYER_ONE] & PADcross )) if ( PadStatus[AS_PLAYER_ONE] & PADstart ) { if (!startButtonStatus) { if (gameMode != 3) // start not used during game { gameMode ++; if (gameMode == 3) // about to start game - reset game { bulletManager->Reset(); markerManager->Reset(); chaserManager->Reset(); player->Reset(); switch(mapNumber) { case 0:player->xRoom = 0;player->yRoom = 0;player->zRoom = 0;break; case 1:player->xRoom = 6;player->yRoom = 0;player->zRoom = 0;break; } player->ResetRotation(); player->Setposition(1000,-AS_PLAYER_LEGS,-1000); stage = 0; currentTime = 0; newTimes = 0; srand(1); // remove randomness } if (gameMode == 5) gameMode = 1; startButtonStatus = 1; } if ( PadStatus[AS_PLAYER_ONE] & PADselect ) PLAYING = 0; } //player->Setposition( 1000, -700, -1000 ) ; } else { startButtonStatus = 0; } if (gameMode == 2) { if ( PadStatus[AS_PLAYER_ONE] & PADLleft ) mapNumber = 0; if ( PadStatus[AS_PLAYER_ONE] & PADLright ) mapNumber = 1; } if (gameMode == 3) { currentTime++; if ( PadStatus[AS_PLAYER_ONE] & PADselect ) // quit game { //if (gameMode == 2) GameOver(3); } //if ( PadStatus[AS_PLAYER_TWO] & PADstart ) // PLAYING = 0; if ( PadStatus[AS_PLAYER_ONE] & PADLleft ) player->rotate(0,-50,0); if ( PadStatus[AS_PLAYER_ONE] & PADLright ) player->rotate(0,50,0); if ( PadStatus[AS_PLAYER_ONE] & PADLup ) // forwards player->advance(-100); // player->rotate(-20,0,0); if ( PadStatus[AS_PLAYER_ONE] & PADLdown ) // backwards player->advance(100); // player->rotate(20,0,0); if ( PadStatus[AS_PLAYER_ONE] & PADL1 ) player->strafe(100); if ( PadStatus[AS_PLAYER_ONE] & PADR1 ) player->strafe(-100); if ( PadStatus[AS_PLAYER_ONE] & PADtriangle ) // smart bomb ; //stopChaser = 1 ; /* { if (chaserManager->numberOfChasers < AS_MAX_CHASERS) { int chaserTest = chaserManager->TestChaserMovement(chaserManager->numberOfChasers); if (!(chaserTest & 0x01)) // current direction blocked chaserManager->numberOfChasers++; } } */ //if ( PadStatus[AS_PLAYER_ONE] & PADcircle ) // SsUtKeyOn(VAB, 2, 0, 60, 0, 100, 100); if ( PadStatus[AS_PLAYER_ONE] & PADcross ) { gunDelay--; if (gunDelay <= 0) { gunDelay = 0; if ((currentTime % 5) == 0) { bullet = bulletManager->FindInactiveBullet(); if (bullet) { bullet->Fire(player->X,-player->Y - 300,-player->Z,player->rotation.vy,player->aroundX ,player->xRoom,player->yRoom,player->zRoom); SsUtKeyOn(VAB, 0, 0,36, 0, 100, 100); } // if bullet }// % 5 }// if gundelay <=0 gunHeat++; if (gunHeat > 200) { gunDelay = 50; gunHeat = 0; } } else { gunHeat = 0; } if ( PadStatus[AS_PLAYER_ONE] & PADsquare ) { if ((currentTime % 10) == 0) { marker = markerManager->FindInactiveMarker(); if (marker) { marker->Set(player->X,-player->Y - 300,-player->Z,player->rotation.vy,player->aroundX ,player->xRoom,player->yRoom,player->zRoom); //SsUtKeyOn(VAB, 1, 0, 60, 0, 100, 100); } } } if ( PadStatus[AS_PLAYER_TWO] & PADLright ) player->rotate(20,20,20); player->StoreOldPosition(); player->SetPosition(player->gsObjectCoord.coord.t[0],player->gsObjectCoord.coord.t[1],player->gsObjectCoord.coord.t[2]); HandlePlayerVWallCollision(); HandlePlayerVChaserCollision(); HandleBulletVChaserCollision(); HandleBulletVPlayerCollision(); bulletManager->Update(); //if (!stopChaser)chaserManager->Update(); chaserManager->Update(mapNumber); switch(mapNumber) { case 0: // easy { switch(stage) { case 0: { if ((player->xRoom == 0) && (player->yRoom == 0) && (player->zRoom == 9)) stage = 1; // mainframe reached break; } case 1: { if ((player->xRoom == 0) && (player->yRoom == 0) && (player->zRoom == 0)) { stage = 2; // exit reached GameOver(0); } break; } } break; }// easy case 1: // hard { switch(stage) { case 0: { if ((player->xRoom == 0) && (player->yRoom == 1) && (player->zRoom == 4)) stage = 1; // mainframe reached break; } case 1: { if ((player->xRoom == 6) && (player->yRoom == 0) && (player->zRoom == 0)) { stage = 2; // exit reached GameOver(0); } break; } } break; }// hard }// swich mapNumber } //if (gameMode == 2) } void AsPSGameManager::SetHandlers(AsPSPlayer *_player,AsArenaBuilder *_map, AsChaserManager *_chaserManager,AsBulletManager *_bulletManager,AsMarkerManager *_markerManager) { player = _player; chaserManager = _chaserManager; bulletManager = _bulletManager; markerManager = _markerManager; map = _map; startButtonStatus = 0; fastestTimeSet[0] = 0; fastestTimeSet[1] = 0; slowestTimeSet[0] = 0; slowestTimeSet[1] = 0; longestTimeSet[0] = 0; longestTimeSet[1] = 0; mapNumber = 0; } void AsPSGameManager::GameOver(int _gameOutcome) { gameOutcome = _gameOutcome; gameMode = 4; switch(stage) { case 2: // success { if (!fastestTimeSet[mapNumber]) { fastestTime[mapNumber] = currentTime; fastestTimeSet[mapNumber] = 1; newTimes |= 1; } else { if (currentTime < fastestTime[mapNumber]) { fastestTime[mapNumber] = currentTime; newTimes |= 1; } } if (!slowestTimeSet[mapNumber]) { slowestTime[mapNumber] = currentTime; slowestTimeSet[mapNumber] = 1; newTimes |= 2; } else { if (currentTime > slowestTime[mapNumber]) { slowestTime[mapNumber] = currentTime; newTimes |= 2; } } //break; want it to carry through and check longestTime } case 1: // died after reaching mainframe { if (!longestTimeSet[mapNumber]) { longestTime[mapNumber] = currentTime; longestTimeSet[mapNumber] = 1; newTimes |= 4; } else { if (currentTime > longestTime[mapNumber]) { longestTime[mapNumber] = currentTime; newTimes |= 4; } } break; } } } /* void AsPSGameManager::HandleCollision() { int level, row, column, oldLevel; AsMapArrayElement *mapArray; int movementMask = 0; // use the map element from the last position //level = player->oldY / AS_MAP_ROOM_LENGTH; player->StoreOldPosition(); level = player->yRoom; //double x1 = (double)player->oldZ; //double x2 = (double)AS_MAP_ROOM_LENGTH; //double z = fmod(x1,x2); //column = fmod(player->oldZ,AS_MAP_ROOM_LENGTH); //row = fmod(player->oldX,AS_MAP_ROOM_LENGTH); //float z = (int)(player->oldZ) / AS_MAP_ROOM_LENGTH; //float x = player->oldX / (float)AS_MAP_ROOM_LENGTH; //column = player->oldZ / AS_MAP_ROOM_LENGTH; column = -player->oldZ / AS_MAP_ROOM_LENGTH; row = player->oldX / AS_MAP_ROOM_LENGTH; mapArray = map->GetMapArray(level,row,column); int lengthMinusNose = AS_MAP_ROOM_LENGTH - AS_PLAYER_NOSE; int baseX = row * AS_MAP_ROOM_LENGTH; int baseZ = column * AS_MAP_ROOM_LENGTH; int baseY = level * AS_MAP_ROOM_LENGTH; int playerSubX = player->X - baseX; //int playerSubY = player->Y;// - baseY; int playerSubY = -player->Y; //int playerSubZ = player->Z - baseZ; int playerSubZ = (-player->Z) - baseZ; int newX, newY, newZ; // First check X and Z and find the correct position in XZ plane // Check X if (!mapArray->adjacentLevelNumber[AS_MAP_UP]) // up if (playerSubX < AS_PLAYER_NOSE) playerSubX = AS_PLAYER_NOSE; if (!mapArray->adjacentLevelNumber[AS_MAP_DOWN]) // down if (playerSubX > lengthMinusNose) playerSubX = lengthMinusNose; // Check Z if (!mapArray->adjacentLevelNumber[AS_MAP_LEFT]) // left if (playerSubZ < AS_PLAYER_NOSE) playerSubZ = AS_PLAYER_NOSE; if (!mapArray->adjacentLevelNumber[AS_MAP_RIGHT]) // right if (playerSubZ > lengthMinusNose) playerSubZ = lengthMinusNose; newX = baseX + playerSubX; newZ = baseZ + playerSubZ; column = (int)(newZ / AS_MAP_ROOM_LENGTH); row = (int)(newX / AS_MAP_ROOM_LENGTH); if (playerSubX < 0) movementMask |= 0x01; if (playerSubX >= AS_MAP_ROOM_LENGTH) movementMask |= 0x02; if (playerSubZ < 0) movementMask |= 0x04; if (playerSubZ >= AS_MAP_ROOM_LENGTH) movementMask |= 0x08; oldLevel = level; do { switch(movementMask) { case 0x00: break; case 0x01: level = mapArray->adjacentLevelNumber[AS_MAP_UP] - AS_MAP_LEVEL_OFFSET; break; case 0x02: level = mapArray->adjacentLevelNumber[AS_MAP_DOWN] - AS_MAP_LEVEL_OFFSET; break; case 0x04: level = mapArray->adjacentLevelNumber[AS_MAP_LEFT] - AS_MAP_LEVEL_OFFSET; break; case 0x08: level = mapArray->adjacentLevelNumber[AS_MAP_RIGHT] - AS_MAP_LEVEL_OFFSET; break; default:; // combination movement - can't get to happen except in the large room in which case level shouldn't change } if (oldLevel != level) playerSubY = playerSubY % AS_MAP_ROOM_LENGTH; mapArray = map->GetMapArray(level,row,column); } while (mapArray->stairInfo & 0x02); baseX = row * AS_MAP_ROOM_LENGTH; baseZ = column * AS_MAP_ROOM_LENGTH; playerSubX = player->X - baseX; //playerSubZ = player->Z - baseZ; playerSubZ = (-player->Z) - baseZ; // Check Y - Must check gravity and stairs if (!mapArray->stairInfo) // if no stairs, just check floor { if (playerSubY < AS_PLAYER_LEGS) playerSubY = AS_PLAYER_LEGS; } else { if (mapArray->stairInfo & 0x02) // stairs are facing down { //level--; // drop down to room below, where stairs are facing up //mapArray = map->GetMapArray(level,row,column); baseY -= AS_MAP_ROOM_LENGTH; //playerSubY -= AS_MAP_ROOM_LENGTH; } if (mapArray->stairInfo & 0x04) // right to left, or up to down { if ((mapArray->adjacentLevelNumber[0]) && (mapArray->adjacentLevelNumber[1])) playerSubY = playerSubX + AS_PLAYER_LEGS; // up to down, facing up else playerSubY = (AS_MAP_ROOM_LENGTH - playerSubZ) + AS_PLAYER_LEGS; //right to left, facing up } else // left to right, or down to up { if ((mapArray->adjacentLevelNumber[0]) && (mapArray->adjacentLevelNumber[1])) playerSubY = (AS_MAP_ROOM_LENGTH - playerSubX) + AS_PLAYER_LEGS; // down to up, facing up else playerSubY = playerSubZ + AS_PLAYER_LEGS; //left to right, facing up } //player->aroundY = AS_DEGREES_45; } //newY = baseY + playerSubY; newY = playerSubY; //player->SetPosition(newX, newY, newZ); //player->position(newX, newY, newZ); player->Setposition(newX, -newY, -newZ); player->xRoom = row; //level = player->Y / AS_MAP_ROOM_LENGTH; player->yRoom = level; player->zRoom = column; } */ /* void AsPSGameManager::HandleCollision() { int level, row, column, oldLevel; AsMapArrayElement *mapArray; AsMapLink link; int movementMask = 0; // use the map element from the last position //level = player->oldY / AS_MAP_ROOM_LENGTH; level = player->yRoom; column = -player->oldZ / AS_MAP_ROOM_LENGTH; //PSX row = player->oldX / AS_MAP_ROOM_LENGTH; mapArray = map->GetMapArray(level,row,column); int lengthMinusNose = AS_MAP_ROOM_LENGTH - AS_PLAYER_NOSE; int baseX = row * AS_MAP_ROOM_LENGTH; int baseZ = column * AS_MAP_ROOM_LENGTH; int baseY = level * AS_MAP_ROOM_LENGTH; int playerSubX = player->X - baseX; int playerSubY = player->Y;// - baseY; int playerSubZ = -player->Z - baseZ; // should be positive //PSX int newX, newY, newZ; // First check X and Z and find the correct position in XZ plane // Check X if (!mapArray->adjacentBlock[AS_MAP_UP]) // up if (playerSubX < AS_PLAYER_NOSE) playerSubX = AS_PLAYER_NOSE; if (!mapArray->adjacentBlock[AS_MAP_DOWN]) // down if (playerSubX > lengthMinusNose) playerSubX = lengthMinusNose; // Check Z if (!mapArray->adjacentBlock[AS_MAP_LEFT]) // left if (playerSubZ < AS_PLAYER_NOSE) playerSubZ = AS_PLAYER_NOSE; if (!mapArray->adjacentBlock[AS_MAP_RIGHT]) // right if (playerSubZ > lengthMinusNose) playerSubZ = lengthMinusNose; newX = baseX + playerSubX; newZ = baseZ + playerSubZ; column = newZ / AS_MAP_ROOM_LENGTH; row = newX / AS_MAP_ROOM_LENGTH; int direction = -1; if (playerSubX < 0) direction = AS_MAP_UP; if (playerSubX >= AS_MAP_ROOM_LENGTH) direction = AS_MAP_DOWN; if (playerSubZ < 0) direction = AS_MAP_LEFT; if (playerSubZ >= AS_MAP_ROOM_LENGTH) direction = AS_MAP_RIGHT; if (direction >= 0) { if (mapArray->adjacentBlock[direction] > 1) // link { link = map->links[mapArray->adjacentBlock[direction]]; level = link.y; // Need to implement visualBaseX and visualBaseZ } } baseX = row * AS_MAP_ROOM_LENGTH; baseZ = column * AS_MAP_ROOM_LENGTH; playerSubX = player->X - baseX; playerSubZ = -player->Z - baseZ; //PSX mapArray = map->GetMapArray(level,row,column); playerSubY = 0; // Check Y - Must check gravity and stairs switch (mapArray->stairInfo) { case AS_MAP_STAIRS_LEFTTORIGHT: playerSubY = playerSubZ + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_RIGHTTOLEFT: playerSubY = (AS_MAP_ROOM_LENGTH - playerSubZ) + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_UPTODOWN: playerSubY = playerSubX + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_DOWNTOUP: playerSubY = (AS_MAP_ROOM_LENGTH - playerSubX) + AS_PLAYER_LEGS; break; default: if (playerSubY < AS_PLAYER_LEGS) playerSubY = AS_PLAYER_LEGS; } //newY = baseY + playerSubY; newY = playerSubY; //PSX player->Setposition(newX, -newY, -newZ); //PSX player->SetPosition(newX, -newY, -newZ); //PSX player->xRoom = row; //level = player->Y / AS_MAP_ROOM_LENGTH; player->yRoom = level; player->zRoom = column; } */ void AsPSGameManager::HandlePlayerVWallCollision() { int level, row, column, oldLevel; AsMapArrayElement *mapArray; AsMapLink link; int movementMask = 0; level = player->yRoom; column = player->zRoom; row = player->xRoom; mapArray = map->GetMapArray(level,row,column); int lengthMinusNose = AS_MAP_ROOM_LENGTH - AS_PLAYER_NOSE; int baseX = row * AS_MAP_ROOM_LENGTH; int baseZ = column * AS_MAP_ROOM_LENGTH; int baseY = level * AS_MAP_ROOM_LENGTH; int playerSubX = player->X; int playerSubY;// = player->Y; int playerSubZ = -player->Z; int newX, newY, newZ; int rotation = player->roomRotation; int newRotation = 0; int translation = (int)(AS_MAP_ROOM_LENGTH / 2); MATRIX rotationMatrix; SVECTOR rotationVector; SVECTOR inputVector; VECTOR outputVector; // First check X and Z and find the correct position in XZ plane // Check X if (!mapArray->adjacentBlock[AS_MAP_UP]) // up if (playerSubX < AS_PLAYER_NOSE) playerSubX = AS_PLAYER_NOSE; if (!mapArray->adjacentBlock[AS_MAP_DOWN]) // down if (playerSubX > lengthMinusNose) playerSubX = lengthMinusNose; // Check Z if (!mapArray->adjacentBlock[AS_MAP_LEFT]) // left if (playerSubZ < AS_PLAYER_NOSE) playerSubZ = AS_PLAYER_NOSE; if (!mapArray->adjacentBlock[AS_MAP_RIGHT]) // right if (playerSubZ > lengthMinusNose) playerSubZ = lengthMinusNose; int direction = -1; if (playerSubX < 0) direction = AS_MAP_UP; if (playerSubX >= AS_MAP_ROOM_LENGTH) direction = AS_MAP_DOWN; if (playerSubZ < 0) direction = AS_MAP_LEFT; if (playerSubZ >= AS_MAP_ROOM_LENGTH) direction = AS_MAP_RIGHT; if (direction >= 0) { if (mapArray->adjacentBlock[direction] > 1) // link { link = map->links[mapArray->adjacentBlock[direction]]; level = link.y; row = link.x; column = link.z; //player->roomRotation = map->visualRotation[0][level][row][column];// don't know which replicate if (direction != link.direction) newRotation = map->GetRotation(direction,link.direction); } else // normal adjacent block { switch(direction) { case AS_MAP_UP: row--; break; case AS_MAP_DOWN: row++; break; case AS_MAP_LEFT: column--; break; case AS_MAP_RIGHT: column++; break; } } } // position of player is always 0..AS_MAP_ROOM_LENGTH for all axes if (playerSubX >= AS_MAP_ROOM_LENGTH) playerSubX -= AS_MAP_ROOM_LENGTH; if (playerSubZ >= AS_MAP_ROOM_LENGTH) playerSubZ -= AS_MAP_ROOM_LENGTH; if (playerSubX < 0) playerSubX += AS_MAP_ROOM_LENGTH; if (playerSubZ < 0) playerSubZ += AS_MAP_ROOM_LENGTH; mapArray = map->GetMapArray(level,row,column); // Now we have correct row/column, must check gravity and stairs playerSubY = 0; switch (mapArray->stairInfo) { case AS_MAP_STAIRS_LEFTTORIGHT: playerSubY = playerSubZ + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_RIGHTTOLEFT: playerSubY = (AS_MAP_ROOM_LENGTH - playerSubZ) + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_UPTODOWN: playerSubY = playerSubX + AS_PLAYER_LEGS; break; case AS_MAP_STAIRS_DOWNTOUP: playerSubY = (AS_MAP_ROOM_LENGTH - playerSubX) + AS_PLAYER_LEGS; break; default: if (playerSubY < AS_PLAYER_LEGS) playerSubY = AS_PLAYER_LEGS; } newY = playerSubY; // now rotate player's position to be with the room rotated if (newRotation) { ResetMatrix(rotationMatrix.m); rotationVector.vx = 0; rotationVector.vy = -newRotation; rotationVector.vz = 0; RotMatrix(&rotationVector,&rotationMatrix); inputVector.vx = playerSubX - 1000; inputVector.vy = playerSubY - 1000; inputVector.vz = playerSubZ - 1000; ApplyMatrix(&rotationMatrix,&inputVector,&outputVector); playerSubX = outputVector.vx + 1000; playerSubY = outputVector.vy + 1000; playerSubZ = outputVector.vz + 1000; player->aroundY = (player->aroundY - newRotation) % AS_DEGREES_360; player->rotate(0,newRotation,0); } player->SetPosition(playerSubX, -playerSubY, -playerSubZ); player->Setposition(playerSubX, -playerSubY, -playerSubZ); player->xRoom = row; player->yRoom = level; player->zRoom = column; } /* void AsPSGameManager::HandleChaserCollision() { float xDifference, yDifference, zDifference; int xClose, zClose; AsChaser *chaser; for (int i = 0; i < chaserManager->numberOfChasers; i++) { chaser = chaserManager->GetChaser(i); yDifference = chaser->GetY() - player->Y; if ((yDifference < 1500.0) && (yDifference > -1500.0)) { xDifference = chaser->X - player->X; zDifference = chaser->Z - player->Z; xClose = ((xDifference >= -1000) && (xDifference <= 1000)); zClose = ((zDifference >= -1000) && (zDifference <= 1000)); if (xClose && zClose) gameOver = 1; } } } */ /* void AsPSGameManager::HandleBulletCollision() { AsChaser *currentChaser; AsBullet *currentBullet; for (int i = 0; i < chaserManager->numberOfChasers; i++) { currentChaser = chaserManager->GetChaser(i); for (int j = 0; j < AS_MAX_BULLETS; j++) { currentBullet = bulletManager->GetBullet(j); if (currentBullet->Active()) { if ((currentBullet->xRoom == currentChaser->xRoom) && (currentBullet->yRoom == currentChaser->yRoom) && (currentBullet->zRoom == currentChaser->zRoom)) { currentBullet->Reset(); currentChaser->delay++; } } } } } */ void AsPSGameManager::HandlePlayerVChaserCollision() { AsChaser *currentChaser; AsMapArrayElement *mapArray; AsMapLink link; int xDifference, yDifference, zDifference; int chaserBlockX,chaserBlockY,chaserBlockZ; // block of chaserNumber int directionBlockX,directionBlockY,directionBlockZ; // next block in whatever direction int baseX, baseZ; int rotation; int collision; collision = 0; // This is a once only thing for (int i = 0; i < chaserManager->numberOfChasers; i++) { currentChaser = chaserManager->GetChaser(i); chaserBlockY = currentChaser->yRoom; chaserBlockX = currentChaser->xRoom; chaserBlockZ = currentChaser->zRoom; mapArray = map->GetMapArray(chaserBlockY,chaserBlockX,chaserBlockZ); // cycle through adjacent blocks // 640000 = precalculated 800 * 800 baseX = 0; baseZ = 0; if ((chaserBlockX == player->xRoom) && (chaserBlockY == player->yRoom) && (chaserBlockZ == player->zRoom)) // same { xDifference = currentChaser->X - player->X; zDifference = currentChaser->Z - (- player->Z); // 640000 = precalculated 800 * 800 if (((xDifference * xDifference) + (zDifference * zDifference)) < 640000) collision = 1; } else { for (int d = 0; d < 4; d++) // directions { directionBlockY = chaserBlockY; directionBlockX = chaserBlockX; directionBlockZ = chaserBlockZ; rotation = 0; if (mapArray->adjacentBlock[d] == 0) continue; // nothing to check if (mapArray->adjacentBlock[d] > 1) // link { link = map->links[mapArray->adjacentBlock[d]]; directionBlockY = link.y; directionBlockX = link.x; directionBlockZ = link.z; if (d != link.direction) rotation = map->GetRotation(d,link.direction); } // if link else // normal adjacent block { switch(d) { case AS_MAP_UP: directionBlockX--; break; case AS_MAP_DOWN: directionBlockX++; break; case AS_MAP_LEFT: directionBlockZ--; break; case AS_MAP_RIGHT: directionBlockZ++; break; } // end switch (d) } // else link if (!((directionBlockX == player->xRoom) && (directionBlockY == player->yRoom) && (directionBlockZ == player->zRoom))) // not directionBlock continue; // to next direction switch(d) // this could be optimised but it would be difficult to follow { case AS_MAP_UP: { switch(rotation) { case 0: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = -AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_DOWN: { switch(rotation) { case 0: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_LEFT: { switch(rotation) { case 0: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_RIGHT: { switch(rotation) { case 0: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = -AS_MAP_ROOM_LENGTH; break; } break; } } // end switch rotation // calculate difference xDifference = currentChaser->X - (player->X + baseX); zDifference = currentChaser->Z - ((- player->Z) + baseZ); // 640000 = precalculated 800 * 800 if (((xDifference * xDifference) + (zDifference * zDifference)) < 640000) collision = 1; } // for direction } // else block if (collision) GameOver(1); } // for chaser } void AsPSGameManager::HandleBulletVChaserCollision() { AsChaser *currentChaser; AsBullet *currentBullet; AsMapArrayElement *mapArray; AsMapLink link; int xDifference, yDifference, zDifference; int chaserBlockX,chaserBlockY,chaserBlockZ; // block of chaserNumber int directionBlockX,directionBlockY,directionBlockZ; // next block in whatever direction int baseX, baseZ; int rotation; int collision; for (int i = 0; i < chaserManager->numberOfChasers; i++) { currentChaser = chaserManager->GetChaser(i); chaserBlockY = currentChaser->yRoom; chaserBlockX = currentChaser->xRoom; chaserBlockZ = currentChaser->zRoom; mapArray = map->GetMapArray(chaserBlockY,chaserBlockX,chaserBlockZ); for (int j = 0; j < AS_MAX_BULLETS; j++) { currentBullet = bulletManager->GetBullet(j); if (currentBullet->Active()) { // cycle through adjacent blocks // 422500 = precalculated 650 * 650 collision = 0; baseX = 0; baseZ = 0; if ((chaserBlockX == currentBullet->xRoom) && (chaserBlockY == currentBullet->yRoom) && (chaserBlockZ == currentBullet->zRoom)) // same { xDifference = currentChaser->X - currentBullet->X; zDifference = currentChaser->Z - currentBullet->Z; // 422500 = precalculated 650 * 650 if (((xDifference * xDifference) + (zDifference * zDifference)) < 422500) collision = 1; } else { /* for (int d = 0; d < 4; d++) // directions { directionBlockY = chaserBlockY; directionBlockX = chaserBlockX; directionBlockZ = chaserBlockZ; rotation = 0; if (mapArray->adjacentBlock[d] == 0) continue; // nothing to check if (mapArray->adjacentBlock[d] > 1) // link { link = map->links[mapArray->adjacentBlock[d]]; directionBlockY = link.y; directionBlockX = link.x; directionBlockZ = link.z; if (d != link.direction) rotation = map->GetRotation(d,link.direction); } // if link else // normal adjacent block { switch(d) { case AS_MAP_UP: directionBlockX--; break; case AS_MAP_DOWN: directionBlockX++; break; case AS_MAP_LEFT: directionBlockZ--; break; case AS_MAP_RIGHT: directionBlockZ++; break; } // end switch (d) } // else link if (!((directionBlockX == currentBullet->xRoom) && (directionBlockY == currentBullet->yRoom) && (directionBlockZ == currentBullet->zRoom))) // not directionBlock continue; // to next direction switch(d) // this could be optimised but it would be difficult to follow { case AS_MAP_UP: { switch(rotation) { case 0: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = -AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_DOWN: { switch(rotation) { case 0: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_LEFT: { switch(rotation) { case 0: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_RIGHT: { switch(rotation) { case 0: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = -AS_MAP_ROOM_LENGTH; break; } break; } } // end switch rotation // calculate difference xDifference = currentChaser->X - (currentBullet->X + baseX); zDifference = currentChaser->Z - (currentBullet->Z + baseZ); // 422500 = precalculated 650 * 650 if (((xDifference * xDifference) + (zDifference * zDifference)) < 422500) collision = 1; } // for direction */ } // else block if (collision) { currentBullet->Reset(); currentChaser->delay+=5; SsUtKeyOn(VAB, 1, 0,36, 0, 100, 100); } // if collision } // bullet active } // for bullets } // for chaser } void AsPSGameManager::HandleBulletVPlayerCollision() { AsBullet *currentBullet; AsMapArrayElement *mapArray; AsMapLink link; int xDifference, yDifference, zDifference; int playerBlockX,playerBlockY,playerBlockZ; // block of player int directionBlockX,directionBlockY,directionBlockZ; // next block in whatever direction int baseX, baseZ; int rotation; int collision; int notHit; playerBlockY = player->yRoom; playerBlockX = player->xRoom; playerBlockZ = player->zRoom; mapArray = map->GetMapArray(playerBlockY,playerBlockX,playerBlockZ); for (int j = 0; j < AS_MAX_BULLETS; j++) { notHit = 1; currentBullet = bulletManager->GetBullet(j); if (currentBullet->Active()) { // cycle through adjacent blocks // 422500 = precalculated 650 * 650 collision = 0; baseX = 0; baseZ = 0; if ((playerBlockX == currentBullet->xRoom) && (playerBlockY == currentBullet->yRoom) && (playerBlockZ == currentBullet->zRoom)) // same { xDifference = player->X - currentBullet->X; zDifference = (- player->Z) - currentBullet->Z; // 422500 = precalculated 650 * 650 if (((xDifference * xDifference) + (zDifference * zDifference)) < 422500) collision = 1; } else { /* for (int d = 0; d < 4; d++) // directions { directionBlockY = playerBlockY; directionBlockX = playerBlockX; directionBlockZ = playerBlockZ; rotation = 0; if (mapArray->adjacentBlock[d] == 0) continue; // nothing to check if (mapArray->adjacentBlock[d] > 1) // link { link = map->links[mapArray->adjacentBlock[d]]; directionBlockY = link.y; directionBlockX = link.x; directionBlockZ = link.z; if (d != link.direction) rotation = map->GetRotation(d,link.direction); } // if link else // normal adjacent block { switch(d) { case AS_MAP_UP: directionBlockX--; break; case AS_MAP_DOWN: directionBlockX++; break; case AS_MAP_LEFT: directionBlockZ--; break; case AS_MAP_RIGHT: directionBlockZ++; break; } // end switch (d) } // else link if (!((directionBlockX == currentBullet->xRoom) && (directionBlockY == currentBullet->yRoom) && (directionBlockZ == currentBullet->zRoom))) // not directionBlock continue; // to next direction switch(d) // this could be optimised but it would be difficult to follow { case AS_MAP_UP: { switch(rotation) { case 0: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = -AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_DOWN: { switch(rotation) { case 0: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseZ = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_LEFT: { switch(rotation) { case 0: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = AS_MAP_ROOM_LENGTH; break; } break; } case AS_MAP_RIGHT: { switch(rotation) { case 0: baseZ = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_90: baseX = AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_180: baseZ = -AS_MAP_ROOM_LENGTH; break; case AS_DEGREES_270: baseX = -AS_MAP_ROOM_LENGTH; break; } break; } } // end switch rotation // calculate difference xDifference = player->X - (currentBullet->X + baseX); zDifference = (- player->Z) - (currentBullet->Z + baseZ); // 422500 = precalculated 650 * 650 if (((xDifference * xDifference) + (zDifference * zDifference)) < 422500) collision = 1; } // for direction */ } // else block if (collision) { if (currentBullet->History() > 2) GameOver(2); } else currentBullet->RecordHistory(); // bullet has left player } // bullet active } // for bullets }