From 13fc4e328534238f0ffe1bcfcaf37c820c64f2ec Mon Sep 17 00:00:00 2001 From: Nathan M Gilbert Date: Sat, 24 Feb 2024 08:55:00 -0500 Subject: [PATCH] LegoGameState::SwitchArea (#590) --- LEGO1/lego/legoomni/include/legogamestate.h | 37 +-- .../lego/legoomni/include/legonavcontroller.h | 1 + LEGO1/lego/legoomni/include/legoutil.h | 1 + .../legoomni/src/common/legogamestate.cpp | 245 ++++++++++-------- LEGO1/lego/legoomni/src/common/legoutil.cpp | 7 + .../legoomni/src/entity/legonavcontroller.cpp | 5 + .../src/infocenter/elevatorbottom.cpp | 2 +- .../legoomni/src/infocenter/infocenter.cpp | 12 +- LEGO1/lego/legoomni/src/police/police.cpp | 2 +- .../lego/sources/3dmanager/lego3dmanager.cpp | 8 + LEGO1/lego/sources/3dmanager/lego3dmanager.h | 2 + 11 files changed, 192 insertions(+), 130 deletions(-) diff --git a/LEGO1/lego/legoomni/include/legogamestate.h b/LEGO1/lego/legoomni/include/legogamestate.h index 011fbf8a..e4458213 100644 --- a/LEGO1/lego/legoomni/include/legogamestate.h +++ b/LEGO1/lego/legoomni/include/legogamestate.h @@ -35,35 +35,35 @@ public: e_infodoor, e_unk4, e_elevbott, - e_unk6, - e_unk7, - e_unk8, - e_unk9, - e_unk10, - e_unk11, + e_elevride, + e_elevride2, + e_elevopen, + e_seaview, + e_observe, + e_elevdown, e_regbook, e_infoscor, e_jetrace, - e_unk15, - e_unk16, + e_jetrace2, + e_jetraceExterior, e_unk17, e_carrace, - e_unk19, + e_carraceExterior, e_unk20, e_unk21, - e_unk22, + e_pizzeriaExterior, - e_unk25 = 25, + e_garageExterior = 25, e_garage, - e_unk27, - - e_unk29 = 29, + e_garadoor, + e_unk28, + e_hospitalExterior, e_hospital, e_unk31, - e_unk32, - - e_police = 34, - e_unk35, + e_policeExterior, + e_unk33, + e_police, + e_polidoor, e_copter, e_dunecar, e_jetski, @@ -73,6 +73,7 @@ public: e_act3script, e_jukeboxw = 53, + e_unk54, e_histbook = 56, e_unk57, diff --git a/LEGO1/lego/legoomni/include/legonavcontroller.h b/LEGO1/lego/legoomni/include/legonavcontroller.h index 58ace217..e5c74f35 100644 --- a/LEGO1/lego/legoomni/include/legonavcontroller.h +++ b/LEGO1/lego/legoomni/include/legonavcontroller.h @@ -56,6 +56,7 @@ public: void SetControlMax(int p_hMax, int p_vMax); void ResetToDefault(); void SetTargets(int p_hPos, int p_vPos, MxBool p_accel); + static void SetLocation(MxU32 p_location); float CalculateNewTargetSpeed(int p_pos, int p_center, float p_maxSpeed); float CalculateNewAccel(int p_pos, int p_center, float p_maxAccel, int p_minAccel); float CalculateNewVel(float p_targetVel, float p_currentVel, float p_accel, float p_time); diff --git a/LEGO1/lego/legoomni/include/legoutil.h b/LEGO1/lego/legoomni/include/legoutil.h index 696a1cc4..0b35fc61 100644 --- a/LEGO1/lego/legoomni/include/legoutil.h +++ b/LEGO1/lego/legoomni/include/legoutil.h @@ -34,6 +34,7 @@ private: void FUN_1003e050(LegoAnimPresenter* p_presenter); Extra::ActionType MatchActionString(const char*); void InvokeAction(Extra::ActionType p_actionId, MxAtomId& p_pAtom, int p_targetEntityId, LegoEntity* p_sender); +void SetCameraControllerFromIsle(); void ConvertHSVToRGB(float p_h, float p_s, float p_v, float* p_rOut, float* p_bOut, float* p_gOut); MxBool FUN_1003ee00(MxAtomId& p_atomId, MxS32 p_id); void FUN_1003ef00(MxBool); diff --git a/LEGO1/lego/legoomni/src/common/legogamestate.cpp b/LEGO1/lego/legoomni/src/common/legogamestate.cpp index 9d81f699..0c43d19e 100644 --- a/LEGO1/lego/legoomni/src/common/legogamestate.cpp +++ b/LEGO1/lego/legoomni/src/common/legogamestate.cpp @@ -1,7 +1,11 @@ #include "legogamestate.h" +#include "act1state.h" +#include "define.h" #include "infocenterstate.h" +#include "islepathactor.h" #include "legoanimationmanager.h" +#include "legonavcontroller.h" #include "legoomni.h" #include "legostate.h" #include "legoutil.h" @@ -298,8 +302,8 @@ void LegoGameState::StopArea(Area p_area) InvokeAction(Extra::e_stop, *g_elevbottScript, 0, NULL); InvokeAction(Extra::e_close, *g_elevbottScript, 0, NULL); break; - case e_unk6: - case e_unk7: + case e_elevride: + case e_elevride2: RemoveFromWorld(*g_isleScript, 0x41b, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 1052, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x41d, *g_isleScript, 0); @@ -312,17 +316,17 @@ void LegoGameState::StopArea(Area p_area) RemoveFromWorld(*g_isleScript, 0x42a, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x42b, *g_isleScript, 0); break; - case e_unk8: + case e_elevopen: RemoveFromWorld(*g_isleScript, 0x45b, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x45c, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x45d, *g_isleScript, 0); break; - case e_unk9: + case e_seaview: RemoveFromWorld(*g_isleScript, 0x475, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x476, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x477, *g_isleScript, 0); break; - case e_unk10: + case e_observe: RemoveFromWorld(*g_isleScript, 0x45f, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x460, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x461, *g_isleScript, 0); @@ -344,7 +348,7 @@ void LegoGameState::StopArea(Area p_area) RemoveFromWorld(*g_isleScript, 0x472, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x12, *g_isleScript, 0); break; - case e_unk11: + case e_elevdown: RemoveFromWorld(*g_isleScript, 0x47a, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x47b, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x47c, *g_isleScript, 0); @@ -373,7 +377,7 @@ void LegoGameState::StopArea(Area p_area) InvokeAction(Extra::e_stop, *g_garageScript, 0, NULL); InvokeAction(Extra::e_close, *g_garageScript, 0, NULL); break; - case e_unk27: + case e_garadoor: RemoveFromWorld(*g_isleScript, 0x489, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x48a, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x48b, *g_isleScript, 0); @@ -387,7 +391,7 @@ void LegoGameState::StopArea(Area p_area) InvokeAction(Extra::e_stop, *g_policeScript, 0, NULL); InvokeAction(Extra::e_close, *g_policeScript, 0, NULL); break; - case e_unk35: + case e_polidoor: RemoveFromWorld(*g_isleScript, 0x47f, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x480, *g_isleScript, 0); RemoveFromWorld(*g_isleScript, 0x481, *g_isleScript, 0); @@ -437,6 +441,26 @@ void LegoGameState::StopArea(Area p_area) } } +inline void LoadIsle() +{ + LegoWorld* world = FindWorld(*g_isleScript, 0); + if (world != NULL) { + if (!world->GetUnknown0xd0().empty()) { +#ifdef COMPAT_MODE + { + MxNotificationParam param(c_notificationType20, NULL); + NotificationManager()->Send(world, ¶m); + } +#else + NotificationManager()->Send(world, &MxNotificationParam(c_notificationType20, NULL)); +#endif + } + } + else { + InvokeAction(Extra::ActionType::e_opendisk, *g_isleScript, 0, NULL); + } +} + // FUNCTION: LEGO1 0x1003b060 void LegoGameState::SwitchArea(Area p_area) { @@ -448,8 +472,6 @@ void LegoGameState::SwitchArea(Area p_area) AnimationManager()->FUN_1005ef10(); VideoManager()->SetUnk0x554(FALSE); - LegoWorld* world; - switch (p_area) { case e_isle: InvokeAction(Extra::ActionType::e_opendisk, *g_isleScript, 0, NULL); @@ -463,17 +485,17 @@ void LegoGameState::SwitchArea(Area p_area) InvokeAction(Extra::ActionType::e_opendisk, *g_infodoorScript, 0, NULL); break; case e_unk4: - case e_unk15: - case e_unk16: + case e_jetrace2: + case e_jetraceExterior: case e_unk17: - case e_unk19: + case e_carraceExterior: case e_unk20: case e_unk21: - case e_unk22: - case e_unk25: - case e_unk29: + case e_pizzeriaExterior: + case e_garageExterior: + case e_hospitalExterior: case e_unk31: - case e_unk32: + case e_policeExterior: case e_unk57: case e_unk58: case e_unk59: @@ -481,58 +503,27 @@ void LegoGameState::SwitchArea(Area p_area) case e_unk61: case e_unk64: case e_unk66: - world = FindWorld(*g_isleScript, 0); - if (world != NULL) { - if (world->GetUnknown0xd0().empty()) { - break; - } - else { -#ifdef COMPAT_MODE - { - MxNotificationParam param(c_notificationType20, NULL); - NotificationManager()->Send(world, ¶m); - } -#else - NotificationManager()->Send(world, &MxNotificationParam(c_notificationType20, NULL)); -#endif - break; - } - } - InvokeAction(Extra::ActionType::e_opendisk, *g_isleScript, 0, NULL); + LoadIsle(); break; case e_elevbott: InvokeAction(Extra::ActionType::e_opendisk, *g_elevbottScript, 0, NULL); break; - case e_unk6: - case e_unk7: - world = FindWorld(*g_isleScript, 0); - - if (world == NULL) { - InvokeAction(Extra::ActionType::e_opendisk, *g_isleScript, 0, NULL); - } - else if (!world->GetUnknown0xd0().empty()) { -#ifdef COMPAT_MODE - { - MxNotificationParam param(c_notificationType20, NULL); - NotificationManager()->Send(world, ¶m); - } -#else - NotificationManager()->Send(world, &MxNotificationParam(c_notificationType20, NULL)); -#endif - } + case e_elevride: + case e_elevride2: + LoadIsle(); InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1050, NULL); break; - case e_unk8: + case e_elevopen: VideoManager()->SetUnk0x554(TRUE); InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1114, NULL); break; - case e_unk9: + case e_seaview: InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1140, NULL); break; - case e_unk10: + case e_observe: InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1118, NULL); break; - case e_unk11: + case e_elevdown: InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1145, NULL); break; case e_regbook: @@ -545,64 +536,110 @@ void LegoGameState::SwitchArea(Area p_area) break; case e_jetrace: if (m_previousArea == e_infomain) { - m_currentArea = e_unk15; - - world = FindWorld(*g_isleScript, 0); - if (world != NULL) { - if (world->GetUnknown0xd0().empty()) { - return; - } - else { -#ifdef COMPAT_MODE - { - MxNotificationParam param(c_notificationType20, NULL); - NotificationManager()->Send(world, ¶m); - } -#else - NotificationManager()->Send(world, &MxNotificationParam(c_notificationType20, NULL)); -#endif - } - return; - } - else { - InvokeAction(Extra::ActionType::e_opendisk, *g_isleScript, 0, NULL); - break; - } + m_currentArea = e_jetrace2; + LoadIsle(); + } + else { + InvokeAction(Extra::ActionType::e_opendisk, *g_jetraceScript, 0, NULL); } - - InvokeAction(Extra::ActionType::e_opendisk, *g_jetraceScript, 0, NULL); break; case e_carrace: if (m_previousArea == e_infomain) { - m_currentArea = e_unk19; - - world = FindWorld(*g_isleScript, 0); - if (world != NULL) { - if (world->GetUnknown0xd0().empty()) { - return; - } - else { -#ifdef COMPAT_MODE - { - MxNotificationParam param(c_notificationType20, NULL); - NotificationManager()->Send(world, ¶m); - } -#else - NotificationManager()->Send(world, &MxNotificationParam(c_notificationType20, NULL)); -#endif - } - return; - } + m_currentArea = e_carraceExterior; + LoadIsle(); + } + else { + InvokeAction(Extra::ActionType::e_opendisk, *g_carraceScript, 0, NULL); } - - InvokeAction(Extra::ActionType::e_opendisk, *g_carraceScript, 0, NULL); break; case e_garage: VideoManager()->SetUnk0x554(TRUE); InvokeAction(Extra::ActionType::e_opendisk, *g_garageScript, 0, NULL); break; - - // TODO: implement other cases + case e_garadoor: + LoadIsle(); + VariableTable()->SetVariable("VISIBILITY", "Hide Gas"); + CurrentVehicle()->ResetWorldTransform(FALSE); + NavController()->SetLocation(0x3b); + VideoManager()->Get3DManager()->SetFrustrum(90, 0.1f, 250.0f); + InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1160, NULL); + break; + case e_unk28: { + Act1State* state = (Act1State*) GameState()->GetState("Act1State"); + LoadIsle(); + if (state->GetUnknown18() == 7) { + VideoManager()->Get3DManager()->SetFrustrum(90, 0.1f, 250.0f); + } + else { + SetCameraControllerFromIsle(); + CurrentVehicle()->ResetWorldTransform(TRUE); + AnimationManager()->FUN_1005f0b0(); + } + CurrentVehicle()->VTable0xe8(p_area, TRUE, 7); + break; + } + case e_hospital: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_hospitalScript, 0, NULL); + break; + case e_unk33: + LoadIsle(); + SetCameraControllerFromIsle(); + CurrentVehicle()->ResetWorldTransform(TRUE); + AnimationManager()->FUN_1005f0b0(); + CurrentVehicle()->VTable0xe8(p_area, TRUE, 7); + break; + case e_police: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_policeScript, 0, NULL); + break; + case e_polidoor: + LoadIsle(); + InvokeAction(Extra::ActionType::e_start, *g_isleScript, 1150, NULL); + break; + case e_copter: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_copterScript, 0, NULL); + break; + case e_dunecar: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_dunecarScript, 0, NULL); + break; + case e_jetski: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_jetskiScript, 0, NULL); + break; + case e_racecar: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_racecarScript, 0, NULL); + break; + case e_act2main: { + LegoWorld* act2main = FindWorld(*g_act2mainScript, 0); + if (act2main == NULL) { + InvokeAction(Extra::ActionType::e_opendisk, *g_act2mainScript, 0, NULL); + } + else { + act2main->Enable(TRUE); + } + break; + } + case e_act3script: { + LegoWorld* act3 = FindWorld(*g_act3Script, 0); + if (act3 == NULL) { + InvokeAction(Extra::ActionType::e_opendisk, *g_act3Script, 0, NULL); + } + else { + act3->Enable(TRUE); + } + break; + } + case e_jukeboxw: + VideoManager()->SetUnk0x554(TRUE); + InvokeAction(Extra::ActionType::e_opendisk, *g_jukeboxwScript, 0, NULL); + break; + case e_unk54: + LoadIsle(); + break; case e_histbook: VideoManager()->SetUnk0x554(TRUE); InvokeAction(Extra::ActionType::e_opendisk, *g_histbookScript, 0, NULL); diff --git a/LEGO1/lego/legoomni/src/common/legoutil.cpp b/LEGO1/lego/legoomni/src/common/legoutil.cpp index 3951f94f..fabe18d6 100644 --- a/LEGO1/lego/legoomni/src/common/legoutil.cpp +++ b/LEGO1/lego/legoomni/src/common/legoutil.cpp @@ -1,5 +1,6 @@ #include "legoutil.h" +#include "legoinputmanager.h" #include "legoomni.h" #include "legoworld.h" #include "legoworldlist.h" @@ -161,6 +162,12 @@ void NotifyEntity(const char* p_filename, MxS32 p_entityId, LegoEntity* p_sender } } +// FUNCTION: LEGO1 0x1003eab0 +void SetCameraControllerFromIsle() +{ + InputManager()->SetCamera(FindWorld(*g_isleScript, 0)->GetCamera()); +} + // FUNCTION: LEGO1 0x1003eae0 void ConvertHSVToRGB(float p_h, float p_s, float p_v, float* p_rOut, float* p_bOut, float* p_gOut) { diff --git a/LEGO1/lego/legoomni/src/entity/legonavcontroller.cpp b/LEGO1/lego/legoomni/src/entity/legonavcontroller.cpp index 8a9ec812..e6dc33a2 100644 --- a/LEGO1/lego/legoomni/src/entity/legonavcontroller.cpp +++ b/LEGO1/lego/legoomni/src/entity/legonavcontroller.cpp @@ -230,6 +230,11 @@ float LegoNavController::CalculateNewVel(float p_targetVel, float p_currentVel, return newVel; } +// STUB: LEGO1 0x10055620 +void LegoNavController::SetLocation(MxU32 p_location) +{ +} + // STUB: LEGO1 0x10055a60 MxLong LegoNavController::Notify(MxParam& p_param) { diff --git a/LEGO1/lego/legoomni/src/infocenter/elevatorbottom.cpp b/LEGO1/lego/legoomni/src/infocenter/elevatorbottom.cpp index 5ef0d580..960cf40e 100644 --- a/LEGO1/lego/legoomni/src/infocenter/elevatorbottom.cpp +++ b/LEGO1/lego/legoomni/src/infocenter/elevatorbottom.cpp @@ -101,7 +101,7 @@ MxLong ElevatorBottom::HandleClick(LegoControlManagerEvent& p_param) } state->SetUnknown1c(1); - m_unk0xf8 = LegoGameState::e_unk6; + m_unk0xf8 = LegoGameState::e_elevride; TransitionManager()->StartTransition(MxTransitionManager::e_pixelation, 50, FALSE, FALSE); VariableTable()->SetVariable(g_varCAMERALOCATION, "LCAMZI1,90"); result = 1; diff --git a/LEGO1/lego/legoomni/src/infocenter/infocenter.cpp b/LEGO1/lego/legoomni/src/infocenter/infocenter.cpp index 64bd9e58..cef49c68 100644 --- a/LEGO1/lego/legoomni/src/infocenter/infocenter.cpp +++ b/LEGO1/lego/legoomni/src/infocenter/infocenter.cpp @@ -756,37 +756,37 @@ MxU8 Infocenter::HandleButtonUp(MxS32 p_x, MxS32 p_y) break; case 10: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk16; + m_transitionDestination = LegoGameState::e_jetraceExterior; m_infocenterState->SetUnknown0x74(5); } break; case 11: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk19; + m_transitionDestination = LegoGameState::e_carraceExterior; m_infocenterState->SetUnknown0x74(5); } break; case 12: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk22; + m_transitionDestination = LegoGameState::e_pizzeriaExterior; m_infocenterState->SetUnknown0x74(5); } break; case 13: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk25; + m_transitionDestination = LegoGameState::e_garageExterior; m_infocenterState->SetUnknown0x74(5); } break; case 14: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk29; + m_transitionDestination = LegoGameState::e_hospitalExterior; m_infocenterState->SetUnknown0x74(5); } break; case 15: if (m_selectedCharacter) { - m_transitionDestination = LegoGameState::e_unk32; + m_transitionDestination = LegoGameState::e_policeExterior; m_infocenterState->SetUnknown0x74(5); } break; diff --git a/LEGO1/lego/legoomni/src/police/police.cpp b/LEGO1/lego/legoomni/src/police/police.cpp index 6c404a33..b95938ee 100644 --- a/LEGO1/lego/legoomni/src/police/police.cpp +++ b/LEGO1/lego/legoomni/src/police/police.cpp @@ -108,7 +108,7 @@ MxLong Police::HandleClick(LegoControlManagerEvent& p_param) } BackgroundAudioManager()->Stop(); - m_transitionDestination = LegoGameState::Area::e_unk35; + m_transitionDestination = LegoGameState::Area::e_polidoor; TransitionManager()->StartTransition(MxTransitionManager::e_pixelation, 50, FALSE, FALSE); break; case c_infoCtl: diff --git a/LEGO1/lego/sources/3dmanager/lego3dmanager.cpp b/LEGO1/lego/sources/3dmanager/lego3dmanager.cpp index 4fa43a3c..f58a519a 100644 --- a/LEGO1/lego/sources/3dmanager/lego3dmanager.cpp +++ b/LEGO1/lego/sources/3dmanager/lego3dmanager.cpp @@ -94,3 +94,11 @@ double Lego3DManager::Render(double p_und) return m_pLego3DView->Render(p_und); } + +// FUNCTION: LEGO1 0x100ab4d0 +int Lego3DManager::SetFrustrum(float p_fov, float p_front, float p_back) +{ + m_pLego3DView->GetView()->SetFrustrum(p_front, p_back, p_fov); + m_pLego3DView->GetViewManager()->SetFrustrum(p_fov, p_front, p_back); + return 0; +} diff --git a/LEGO1/lego/sources/3dmanager/lego3dmanager.h b/LEGO1/lego/sources/3dmanager/lego3dmanager.h index 9d993f26..82f4e4a3 100644 --- a/LEGO1/lego/sources/3dmanager/lego3dmanager.h +++ b/LEGO1/lego/sources/3dmanager/lego3dmanager.h @@ -51,6 +51,8 @@ public: double Render(double p_und); + int SetFrustrum(float p_fov, float p_front, float p_back); + Tgl::Renderer* GetRenderer(); Tgl::Group* GetScene(); Lego3DView* GetLego3DView();