From bced345b573d1a0cc72acb4a6ff6200904634841 Mon Sep 17 00:00:00 2001 From: Michael Schwartz Date: Fri, 6 Nov 2020 16:40:35 -0800 Subject: [PATCH] almost done... need to test Boss, need to implement asteroids, need to respawn enemies/etc. after boss, needs game over --- Evade2/CMakeLists.txt | 69 +- Evade2/src/AttractState/GAttractProcess.cpp | 21 +- Evade2/src/AttractState/GAttractState.cpp | 15 +- Evade2/src/GGame.cpp | 43 +- Evade2/src/GGame.h | 13 +- Evade2/src/Game.h | 2 + Evade2/src/GameState/GBossProcess.cpp | 593 ++++++++++++++++++ Evade2/src/GameState/GBossProcess.h | 43 ++ Evade2/src/GameState/GEnemyBulletProcess.cpp | 14 +- Evade2/src/GameState/GEnemyProcess.cpp | 53 +- Evade2/src/GameState/GGameState.cpp | 29 +- Evade2/src/GameState/GGameState.h | 16 +- Evade2/src/GameState/GNextWaveProcess.cpp | 36 ++ Evade2/src/GameState/GNextWaveProcess.h | 25 + Evade2/src/GameState/GPlayerBulletProcess.cpp | 16 +- Evade2/src/GameState/GPlayerProcess.cpp | 22 +- Evade2/src/MainMenuState/GMainMenu.cpp | 12 - Evade2/src/MainMenuState/GMainMenu.h | 18 - Evade2/src/MainMenuState/GMainMenuProcess.cpp | 44 ++ Evade2/src/MainMenuState/GMainMenuProcess.h | 3 + Evade2/src/MainMenuState/GMainMenuState.cpp | 18 + Evade2/src/MainMenuState/GMainMenuState.h | 18 + Evade2/src/SplashState/GSplashProcess.cpp | 2 +- Evade2/src/common/GCamera.cpp | 61 +- Evade2/src/common/GCamera.h | 21 +- Evade2/src/common/GStarfield.cpp | 13 +- Evade2/src/common/GVectorFont.cpp | 7 +- Evade2/src/common/GVectorSprite.cpp | 14 +- 28 files changed, 989 insertions(+), 252 deletions(-) create mode 100644 Evade2/src/GameState/GBossProcess.cpp create mode 100644 Evade2/src/GameState/GBossProcess.h create mode 100644 Evade2/src/GameState/GNextWaveProcess.cpp create mode 100644 Evade2/src/GameState/GNextWaveProcess.h delete mode 100644 Evade2/src/MainMenuState/GMainMenu.cpp delete mode 100644 Evade2/src/MainMenuState/GMainMenu.h create mode 100644 Evade2/src/MainMenuState/GMainMenuState.cpp create mode 100644 Evade2/src/MainMenuState/GMainMenuState.h diff --git a/Evade2/CMakeLists.txt b/Evade2/CMakeLists.txt index af1169f..2d20388 100644 --- a/Evade2/CMakeLists.txt +++ b/Evade2/CMakeLists.txt @@ -25,63 +25,54 @@ INCLUDE(${CMAKE_CURRENT_SOURCE_DIR}/creative-engine/CreativeEngine.cmake) SET(EVADE2_INCLUDE_DIRS - ${CMAKE_SOURCE_DIR}/src - ${CMAKE_SOURCE_DIR}/src/resources - ${CMAKE_SOURCE_DIR}/src/common -# ${CMAKE_SOURCE_DIR}/src/LoadGameState - ${CMAKE_SOURCE_DIR}/src/GameState -# ${CMAKE_SOURCE_DIR}/src/GameState/environment -# ${CMAKE_SOURCE_DIR}/src/GameState/player -# ${CMAKE_SOURCE_DIR}/src/GameState/inventory -# ${CMAKE_SOURCE_DIR}/src/GameState/enemies -# ${CMAKE_SOURCE_DIR}/src/GameState/enemies/final-boss -# ${CMAKE_SOURCE_DIR}/src/GameState/enemies/grunts -# ${CMAKE_SOURCE_DIR}/src/GameState/enemies/mid-bosses -# ${CMAKE_SOURCE_DIR}/src/GameState/status -# ${CMAKE_SOURCE_DIR}/src/img/ -# ${CMAKE_SOURCE_DIR}/src/AttractState -# ${CMAKE_SOURCE_DIR}/src/GameMenuState -# ${CMAKE_SOURCE_DIR}/src/DebugMenuState -# ${CMAKE_SOURCE_DIR}/src/GameOverState -# ${CMAKE_SOURCE_DIR}/src/VictoryState -# ${CMAKE_SOURCE_DIR}/src/MainMenuState -# ${CMAKE_SOURCE_DIR}/src/MainOptionsState - ${CMAKE_SOURCE_DIR}/src/SplashState -# ${CMAKE_SOURCE_DIR}/src/CreditsState -# ${CMAKE_SOURCE_DIR}/src/ResetState - ${CMAKE_BINARY_DIR}/usr/local/include -) + ${CMAKE_SOURCE_DIR}/src + ${CMAKE_SOURCE_DIR}/src/resources + ${CMAKE_SOURCE_DIR}/src/common + ${CMAKE_SOURCE_DIR}/src/SplashState + ${CMAKE_SOURCE_DIR}/src/AttractState + ${CMAKE_SOURCE_DIR}/src/MainMenuState + ${CMAKE_SOURCE_DIR}/src/GameState + # ${CMAKE_SOURCE_DIR}/src/img/ + # ${CMAKE_SOURCE_DIR}/src/GameMenuState + # ${CMAKE_SOURCE_DIR}/src/DebugMenuState + # ${CMAKE_SOURCE_DIR}/src/GameOverState + # ${CMAKE_SOURCE_DIR}/src/VictoryState + # ${CMAKE_SOURCE_DIR}/src/MainOptionsState + # ${CMAKE_SOURCE_DIR}/src/CreditsState + # ${CMAKE_SOURCE_DIR}/src/ResetState + ${CMAKE_BINARY_DIR}/usr/local/include + ) INCLUDE_DIRECTORIES( - ${EVADE2_INCLUDE_DIRS} - ${CREATIVE_ENGINE_INCLUDE_DIRS} + ${EVADE2_INCLUDE_DIRS} + ${CREATIVE_ENGINE_INCLUDE_DIRS} ) # gather Modite sources FILE(GLOB_RECURSE EVADE2_SRC RELATIVE ${CMAKE_SOURCE_DIR} "src/*.cpp") ADD_EXECUTABLE( - ${PROJECT_NAME} - Resources.bin - ${CREATIVE_ENGINE_SOURCE_FILES} - ${EVADE2_SRC} - src/GameState/GGameState.cpp src/GameState/GGameState.h src/common/GStarfield.cpp src/common/GStarfield.h src/GameState/GPlayerBulletProcess.cpp src/GameState/GPlayerBulletProcess.h src/main.cpp src/GameState/GEnemyProcess.cpp src/GameState/GEnemyProcess.h src/GameState/GEnemyBulletProcess.cpp src/GameState/GEnemyBulletProcess.h src/AttractState/GAttractState.cpp src/AttractState/GAttractState.h src/AttractState/GAttractProcess.cpp src/AttractState/GAttractProcess.h src/MainMenuState/GMainMenu.cpp src/MainMenuState/GMainMenu.h src/MainMenuState/GMainMenuProcess.cpp src/MainMenuState/GMainMenuProcess.h) + ${PROJECT_NAME} + Resources.bin + ${CREATIVE_ENGINE_SOURCE_FILES} + ${EVADE2_SRC} + src/GameState/GGameState.cpp src/GameState/GGameState.h src/common/GStarfield.cpp src/common/GStarfield.h src/GameState/GPlayerBulletProcess.cpp src/GameState/GPlayerBulletProcess.h src/main.cpp src/GameState/GEnemyProcess.cpp src/GameState/GEnemyProcess.h src/GameState/GEnemyBulletProcess.cpp src/GameState/GEnemyBulletProcess.h src/AttractState/GAttractState.cpp src/AttractState/GAttractState.h src/AttractState/GAttractProcess.cpp src/AttractState/GAttractProcess.h src/MainMenuState/GMainMenuState.cpp src/MainMenuState/GMainMenuState.h src/MainMenuState/GMainMenuProcess.cpp src/MainMenuState/GMainMenuProcess.h src/GameState/GNextWaveProcess.cpp src/GameState/GNextWaveProcess.h src/GameState/GBossProcess.cpp src/GameState/GBossProcess.h) ProcessorCount(N) if (NOT N EQUAL 0) - set(${PROJECT_NAME}_FLAGS -j${N}) - set(${PROJECT_NAME}_BUILD_FLAGS -j${N}) - set(${PROJECT_NAME}_args ${${PROJECT_NAME}_args} PARALLEL_LEVEL ${N}) + set(${PROJECT_NAME}_FLAGS -j${N}) + set(${PROJECT_NAME}_BUILD_FLAGS -j${N}) + set(${PROJECT_NAME}_args ${${PROJECT_NAME}_args} PARALLEL_LEVEL ${N}) endif () BUILD_COMMAND( - $(MAKE) --silent + $(MAKE) --silent ) # make Modite.app if (APPLE) - SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES MACOSX_BUNDLE TRUE) - INSTALL(TARGETS ${PROJECT_NAME} DESTINATION ".") + SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES MACOSX_BUNDLE TRUE) + INSTALL(TARGETS ${PROJECT_NAME} DESTINATION ".") endif (APPLE) TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${CREATIVE_ENGINE_LINK_LIBRARIES}) diff --git a/Evade2/src/AttractState/GAttractProcess.cpp b/Evade2/src/AttractState/GAttractProcess.cpp index 6bd5b5e..8af019e 100644 --- a/Evade2/src/AttractState/GAttractProcess.cpp +++ b/Evade2/src/AttractState/GAttractProcess.cpp @@ -123,19 +123,19 @@ TBool GAttractProcess::NextState() { ad->timer--; if (ad->timer < 0) { ad->screen++; - if ((game_mode == GAME_STATE_ATTRACT_MODE && ad->screen > MAX_SCREEN) || - (game_mode == GAME_STATE_CREDITS && ad->screen > MAX_CREDITS)) { + if ((game_mode == GAME_STATE_ATTRACT_MODE && ad->screen > MAX_SCREEN)) { gGame->SetState(GAME_STATE_CREDITS); return EFalse; - } else { -// Sound::play_sound(SFX_NEXT_ATTRACT_SCREEN); - InitScreen(); - mState = STATE_TYPEWRITER; - return ETrue; } - } else { - return ETrue; + if (game_mode == GAME_STATE_CREDITS && ad->screen > MAX_CREDITS) { + gGame->SetState(GAME_STATE_MAIN_MENU); + return EFalse; + } +// Sound::play_sound(SFX_NEXT_ATTRACT_SCREEN); + InitScreen(); + mState = STATE_TYPEWRITER; } + return ETrue; } TBool GAttractProcess::TypewriterState() { @@ -148,9 +148,10 @@ TBool GAttractProcess::TypewriterState() { gGame->SetState(GAME_STATE_GAME); return EFalse; } + if (gControls.WasPressed(BUTTON_START)) { ad->timer = -1; -// me->sleep(1, next); + gGame->SetState(GAME_STATE_GAME); return EFalse; } diff --git a/Evade2/src/AttractState/GAttractState.cpp b/Evade2/src/AttractState/GAttractState.cpp index d892685..7a65e72 100644 --- a/Evade2/src/AttractState/GAttractState.cpp +++ b/Evade2/src/AttractState/GAttractState.cpp @@ -14,19 +14,8 @@ GAttractState::GAttractState() : BGameEngine(gViewPort) { gGameEngine = this; mPlayfield = new GStarfield(); AddProcess(new GAttractProcess()); - GCamera::vx = GCamera::vy = 0; - GCamera::vz = 2; - - gDisplay.SetColor(COLOR_BLACK, 0,0,0); - for (TInt i=1; i<256; i++) { - gDisplay.SetColor(i, 255,255,255); - } - gDisplay.SetColor(COLOR_WHITE, 255, 255, 255); - gDisplay.SetColor(ASSAULT_COLOR, 255, 50, 50); - gDisplay.SetColor(BOMBER_COLOR, 50, 255, 50); - gDisplay.SetColor(SCOUT_COLOR, 255, 50, 255); - gDisplay.SetColor(EBULLET_COLOR, 50, 50, 255); - gDisplay.SetColor(BOMB_COLOR, 255, 255, 50); + gCamera->vx = gCamera->vy = 0; + gCamera->vz = 2; } GAttractState::~GAttractState() noexcept { diff --git a/Evade2/src/GGame.cpp b/Evade2/src/GGame.cpp index 561437c..40e1aea 100644 --- a/Evade2/src/GGame.cpp +++ b/Evade2/src/GGame.cpp @@ -7,6 +7,7 @@ // states #include "./GameState/GGameState.h" #include "./SplashState/GSplashState.h" +#include "./MainMenuState/GMainMenuState.h" #include "./AttractState/GAttractState.h" static TUint32 start; @@ -25,12 +26,10 @@ TBool GGame::mDebug = EFalse; GGame::GGame() { gGame = this; printf("Construct GGame\n"); - mWave = 1; - mKills = 0; - mDifficulty = 1; - gVectorFont = new GVectorFont(); - gGameEngine = ENull; - mState = 0; + gVectorFont = new GVectorFont(); + mDifficulty = 1; + gGameEngine = ENull; + mState = 0; SetState(GAME_STATE_SPLASH); // SetState(GAME_STATE_GAME); } @@ -58,33 +57,57 @@ TInt GGame::GetState() const { } void GGame::SetState(GAMESTATE aNewState) { - delete gGameEngine; + for (TInt i = 0; i < 256; i++) { + gDisplay.SetColor(i, 255, 255, 255); + } + + gDisplay.SetColor(COLOR_BLACK, 0, 0, 0); + gDisplay.SetColor(COLOR_WHITE, 255, 255, 255); + + gDisplay.SetColor(COLOR_STAR, 255,255,255); + + gDisplay.SetColor(ASSAULT_COLOR, 255, 50, 50); + gDisplay.SetColor(BOMBER_COLOR, 50, 255, 50); + gDisplay.SetColor(SCOUT_COLOR, 255, 50, 255); + + gDisplay.SetColor(EBULLET_COLOR, 50, 50, 255); + gDisplay.SetColor(BOMB_COLOR, 255, 255, 50); + mState = aNewState; switch (aNewState) { case GAME_STATE_SPLASH: printf("new State SPLASH\n"); + delete gGameEngine; gGameEngine = new GSplashState(); break; case GAME_STATE_ATTRACT_MODE: printf("new State ATTRACT\n"); + delete gGameEngine; gGameEngine = new GAttractState(); break; case GAME_STATE_GAME: printf("new State GAME\n"); + delete gGameEngine; gGameEngine = new GGameState(); break; case GAME_STATE_MAIN_MENU: printf("new State MAIN MENU\n"); - gGameEngine = new GGameState(); + delete gGameEngine; + gGameEngine = new GMainMenuState(); break; case GAME_STATE_VICTORY: printf("new State VICTORY\n"); + delete gGameEngine; gGameEngine = new GGameState(); break; case GAME_STATE_CREDITS: printf("new State CREDITS\n"); + delete gGameEngine; gGameEngine = new GAttractState(); break; +// case GAME_STATE_NEXT_WAVE: +// printf("new State NEXT WAVE\n"); +// break; } }; @@ -98,13 +121,15 @@ TBool GGame::IsGameState() const { void GGame::Run() { TBool done = EFalse; + while (!done) { Random(); // randomize mShmoo.Set(TUint8(mShmoo.r + 16), TUint8(mShmoo.g + 16), TUint8(mShmoo.b + 16)); gDisplay.displayBitmap->SetColor(COLOR_SHMOO, mShmoo); - GCamera::Move(); + gCamera->Move(); gGameEngine->GameLoop(); gDisplay.Update(); + if (gControls.WasPressed(BUTTONQ)) { done = ETrue; } diff --git a/Evade2/src/GGame.h b/Evade2/src/GGame.h index 97a3d06..26f9abb 100644 --- a/Evade2/src/GGame.h +++ b/Evade2/src/GGame.h @@ -12,14 +12,9 @@ class BFont; enum GAMESTATE { GAME_STATE_SPLASH, GAME_STATE_MAIN_MENU, -// GAME_STATE_LOAD_GAME, -// GAME_STATE_MAIN_OPTIONS, -// GAME_STATE_RESET_OPTIONS, GAME_STATE_ATTRACT_MODE, -// GAME_STATE_RESET_GAME, GAME_STATE_GAME, -// GAME_STATE_RESUME_GAME, -// GAME_STATE_LOAD_SAVEGAME, +// GAME_STATE_NEXT_WAVE, GAME_STATE_VICTORY, GAME_STATE_CREDITS, }; @@ -40,11 +35,7 @@ class GGame : public BApplication { TBool IsGameState() const; -public: - TUint8 mDifficulty; - TInt16 mKills; - TInt16 mWave; - + TUint8 mDifficulty; static TBool mDebug; protected: TInt mState; diff --git a/Evade2/src/Game.h b/Evade2/src/Game.h index 99eaa4b..00c643c 100644 --- a/Evade2/src/Game.h +++ b/Evade2/src/Game.h @@ -10,9 +10,11 @@ //#define SCREEN_DEPTH 8 const TFloat CAMERA_VZ = 2; // 4; +const TFloat CAMERA_WARP_VZ = 4; const TFloat DELTACONTROL = 6; // 11; const TInt8 MAX_BULLETS = 6; const TFloat BULLET_VZ = 8; // 15; +const TFloat ALERT_TOP = 30; // COLLISION_RADIUS = distance from player bullet to enemy required for a hit const TFloat COLLISION_RADIUS = 64; diff --git a/Evade2/src/GameState/GBossProcess.cpp b/Evade2/src/GameState/GBossProcess.cpp new file mode 100644 index 0000000..9c1cc8d --- /dev/null +++ b/Evade2/src/GameState/GBossProcess.cpp @@ -0,0 +1,593 @@ +// +// Created by Michael Schwartz on 11/6/20. +// + +#include "GBossProcess.h" +#include "GNextWaveProcess.h" +#include "GGameState.h" +#include "GPlayerProcess.h" +#include "GEnemyBulletProcess.h" +#include "GCamera.h" + +#include "img/boss_1_img.h" +#include "img/boss_2_img.h" +#include "img/boss_3_img.h" + +static const TFloat z_dist = 256; +static const TFloat frames = 32; + +const TInt TIMER = 240; + +enum { + WARP_STATE, + EXPLODE_STATE, + ACTION_STATE, +}; + +GBossProcess::GBossProcess() : BProcess() { + mSprite = new GVectorSprite(); + mSprite->z = gCamera->z + TIMER * 30 + 512; + mSprite->x = gCamera->x; + mSprite->y = gCamera->y; + mSprite->vx = mSprite->vy = mSprite->vz = 0; + mSprite->mState = 0; + + gGameState->AddSprite(mSprite); + mTimer = TIMER; + mState = WARP_STATE; + gGameState->mState = STATE_BOSS; + + if (gGameState->mWave % 3 == 0) { + mType = 3; + mLines = boss_3_img; + mSprite->SetLines(boss_3_img); + mSprite->x = gCamera->x - 512; + mSprite->vx = 10; + mSprite->vy = Random(-3, 3); + } else if (gGameState->mWave % 2 == 0) { + mType = 2; + mLines = boss_2_img; + mSprite->SetLines(boss_2_img); + InitOrbit(); + } else { + mType = 1; + mLines = boss_1_img; + mSprite->SetLines(boss_1_img); + mSprite->x = gCamera->x + 512; + mSprite->vx = -10; + mSprite->y = gCamera->y; + } + mHitPoints = 20 + (gGame->mDifficulty * mType); +} + +GBossProcess::~GBossProcess() { + mSprite->Remove(); + delete mSprite; +} + +TBool GBossProcess::RunBefore() { + if (gGameState->mState != STATE_PLAY) { + return ETrue; + } + return ETrue; +} + +TBool GBossProcess::Hit() { + if (mSprite->flags & OFLAG_COLLISION) { + mHitPoints--; + mSprite->flags &= ~OFLAG_COLLISION; + return ETrue; + } + return EFalse; +} + +void GBossProcess::InitOrbit() { + TBool left = Random() & 1; + TFloat angle = left ? 0 : (2 * PI); + mSprite->x = cos(angle) * 256; + mSprite->z = gCamera->z + sin(angle) * 256; + mSprite->y = gCamera->y + Random(30, 90); + mSprite->vy = Random(-6 + (gGame->mDifficulty * -1), 6 + (gGame->mDifficulty)); + mSprite->vx = 0; + mSprite->vz = -50 - (gGame->mDifficulty * 2); + mSprite->mState = left ? 0 : 180; +} + +TBool GBossProcess::WarpState() { + if (mTimer-- < 0) { + mState = ACTION_STATE; + gGameState->mState = STATE_BOSS; + gCamera->vz = CAMERA_VZ; + mSprite->vz = CAMERA_VZ; + return ETrue; + } + + gVectorFont->scale = 1.5; + gCamera->vz = 30; + gVectorFont->printf(90, ALERT_TOP, "WARP TO ACE!"); + gGameState->mPlayerProcess->recharge_shield(); + gGameState->mPlayerProcess->recharge_power(); + return ETrue; +} + +TBool GBossProcess::ExplodeState() { + const TInt16 NUM_FRAMES = 58 * 2; + mSprite->flags |= OFLAG_EXPLODE; + mSprite->mState++; + +// EBullet::genocide(); // Kill all enemy bullets + // Done exploding, move forward to the next wave + if (mSprite->mState > NUM_FRAMES) { + mState = STATE_NEXT_WAVE; + gCamera->vz = CAMERA_VZ; + + gGameState->AddProcess(new GNextWaveProcess()); + return EFalse; + } else { + return ETrue; + } +} + +void GBossProcess::EngagePlayerRandomXY() { + mSprite->z = gCamera->z + z_dist - 150; + + // Debugging stuff + // Font::scale = .7 * 256; + // Font::printf(5, 5, "%f", mSprite->x - gCamera->x); + // Font::printf(5, 15, "%f", mSprite->y - gCamera->y); + + if (mSprite->mState == 1) { + mSprite->mTheta += 5. + gGame->mDifficulty; + } else { + mSprite->mTheta -= 5. + gGame->mDifficulty; + } + // Debug + // mSprite->x = gCamera->x; + // mSprite->y = gCamera->y; + + if (--mSprite->mTimer > 0) { + return; + } + + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + mSprite->mTimer = gGameState->mWave > 20 ? 10 : (40 - gGame->mDifficulty); + // Keep within bounds of the screen + if (mSprite->x - gCamera->x < -300) { + mSprite->vx = Random(3, 10 + gGame->mDifficulty); + } else if (mSprite->x - gCamera->x > 300) { + mSprite->vx = Random(-3, -10 + gGame->mDifficulty * -1); + } else { + mSprite->vx = Random(-10 + (gGame->mDifficulty * -1), 10 + gGame->mDifficulty); + } + + if (mSprite->y - gCamera->y < -300) { + mSprite->vy = Random(3, 10 + gGame->mDifficulty); + } else if (mSprite->y - gCamera->y > 300) { + mSprite->vy = Random(-3, -10 + gGame->mDifficulty * -1); + } else { + mSprite->vy = Random(-10 + (gGame->mDifficulty * -1), 10 + gGame->mDifficulty); + } +} + +void GBossProcess::RandomizeFlee() { + mSprite->y = gCamera->y + Random(-150, 150); + mSprite->vy = Random(-7, 7); + mSprite->vx = Random(-7, 7); + mSprite->z = gCamera->z - 50; + mSprite->vz = gCamera->vz + TFloat(Random(1, 7) * gGame->mDifficulty); + mSprite->mTheta = Random(-180, 180); +} + +void GBossProcess::EngagePlayerFlee() { + if (mSprite->flags & ORBIT_LEFT) { + mSprite->mState -= gGame->mDifficulty; + if (mSprite->mState < 0) { + mSprite->mState = 0; + RandomizeFlee(); + mSprite->flags &= ~ORBIT_LEFT; + } + } else { + mSprite->mState += gGame->mDifficulty; + if (mSprite->mState > 90) { + mSprite->mState = 90; + RandomizeFlee(); + mSprite->flags |= ORBIT_LEFT; + } + } + + if (--mSprite->mTimer > 0) { + return; + } + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + + mSprite->mTimer = gGameState->mWave > 20 ? 20 : (50 - gGame->mDifficulty); + // mSprite->x = gCamera->x; + // mSprite->y = gCamera->y; + mSprite->vx += Random(-7, 7); + mSprite->vy += Random(-7, 7); +} + +void GBossProcess::EngagePlayerOrbit() { + if (mSprite->flags & ORBIT_LEFT) { + mSprite->mState -= gGame->mDifficulty; + if (mSprite->mState < 0) { + mSprite->y = gCamera->y + Random(-150, 150); + // mSprite->vy = random(-7,7); + + mSprite->mState = 0; + mSprite->flags &= ~ORBIT_LEFT; + } else { + mSprite->mTheta -= 12; + } + } else { + mSprite->mState += gGame->mDifficulty; + if (mSprite->mState > 180) { + mSprite->y = gCamera->y + Random(-150, 150); + mSprite->mState = 180; + mSprite->flags |= ORBIT_LEFT; + } else { + mSprite->mTheta += 12; + } + } + + TFloat rad = RADIANS(mSprite->mState); + mSprite->x = cos(rad) * 512; + mSprite->z = gCamera->z + sin(rad) * 512; + + if (--mSprite->mTimer <= 0) { + mSprite->mTimer = gGameState->mWave > 20 ? 20 : (50 - gGame->mDifficulty); + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + } +} + +TBool GBossProcess::ActionState() { + if (Hit()) { + if (mHitPoints <= 2) { + mSprite->flags &= OFLAG_EXPLODE; + mSprite->mState = 0; + mSprite->vz = gCamera->vz - 3; + +// Sound::play_sound(SFX_BOSS_EXPLODE); + mState = EXPLODE_STATE; + return ETrue; + } + + mSprite->SetLines(ENull); + + if (mType == 1) { + // mSprite->y = Random(-5, 5); + mSprite->mState = (mSprite->mState == 1) ? 0 : 1; + } + // else if (Boss::boss_type == 2) { + // init_orbit(o, Random() & 1); + // } + // else { + // randomize_flee(o); + // } + } else { + mSprite->SetLines(mLines); + + if (mType == 1) { + EngagePlayerRandomXY(); + } else if (mType == 2) { + EngagePlayerOrbit(); + } else { + EngagePlayerFlee(); + } + } + + return ETrue; +} + + +TBool GBossProcess::RunAfter() { + switch (mState) { + case WARP_STATE: + return WarpState(); + case EXPLODE_STATE: + return ExplodeState(); + } + return ETrue; + +// if (mTimer-- < 0) { +// gGameState->mState = STATE_BOSS; +// gCamera->vz = CAMERA_VZ; +// mSprite->vz = CAMERA_VZ; +// } else { +// } +// return ETrue; +} + +#if 0 +TUint16 Boss::hit_points = 0; +UTInt8 Boss::boss_type; + +static BOOL hit(Object *o) { + if (mSprite->flags & OFLAG_COLLISION) { + Boss::hit_points--; + mSprite->flags &= ~OFLAG_COLLISION; + return TRUE; + } + return FALSE; +} + +const TInt8 *getBossLines() { + switch (Boss::boss_type) { + case 3: + return boss_3_img; + break; + case 2: + return boss_2_img; + break; + default: + return boss_1_img; + } +} + +/** +Ideas: +instead of randomizing vx, vy, you can set y to sin(theta)*64 or something like +that (edited) [18:43] and change theta over time [18:43] it'll make it a +sinusoidal pattern +*/ + +static void engage_player_random_xy(Object *o) { + mSprite->z = gCamera->z + z_dist - 150; + + // Debugging stuff + // Font::scale = .7 * 256; + // Font::printf(5, 5, "%f", mSprite->x - gCamera->x); + // Font::printf(5, 15, "%f", mSprite->y - gCamera->y); + + if (mSprite->mState == 1) { + mSprite->theta += 5 + gGame->mDifficulty; + } else { + mSprite->theta -= 5 + gGame->mDifficulty; + } + // Debug + // mSprite->x = gCamera->x; + // mSprite->y = gCamera->y; + + if (--mSprite->timer > 0) { + return; + } + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + mSprite->timer = gGame->mWave > 20 ? 10 : (40 - gGame->mDifficulty); + // Keep within bounds of the screen + if (mSprite->x - gCamera->x < -300) { + mSprite->vx = random(3, 10 + gGame->mDifficulty); + } else if (mSprite->x - gCamera->x > 300) { + mSprite->vx = random(-3, -10 + gGame->mDifficulty * -1); + } else { + mSprite->vx = random(-10 + (gGame->mDifficulty * -1), 10 + gGame->mDifficulty); + } + + if (mSprite->y - gCamera->y < -300) { + mSprite->vy = random(3, 10 + gGame->mDifficulty); + } else if (mSprite->y - gCamera->y > 300) { + mSprite->vy = random(-3, -10 + gGame->mDifficulty * -1); + } else { + mSprite->vy = random(-10 + (gGame->mDifficulty * -1), 10 + gGame->mDifficulty); + } +} + +static void randomize_flee(Object *o) { + mSprite->y = gCamera->y + random(-150, 150); + mSprite->vy = random(-7, 7); + mSprite->vx = random(-7, 7); + mSprite->z = gCamera->z - 50; + mSprite->vz = gCamera->vz + (random(1, 7) * gGame->mDifficulty); + mSprite->theta = random(-180, 180); +} + +static void engage_player_flee(Object *o) { + + if (mSprite->flags & ORBIT_LEFT) { + mSprite->mState -= gGame->mDifficulty; + if (mSprite->mState < 0) { + mSprite->mState = 0; + randomize_flee(o); + mSprite->flags &= ~ORBIT_LEFT; + } + } else { + mSprite->mState += gGame->mDifficulty; + if (mSprite->mState > 90) { + mSprite->mState = 90; + randomize_flee(o); + mSprite->flags |= ORBIT_LEFT; + } + } + + if (--mSprite->timer > 0) { + return; + } + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + + mSprite->timer = gGame->mWave > 20 ? 20 : (50 - gGame->mDifficulty); + // mSprite->x = gCamera->x; + // mSprite->y = gCamera->y; + mSprite->vx += random(-7, 7); + mSprite->vy += random(-7, 7); +} + +// Copy of init_assault +static void init_orbit(Object *o, BOOL left) { + TFloat angle = left ? 0 : (2 * PI); + mSprite->x = cos(angle) * 256; + mSprite->z = gCamera->z + sin(angle) * 256; + mSprite->y = gCamera->y + random(30, 90); + mSprite->vy = random(-6 + (gGame->mDifficulty * -1), 6 + (gGame->mDifficulty)); + mSprite->vx = 0; + mSprite->vz = -50 - (gGame->mDifficulty * 2); + mSprite->mState = left ? 0 : 180; +} + +static void engage_player_orbit(Object *o) { + + if (mSprite->flags & ORBIT_LEFT) { + mSprite->mState -= gGame->mDifficulty; + if (mSprite->mState < 0) { + mSprite->y = gCamera->y + random(-150, 150); + // mSprite->vy = random(-7,7); + + mSprite->mState = 0; + mSprite->flags &= ~ORBIT_LEFT; + } else { + mSprite->theta -= 12; + } + } else { + mSprite->mState += gGame->mDifficulty; + if (mSprite->mState > 180) { + mSprite->y = gCamera->y + random(-150, 150); + mSprite->mState = 180; + mSprite->flags |= ORBIT_LEFT; + } else { + mSprite->theta += 12; + } + } + + TFloat rad = RADIANS(mSprite->mState); + mSprite->x = cos(rad) * 512; + mSprite->z = gCamera->z + sin(rad) * 512; + + if (--mSprite->timer <= 0) { + mSprite->timer = gGame->mWave > 20 ? 20 : (50 - gGame->mDifficulty); + gGameState->AddProcess(new GEnemyBulletProcess(mSprite, EBULLET_BOMB)); + } +} + +/** + * Boss is exploding state. + */ +void Boss::explode(Process *me, Object *o) { + const WORD NUM_FRAMES = 58; + mSprite->flags |= OFLAG_EXPLODE; + mSprite->mState++; + EBullet::genocide(); // Kill all enemy bullets + // Done exploding, move forward to the next wave + if (mSprite->mState > NUM_FRAMES) { + game_mode = MODE_NEXT_WAVE; + Game::kills = 65; + gCamera->vz = CAMERA_VZ; + Sound::play_score(NEXT_WAVE_SONG); + + ProcessManager::birth(Game::next_wave); + me->suicide(); + } else { + me->sleep(1, explode); + } +} + +void Boss::action(Process *me, Object *o) { + if (hit(o)) { + if (Boss::hit_points <= 2) { + + mSprite->flags &= OFLAG_EXPLODE; + mSprite->mState = 0; + mSprite->vz = gCamera->vz - 3; + + Sound::play_sound(SFX_BOSS_EXPLODE); + me->sleep(1, explode); + return; + } + + mSprite->lines = NULL; + + if (Boss::boss_type == 1) { + // mSprite->y = random(-5, 5); + mSprite->mState = (mSprite->mState == 1) ? 0 : 1; + } + // else if (Boss::boss_type == 2) { + // init_orbit(o, random() & 1); + // } + // else { + // randomize_flee(o); + // } + } else { + mSprite->lines = getBossLines(); + + if (Boss::boss_type == 1) { + engage_player_random_xy(o); + } else if (Boss::boss_type == 2) { + engage_player_orbit(o); + } else { + engage_player_flee(o); + } + } + + me->sleep(1); +} + +void Boss::start_action(Process *me, Object *o) { + + if (Boss::boss_type == 2) { + if (--mSprite->timer > 0) { + game_mode = MODE_GAME; + me->sleep(1, action); + } else { + me->sleep(1); + } + } else { + mSprite->y = gCamera->y; + mSprite->z = gCamera->z + z_dist; + if (Boss::boss_type == 1) { + mSprite->z = gCamera->z + z_dist - 150; + if (mSprite->x <= gCamera->x) { + game_mode = MODE_GAME; + me->sleep(1, action); + } else { + me->sleep(1); + } + } else { + if (mSprite->x > gCamera->x) { + game_mode = MODE_GAME; + me->sleep(1, action); + } else { + me->sleep(1); + } + } + } +} + +void Boss::entry(Process *me, Object *o) { + // production + game_mode = MODE_NEXT_WAVE; + Game::kills = 0; + gCamera->vz = -10; + + mSprite->set_type(OTYPE_ENEMY); + mSprite->z = gCamera->z + z_dist - 150; + + mSprite->mState = 0; + mSprite->vz = gCamera->vz; + mSprite->color = BOSS_COLOR; + + if (gGame->mWave % 3 == 0) { + Boss::boss_type = 3; + mSprite->x = gCamera->x - 512; + mSprite->vx = +10; + mSprite->vy = random(-3, 3); + Sound::play_score(STAGE_3_BOSS_SONG); + } else if (gGame->mWave % 2 == 0) { + Boss::boss_type = 2; + init_orbit(o, random() & 1); + Sound::play_score(STAGE_2_BOSS_SONG); + } else { + Boss::boss_type = 1; + mSprite->x = gCamera->x + 512; + mSprite->vx = -10; + mSprite->y = gCamera->y; + Sound::play_score(STAGE_1_BOSS_SONG); + } + + mSprite->lines = getBossLines(); + + // PRODUCTION + Boss::hit_points = 20 + (gGame->mDifficulty * Boss::boss_type); + // DEV/TEST + // Boss::hit_points = 1; + me->sleep(1, Boss::start_action); +} + + +#endif \ No newline at end of file diff --git a/Evade2/src/GameState/GBossProcess.h b/Evade2/src/GameState/GBossProcess.h new file mode 100644 index 0000000..27c5361 --- /dev/null +++ b/Evade2/src/GameState/GBossProcess.h @@ -0,0 +1,43 @@ +// +// Created by Michael Schwartz on 11/6/20. +// + +#ifndef EVADE2_GBOSSPROCESS_H +#define EVADE2_GBOSSPROCESS_H + +#include "Game.h" +#include "GVectorSprite.h" + +class GBossProcess : public BProcess { +public: + GBossProcess(); + + ~GBossProcess() OVERRIDE; + +public: + TBool RunBefore() OVERRIDE; + + TBool RunAfter() OVERRIDE; + +protected: + void InitOrbit(); + TBool Hit(); + void EngagePlayerRandomXY(); + void EngagePlayerOrbit(); + void RandomizeFlee(); + void EngagePlayerFlee(); +protected: + TBool WarpState(); + TBool ExplodeState(); + TBool ActionState(); + +protected: + GVectorSprite *mSprite; + const TInt8 *mLines; + TInt mTimer; + TInt mState; + TInt mType; + TInt mHitPoints; +}; + +#endif //EVADE2_GBOSSPROCESS_H diff --git a/Evade2/src/GameState/GEnemyBulletProcess.cpp b/Evade2/src/GameState/GEnemyBulletProcess.cpp index b44bc5d..cf90c53 100644 --- a/Evade2/src/GameState/GEnemyBulletProcess.cpp +++ b/Evade2/src/GameState/GEnemyBulletProcess.cpp @@ -12,15 +12,15 @@ GEnemyBulletProcess::GEnemyBulletProcess(GVectorSprite *enemy, TInt8 type) { const TFloat FRAMES = 90 / gGame->mDifficulty; mSprite = new GVectorSprite(STYPE_EBULLET); - mSprite->SetLines( (type == EBULLET_BOMB) ? ebomb_img : ebullet_img); + mSprite->SetLines((type == EBULLET_BOMB) ? ebomb_img : ebullet_img); mSprite->mColor = (type == EBULLET_BOMB) ? BOMB_COLOR : EBULLET_COLOR; mSprite->mTimer = 256; // timeout mSprite->x = enemy->x - 8; mSprite->y = enemy->y - 8; mSprite->z = enemy->z; - mSprite->vx = (GCamera::x - mSprite->x) / FRAMES; - mSprite->vy = (GCamera::y - mSprite->y) / FRAMES; - mSprite->vz = GCamera::vz - (mSprite->z - GCamera::z) / FRAMES; + mSprite->vx = (gCamera->x - mSprite->x) / FRAMES; + mSprite->vy = (gCamera->y - mSprite->y) / FRAMES; + mSprite->vz = gCamera->vz - (mSprite->z - gCamera->z) / FRAMES; // printf("Bullet vx,vy,vz = %f,%f,%f mState(%d)\n", mSprite->vx, mSprite->vy, mSprite->vz, mSprite->mTimer); gGameEngine->AddSprite(mSprite); } @@ -32,14 +32,18 @@ GEnemyBulletProcess::~GEnemyBulletProcess() noexcept { } TBool GEnemyBulletProcess::RunBefore() { + if (gGameState->mState != STATE_PLAY) { + return EFalse; + } mSprite->mTheta += (mSprite->GetLines() == ebomb_img) ? mSprite->x : 40; return ETrue; } TBool GEnemyBulletProcess::RunAfter() { - if (GCamera::CollidesWith(mSprite)) { + if (gCamera->CollidesWith(mSprite)) { if (gGame->IsGameState()) { gGameState->mPlayerProcess->Hit(10); + return EFalse; } } diff --git a/Evade2/src/GameState/GEnemyProcess.cpp b/Evade2/src/GameState/GEnemyProcess.cpp index 11e90ef..d326e4d 100644 --- a/Evade2/src/GameState/GEnemyProcess.cpp +++ b/Evade2/src/GameState/GEnemyProcess.cpp @@ -16,11 +16,11 @@ const TInt8 *GEnemyProcess::Graphic(TInt aType) { switch (aType) { case ENEMY_ASSAULT: - return (const TInt8 *)&enemy_assault_1_img; + return (const TInt8 *) &enemy_assault_1_img; case ENEMY_BOMBER: - return (const TInt8 *)&enemy_heavy_bomber_1_img; + return (const TInt8 *) &enemy_heavy_bomber_1_img; case ENEMY_SCOUT: - return (const TInt8 *)&enemy_scout_1_img; + return (const TInt8 *) &enemy_scout_1_img; default: Panic("Invalid enemy type: %d\n", aType); } @@ -42,7 +42,7 @@ GEnemyProcess::~GEnemyProcess() noexcept { TBool GEnemyProcess::death() { if (mSprite->flags & OFLAG_COLLISION) { - gGame->mKills++; + gGameState->mKills++; mSprite->flags &= OFLAG_EXPLODE; mSprite->mState = 0; return ETrue; @@ -51,9 +51,12 @@ TBool GEnemyProcess::death() { } void GEnemyProcess::fire() { + if (gGameState->mState != STATE_PLAY) { + return; + } mSprite->mTimer--; if (mSprite->mTimer <= 0) { - if (GCamera::vx || GCamera::vy) { + if (gCamera->vx || gCamera->vy) { mSprite->mTimer = 1; return; } @@ -85,7 +88,7 @@ void GEnemyProcess::bank(TInt16 delta) { } void GEnemyProcess::respawn() { - mSprite->mTimer = Random(gGame->mWave > 6 ? 30 : 30, 60) + 30; + mSprite->mTimer = Random(gGameState->mWave > 6 ? 30 : 30, 60) + 30; // printf("RESPAWN %d\n", mSprite->mTimer); mState = ESTATE_WAITINIT; @@ -94,8 +97,8 @@ void GEnemyProcess::respawn() { void GEnemyProcess::init_assault(TBool left) { TFloat angle = left ? 0 : (2 * PI); mSprite->x = cos(angle) * 256; - mSprite->z = GCamera::z + sin(angle) * 256; - mSprite->y = GCamera::y; // + 64 - random(0, 128); + mSprite->z = gCamera->z + sin(angle) * 256; + mSprite->y = gCamera->y; // + 64 - random(0, 128); mSprite->vx = mSprite->vy = mSprite->vz = 0; mSprite->mState = 0; mSprite->mColor = ASSAULT_COLOR; @@ -105,9 +108,9 @@ void GEnemyProcess::init_assault(TBool left) { * Initialize object for scout enemy */ void GEnemyProcess::init_scout() { - mSprite->x = GCamera::x + Random(-256, 256); - mSprite->y = GCamera::y + Random(-256, 256); - mSprite->z = GCamera::z + 1024; + mSprite->x = gCamera->x + Random(-256, 256); + mSprite->y = gCamera->y + Random(-256, 256); + mSprite->z = gCamera->z + 1024; mSprite->vz = CAMERA_VZ - 3; // 12; mSprite->vx = mSprite->vy = 0; mSprite->mTheta = Random(-50, 50); @@ -118,10 +121,10 @@ void GEnemyProcess::init_scout() { * Initialize object for bomber enemy */ void GEnemyProcess::init_bomber() { - mSprite->x = GCamera::x + 128 - Random(0, 127); - mSprite->y = GCamera::y + 128 - Random(0, 127); - mSprite->z = GCamera::z - 30; - mSprite->vz = CAMERA_VZ + 1 + gGame->mWave; + mSprite->x = gCamera->x + 128 - Random(0, 127); + mSprite->y = gCamera->y + 128 - Random(0, 127); + mSprite->z = gCamera->z - 30; + mSprite->vz = CAMERA_VZ + 1 + gGameState->mWave; mSprite->vx = mSprite->vy = 0; mSprite->mColor = BOMBER_COLOR; } @@ -133,7 +136,7 @@ void GEnemyProcess::init() { mSprite->mTheta = 0; // One enemy type enters per wave - switch (Random(0, (gGame->mWave > 3) ? 3 : gGame->mWave)) { + switch (Random(0, (gGameState->mWave > 3) ? 3 : gGameState->mWave)) { case 0: mSprite->SetLines((const TInt8 *) &enemy_scout_1_img); init_scout(); @@ -165,7 +168,7 @@ TBool GEnemyProcess::StateSeek() { // bank(o); fire(); o->mTheta += 8; - if (o->z - GCamera::z < Random(256, 512)) { + if (o->z - gCamera->z < Random(256, 512)) { o->mState = -1; mState = ESTATE_RUNAWAY; return ETrue; @@ -176,7 +179,7 @@ TBool GEnemyProcess::StateSeek() { TBool GEnemyProcess::StateEvade() { GVectorSprite *o = mSprite; - if (o->z - GCamera::z > 512) { + if (o->z - gCamera->z > 512) { o->mState = 1; mState = ESTATE_RUNAWAY; return ETrue; @@ -217,11 +220,11 @@ TBool GEnemyProcess::StateOrbit() { } TFloat rad = RADIANS(o->mState); - o->vy = (GCamera::y > o->y) ? -2 : 2; - o->y = GCamera::y; + o->vy = (gCamera->y > o->y) ? -2 : 2; + o->y = gCamera->y; o->x = cos(rad) * 256; if (gGame->GetState() == GAME_STATE_GAME) { - o->z = GCamera::z + sin(rad) * 256; + o->z = gCamera->z + sin(rad) * 256; } return ETrue; @@ -248,7 +251,7 @@ TBool GEnemyProcess::StateRunAway() { } o->vx += o->vx > 0 ? .1 : -.1; o->vy += o->vy > 0 ? .1 : -.1; - if (o->BehindCamera() || (o->z - GCamera::z) > 1024) { + if (o->BehindCamera() || (o->z - gCamera->z) > 1024) { respawn(); return ETrue; } @@ -265,12 +268,18 @@ TBool GEnemyProcess::StateExplode() { mSprite->flags |= OFLAG_EXPLODE; mSprite->mState++; if (mSprite->BehindCamera() || mSprite->mState > 50) { + if (gGameState->mState != STATE_PLAY) { + return EFalse; + } respawn(); } return ETrue; } TBool GEnemyProcess::RunBefore() { + if (gGameState->mState != STATE_PLAY) { + return EFalse; + } switch (mState) { case ESTATE_SEEK: return StateSeek(); diff --git a/Evade2/src/GameState/GGameState.cpp b/Evade2/src/GameState/GGameState.cpp index 5ad85ad..4cb73ce 100644 --- a/Evade2/src/GameState/GGameState.cpp +++ b/Evade2/src/GameState/GGameState.cpp @@ -6,35 +6,36 @@ #include "GStarfield.h" #include "GPlayerProcess.h" #include "GEnemyProcess.h" +#include "GNextWaveProcess.h" +#include "GBossProcess.h" GGameState *gGameState; GGameState::GGameState() : BGameEngine(gViewPort) { gGameEngine = this; - gGameState = this; - mPlayfield = new GStarfield(); + gGameState = this; + mState = STATE_PLAY; + mWave = 1; + mKills = 0; + mPlayfield = new GStarfield(); // set colors - gDisplay.SetColor(COLOR_BLACK, 0,0,0); - for (TInt i=1; i<256; i++) { - gDisplay.SetColor(i, 255,255,255); - } - gDisplay.SetColor(COLOR_WHITE, 255, 255, 255); - gDisplay.SetColor(ASSAULT_COLOR, 255, 50, 50); - gDisplay.SetColor(BOMBER_COLOR, 50, 255, 50); - gDisplay.SetColor(SCOUT_COLOR, 255, 50, 255); - gDisplay.SetColor(EBULLET_COLOR, 50, 50, 255); - gDisplay.SetColor(BOMB_COLOR, 255, 255, 50); AddProcess(new GEnemyProcess()); AddProcess(new GEnemyProcess()); AddProcess(new GEnemyProcess()); mPlayerProcess = new GPlayerProcess(); AddProcess(mPlayerProcess); - gDisplay.SetColor(COLOR_WHITE, 255,255,255); - gDisplay.SetColor(COLOR_STAR, 255,255,255); } GGameState::~GGameState() { // delete mPlayfield; } +void GGameState::PostRender() { + if (mState != STATE_PLAY) { + return; + } + if (mKills > (10 + mWave) * gGame->mDifficulty) { + AddProcess(new GBossProcess()); + } +} diff --git a/Evade2/src/GameState/GGameState.h b/Evade2/src/GameState/GGameState.h index c478509..320e2ad 100644 --- a/Evade2/src/GameState/GGameState.h +++ b/Evade2/src/GameState/GGameState.h @@ -7,17 +7,29 @@ #include +enum { + STATE_PLAY, + STATE_BOSS, + STATE_NEXT_WAVE, +}; + class GPlayerProcess; class GGameState : public BGameEngine { public: GGameState(); - ~GGameState(); + ~GGameState() OVERRIDE; + +public: + void PostRender() OVERRIDE; public: -// void GameLoop() OVERRIDE; GPlayerProcess *mPlayerProcess; + TInt32 mState; + TInt16 mKills; + TInt16 mWave; + }; extern GGameState *gGameState; diff --git a/Evade2/src/GameState/GNextWaveProcess.cpp b/Evade2/src/GameState/GNextWaveProcess.cpp new file mode 100644 index 0000000..7f65cb4 --- /dev/null +++ b/Evade2/src/GameState/GNextWaveProcess.cpp @@ -0,0 +1,36 @@ +// +// Created by Michael Schwartz on 11/6/20. +// + +#include "GNextWaveProcess.h" +#include "GPlayerProcess.h" +#include "GGameState.h" +#include "GCamera.h" + +GNextWaveProcess::GNextWaveProcess() : BProcess() { + mTimer = 240; + gCamera->vz = 30; + gGameState->mState = STATE_NEXT_WAVE; +} + +GNextWaveProcess::~GNextWaveProcess() noexcept { + gGameState->mState = STATE_PLAY; + gGameState->mKills = 0; + gGameState->mWave++; + if (gGameState->mWave % 4 == 0) { + gGame->mDifficulty++; + } + gCamera->vz = CAMERA_VZ; +} + +TBool GNextWaveProcess::RunBefore() { + return ETrue; +} + +TBool GNextWaveProcess::RunAfter() { + gVectorFont->scale = 1.5; + gVectorFont->printf(85, ALERT_TOP, "START WAVE %d", gGameState->mWave + 1); + gGameState->mPlayerProcess->recharge_shield(); + gGameState->mPlayerProcess->recharge_power(); + return --mTimer > 0; +} \ No newline at end of file diff --git a/Evade2/src/GameState/GNextWaveProcess.h b/Evade2/src/GameState/GNextWaveProcess.h new file mode 100644 index 0000000..185a6a3 --- /dev/null +++ b/Evade2/src/GameState/GNextWaveProcess.h @@ -0,0 +1,25 @@ +// +// Created by Michael Schwartz on 11/6/20. +// + +#ifndef EVADE2_GNEXTWAVEPROCESS_H +#define EVADE2_GNEXTWAVEPROCESS_H + +#include "Game.h" + +class GNextWaveProcess : public BProcess { +public: + GNextWaveProcess(); + + ~GNextWaveProcess(); + +public: + TBool RunBefore(); + + TBool RunAfter(); +protected: + TInt mTimer; +}; + + +#endif //EVADE2_GNEXTWAVEPROCESS_H diff --git a/Evade2/src/GameState/GPlayerBulletProcess.cpp b/Evade2/src/GameState/GPlayerBulletProcess.cpp index 9a9ca26..96dc6ad 100644 --- a/Evade2/src/GameState/GPlayerBulletProcess.cpp +++ b/Evade2/src/GameState/GPlayerBulletProcess.cpp @@ -12,19 +12,19 @@ GPlayerBulletProcess::GPlayerBulletProcess(TFloat deltaX, TFloat deltaY, TBool alt) { mSprite = new GVectorSprite(STYPE_PBULLET); if (alt) { - mSprite->x = GCamera::x + 28; - mSprite->y = GCamera::y - 28; - mSprite->z = GCamera::z; + mSprite->x = gCamera->x + 28; + mSprite->y = gCamera->y - 28; + mSprite->z = gCamera->z; mSprite->mState = 20; } else { - mSprite->x = GCamera::x - 28; - mSprite->y = GCamera::y - 28; - mSprite->z = GCamera::z; + mSprite->x = gCamera->x - 28; + mSprite->y = gCamera->y - 28; + mSprite->z = gCamera->z; mSprite->mState = -20; } mSprite->vx = deltaX; mSprite->vy = deltaY; - mSprite->vz = GCamera::vz + BULLET_VZ; + mSprite->vz = gCamera->vz + BULLET_VZ; mSprite->SetLines(bullet_img); gGameEngine->AddSprite(mSprite); } @@ -42,7 +42,7 @@ TBool GPlayerBulletProcess::RunBefore() { } TBool GPlayerBulletProcess::RunAfter() { - if (mSprite->z - GCamera::z > 512) { + if (mSprite->z - gCamera->z > 512) { return EFalse; } BSpriteList &l = gGameState->mSpriteList; diff --git a/Evade2/src/GameState/GPlayerProcess.cpp b/Evade2/src/GameState/GPlayerProcess.cpp index 4c57505..25e6c48 100644 --- a/Evade2/src/GameState/GPlayerProcess.cpp +++ b/Evade2/src/GameState/GPlayerProcess.cpp @@ -26,7 +26,7 @@ const TUint8 crosshair_right_4x8[] = { GPlayerProcess::GPlayerProcess() { color = COLOR_WHITE; - GCamera::vz = CAMERA_VZ; + gCamera->vz = CAMERA_VZ; power = MAX_POWER; shield = MAX_LIFE; mNumBullets = 0; @@ -124,7 +124,7 @@ void GPlayerProcess::recharge_power() { TBool GPlayerProcess::RunBefore() { if (gGame->GetState() != GAME_STATE_GAME) { // if (game_mode != MODE_GAME) { - GCamera::vx = GCamera::vy = 0; + gCamera->vx = gCamera->vy = 0; return ETrue; } @@ -149,16 +149,16 @@ TBool GPlayerProcess::RunBefore() { if (gControls.IsPressed(CONTROL_BURST)) { if (power > 0) { - GCamera::vz = CAMERA_VZ * 2; + gCamera->vz = CAMERA_WARP_VZ; power--; if (power < 0) { power = 0; } } else { - GCamera::vz = CAMERA_VZ; + gCamera->vz = CAMERA_VZ; } } else { - GCamera::vz = CAMERA_VZ; + gCamera->vz = CAMERA_VZ; power++; if (power > MAX_POWER) { power = MAX_POWER; @@ -166,19 +166,19 @@ TBool GPlayerProcess::RunBefore() { } if (gControls.IsPressed(CONTROL_JOYRIGHT)) { - GCamera::vx = -DELTACONTROL; + gCamera->vx = -DELTACONTROL; } else if (gControls.IsPressed(CONTROL_JOYLEFT)) { - GCamera::vx = DELTACONTROL; + gCamera->vx = DELTACONTROL; } else { - GCamera::vx = 0; + gCamera->vx = 0; } if (gControls.IsPressed(CONTROL_JOYDOWN)) { - GCamera::vy = DELTACONTROL; + gCamera->vy = DELTACONTROL; } else if (gControls.IsPressed(CONTROL_JOYUP)) { - GCamera::vy = -DELTACONTROL; + gCamera->vy = -DELTACONTROL; } else { - GCamera::vy = 0; + gCamera->vy = 0; } return ETrue; } diff --git a/Evade2/src/MainMenuState/GMainMenu.cpp b/Evade2/src/MainMenuState/GMainMenu.cpp deleted file mode 100644 index fe91034..0000000 --- a/Evade2/src/MainMenuState/GMainMenu.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// -// Created by Michael Schwartz on 11/4/20. -// - -#include "GMainMenu.h" -#include "GStarfield.h" - -GMainMenu::GMainMenu() : BGameEngine(gViewPort) { - mPlayfield = new GStarfield(); -} - -GMainMenu::~GMainMenu() noexcept {} \ No newline at end of file diff --git a/Evade2/src/MainMenuState/GMainMenu.h b/Evade2/src/MainMenuState/GMainMenu.h deleted file mode 100644 index 5c52ac5..0000000 --- a/Evade2/src/MainMenuState/GMainMenu.h +++ /dev/null @@ -1,18 +0,0 @@ -// -// Created by Michael Schwartz on 11/4/20. -// - -#ifndef EVADE2_GMAINMENU_H -#define EVADE2_GMAINMENU_H - -#include "Game.h" - -class GMainMenu : public BGameEngine { -public: - GMainMenu(); - - ~GMainMenu() OVERRIDE; -}; - - -#endif //EVADE2_GMAINMENU_H diff --git a/Evade2/src/MainMenuState/GMainMenuProcess.cpp b/Evade2/src/MainMenuState/GMainMenuProcess.cpp index 18c15df..3a70c3b 100644 --- a/Evade2/src/MainMenuState/GMainMenuProcess.cpp +++ b/Evade2/src/MainMenuState/GMainMenuProcess.cpp @@ -3,3 +3,47 @@ // #include "GMainMenuProcess.h" +#include "GCamera.h" + +GMainMenuProcess::GMainMenuProcess() : BProcess() { +// gCamera->vx = 0; +// gCamera->vy = 0; +// gCamera->vz = CAMERA_VZ; + mTimer = 280 * 2; + mTheta = 90; +} + +GMainMenuProcess::~GMainMenuProcess() noexcept {} + +TBool GMainMenuProcess::RunAfter() { + gVectorFont->scale = 4; + gVectorFont->color = COLOR_SHMOO; + gVectorFont->print_string_rotatedx(70, 90, mTheta, "EVADE2"); + gVectorFont->color = COLOR_WHITE; + + mTimer--; + gVectorFont->scale = 1; + if (mTimer & 32) { + gVectorFont->scale = 2; + gVectorFont->printf(130, 155, "START"); + } + + mTheta += 5; + if (mTheta > 90 + 360 * 2) { + mTheta = 90 + 360 * 2; + } + + return ETrue; +} + +TBool GMainMenuProcess::RunBefore() { + if (gControls.WasPressed(BUTTON_START)) { + gGame->SetState(GAME_STATE_GAME); + return EFalse; + } + if (mTimer < 0 || gControls.WasPressed(BUTTONA|BUTTONB)) { + gGame->SetState(GAME_STATE_ATTRACT_MODE); + return EFalse; + } + return ETrue; +} diff --git a/Evade2/src/MainMenuState/GMainMenuProcess.h b/Evade2/src/MainMenuState/GMainMenuProcess.h index 56ed2d0..935f130 100644 --- a/Evade2/src/MainMenuState/GMainMenuProcess.h +++ b/Evade2/src/MainMenuState/GMainMenuProcess.h @@ -18,6 +18,9 @@ class GMainMenuProcess : public BProcess { TBool RunAfter(); +protected: + TFloat mTheta; + TInt32 mTimer; }; diff --git a/Evade2/src/MainMenuState/GMainMenuState.cpp b/Evade2/src/MainMenuState/GMainMenuState.cpp new file mode 100644 index 0000000..fc98a9d --- /dev/null +++ b/Evade2/src/MainMenuState/GMainMenuState.cpp @@ -0,0 +1,18 @@ +// +// Created by Michael Schwartz on 11/4/20. +// + +#include "GMainMenuState.h" +#include "GMainMenuProcess.h" +#include "GStarfield.h" +#include "GCamera.h" + +GMainMenuState::GMainMenuState() : BGameEngine(gViewPort) { +// gGameEngine = this; + mPlayfield = new GStarfield(); + gCamera->vx = gCamera->vy = 0; + gCamera->vz = CAMERA_VZ; + AddProcess(new GMainMenuProcess()); +} + +GMainMenuState::~GMainMenuState() noexcept {} \ No newline at end of file diff --git a/Evade2/src/MainMenuState/GMainMenuState.h b/Evade2/src/MainMenuState/GMainMenuState.h new file mode 100644 index 0000000..edccfd3 --- /dev/null +++ b/Evade2/src/MainMenuState/GMainMenuState.h @@ -0,0 +1,18 @@ +// +// Created by Michael Schwartz on 11/4/20. +// + +#ifndef EVADE2_GMAINMENUSTATE_H +#define EVADE2_GMAINMENUSTATE_H + +#include "Game.h" + +class GMainMenuState : public BGameEngine { +public: + GMainMenuState(); + + ~GMainMenuState() OVERRIDE; +}; + + +#endif //EVADE2_GMAINMENUSTATE_H diff --git a/Evade2/src/SplashState/GSplashProcess.cpp b/Evade2/src/SplashState/GSplashProcess.cpp index 5a797bc..dcdbaea 100644 --- a/Evade2/src/SplashState/GSplashProcess.cpp +++ b/Evade2/src/SplashState/GSplashProcess.cpp @@ -65,7 +65,7 @@ void GSplashProcess::RenderText() { TBool GSplashProcess::RunAfter() { if (gControls.WasPressed(BUTTON_ANY)) { // } || --mTimer <= 0) { - gGame->SetState(GAME_STATE_ATTRACT_MODE); + gGame->SetState(GAME_STATE_MAIN_MENU); #ifdef ENABLE_AUDIO gSoundPlayer.SfxStartGame(); diff --git a/Evade2/src/common/GCamera.cpp b/Evade2/src/common/GCamera.cpp index f2fee77..d81c2c5 100644 --- a/Evade2/src/common/GCamera.cpp +++ b/Evade2/src/common/GCamera.cpp @@ -1,58 +1,15 @@ #include "GCamera.h" -// -// -// +GCamera *gCamera; -TFloat GCamera::x = 0; -TFloat GCamera::y = 0; -TFloat GCamera::z = 0; +GCamera::GCamera() { + x = 0; + y = 0; + z = 0; -TFloat GCamera::vx = 0; -TFloat GCamera::vy = 0; -TFloat GCamera::vz = CAMERA_VZ; + vx = 0; + vy = 0; + vz = CAMERA_VZ; +} -// -//Camera::Camera() { -// mX = mY = mZ = 0; -// mVX = mVY = mVZ = 0; -//} -// -//public: -// static TFloat mX, mY, mZ; -// static TFloat mVX, mVY, mVZ; -// -// static void Move() { -// mX += mVX; -// mY += mVY; -// mZ += mVZ; -// } -// -//}; -//extern Camera *gCamera; - -//TFloat Camera::mX = 0; -//TFloat Camera::mY = 0; -//TFloat Camera::mZ = 0; -// -//TFloat Camera::mVX = 0; -//TFloat Camera::mVY = 0; -//TFloat Camera::mVZ = 0; -// -// -//void Camera::Move() { -// Camera::mX += Camera::mVX; -// Camera::mY += Camera::mVY; -// Camera::mZ += Camera::mVZ; -//} -//// -//TBool Camera::CollidesWith(GVectorSprite *aVSprite) { -// // If enemy bullet collides with player -// if (abs(aVSprite->mZ - Camera::mZ) < abs(aVSprite->mVZ) && abs(aVSprite->mX - Camera::mX) < 64 && abs(aVSprite->mY - Camera::mY) < 64) { -// return ETrue; -// } -// return EFalse; -//} -// -//extern Camera *gCamera; diff --git a/Evade2/src/common/GCamera.h b/Evade2/src/common/GCamera.h index 8253006..39be235 100644 --- a/Evade2/src/common/GCamera.h +++ b/Evade2/src/common/GCamera.h @@ -6,25 +6,28 @@ class GCamera { public: - static TFloat x,y,z; - static TFloat vx,vy,vz; + GCamera(); public: - static void Move() { - GCamera::x += GCamera::vx; - GCamera::y += GCamera::vy; - GCamera::z += GCamera::vz; + TFloat x, y, z; + TFloat vx, vy, vz; + +public: + void Move() { + x += vx; + y += vy; + z += vz; } - static TBool CollidesWith(GVectorSprite *aVSprite) { + TBool CollidesWith(GVectorSprite *aVSprite) const { // If enemy bullet collides with player - if (abs(aVSprite->z - GCamera::z) < abs(aVSprite->vz) && abs(aVSprite->x - GCamera::x) < 64 && abs(aVSprite->y - GCamera::y) < 64) { + if (abs(aVSprite->z - z) < abs(aVSprite->vz) && abs(aVSprite->x - x) < 64 && abs(aVSprite->y - y) < 64) { return ETrue; } return EFalse; } }; - +extern GCamera *gCamera; #endif diff --git a/Evade2/src/common/GStarfield.cpp b/Evade2/src/common/GStarfield.cpp index b7cf405..72b1713 100644 --- a/Evade2/src/common/GStarfield.cpp +++ b/Evade2/src/common/GStarfield.cpp @@ -6,6 +6,7 @@ #include "GCamera.h" GStarfield::GStarfield() : BPlayfield() { + gCamera = new GCamera(); for (TInt i = 0; i < NUM_STARS; i++) { InitStar(i); } @@ -17,7 +18,7 @@ GStarfield::~GStarfield() noexcept { void GStarfield::Render() { gDisplay.renderBitmap->Clear(0); - TFloat cz = GCamera::z, + TFloat cz = gCamera->z, sw = TFloat(SCREEN_WIDTH), sh = TFloat(SCREEN_HEIGHT); @@ -29,8 +30,8 @@ void GStarfield::Render() { } TFloat ratioX = sw / (zz + sw); TFloat ratioY = sh / (zz + sh); - TFloat x = (sw / 2) - (mStarX[i] - GCamera::x) * ratioX; - TFloat y = (sh / 2) - (mStarY[i] - GCamera::y) * ratioY; + TFloat x = (sw / 2) - (mStarX[i] - gCamera->x) * ratioX; + TFloat y = (sh / 2) - (mStarY[i] - gCamera->y) * ratioY; if (x < 0) { // printf("InitStar x %f < 0\n", x); @@ -51,7 +52,7 @@ void GStarfield::Render() { } void GStarfield::InitStar(TInt aIndex) { - mStarX[aIndex] = TFloat(256) - Random(0, 512) + GCamera::x; - mStarY[aIndex] = TFloat(256) - Random(0, 512) + GCamera::y; - mStarZ[aIndex] = GCamera::z + Random(200, 512); + mStarX[aIndex] = TFloat(256) - Random(0, 512) + gCamera->x; + mStarY[aIndex] = TFloat(256) - Random(0, 512) + gCamera->y; + mStarZ[aIndex] = gCamera->z + Random(200, 512); } \ No newline at end of file diff --git a/Evade2/src/common/GVectorFont.cpp b/Evade2/src/common/GVectorFont.cpp index 32f307f..3c15082 100644 --- a/Evade2/src/common/GVectorFont.cpp +++ b/Evade2/src/common/GVectorFont.cpp @@ -11,6 +11,7 @@ #include "charset.h" GVectorFont *gVectorFont; + // constructor GVectorFont::GVectorFont() { scale = 1.0; @@ -20,7 +21,7 @@ GVectorFont::GVectorFont() { #ifdef ENABLE_ROTATING_TEXT TInt16 GVectorFont::print_string_rotatedx(TFloat x, TFloat y, TFloat theta, const char *s) { - theta = float(theta) * 3.1415926 / 180; + theta = TFloat(theta) * 3.1415926 / 180; TFloat cost = cos(theta), sint = sin(theta); const char *p = s; @@ -29,9 +30,9 @@ TInt16 GVectorFont::print_string_rotatedx(TFloat x, TFloat y, TFloat theta, cons TInt16 xo = x; while (char c = *p++) { - auto *glyph = (const TInt16 *)charset[toupper(c) - 32]; + auto *glyph = (const TInt8 *)charset[toupper(c) - 32]; if (glyph) { - TInt16 lines = *glyph++; + TInt8 lines = *glyph++; for (TInt16 i = 0; i < lines; i++) { TFloat x0 = *glyph++ * scale + x, diff --git a/Evade2/src/common/GVectorSprite.cpp b/Evade2/src/common/GVectorSprite.cpp index 7714cea..f069138 100644 --- a/Evade2/src/common/GVectorSprite.cpp +++ b/Evade2/src/common/GVectorSprite.cpp @@ -78,20 +78,20 @@ TFloat GVectorSprite::DistanceTo(GVectorSprite *aOther) { }; TBool GVectorSprite::Render(BViewPort *aViewPort) { - if (!mLines || z <= GCamera::z) { + if (!mLines || z <= gCamera->z) { // nothing to draw return EFalse; } - TFloat zz = (z - GCamera::z) * 2; + TFloat zz = (z - gCamera->z) * 2; TFloat ratio = 128 / (zz + 128); TFloat sw = TFloat(SCREEN_WIDTH), sh = TFloat(SCREEN_HEIGHT); bool isEnemy = type == STYPE_ENEMY; // printf("is enemy = %i\n", isEnemy); - TFloat cx = (GCamera::x - x) * ratio + sw / 2; - TFloat cy = (GCamera::y - y) * ratio + sh / 2; + TFloat cx = (gCamera->x - x) * ratio + sw / 2; + TFloat cy = (gCamera->y - y) * ratio + sh / 2; // uint8_t color = isEnemy ? 5 : 255; @@ -102,8 +102,8 @@ TBool GVectorSprite::Render(BViewPort *aViewPort) { if ((!drawn) && isEnemy) { // draw radar blip - TFloat dx = GCamera::x - x, - dy = GCamera::y - y, + TFloat dx = gCamera->x - x, + dy = gCamera->y - y, angle = atan2(dy, dx), midx = sw / 2, midy = sh / 2, @@ -129,5 +129,5 @@ TBool GVectorSprite::Render(BViewPort *aViewPort) { TBool GVectorSprite::BehindCamera() { - return z <= GCamera::z; + return z <= gCamera->z; } \ No newline at end of file