From d649039676a16f61a1c06ade5dadb2a416c95a44 Mon Sep 17 00:00:00 2001 From: CCHyper <73803386+CCHyper@users.noreply.github.com> Date: Wed, 9 Jun 2021 13:39:29 +0100 Subject: [PATCH] Fixes bug with the current difficulty not being checked when enabling triggers. --- src/extensions/extension_hooks.cpp | 4 +- src/extensions/taction/tactionext_hooks.cpp | 52 ++++++++++++ src/extensions/trigger/triggerext_hooks.cpp | 87 +++++++++++++++++++++ src/extensions/trigger/triggerext_hooks.h | 31 ++++++++ 4 files changed, 172 insertions(+), 2 deletions(-) create mode 100644 src/extensions/trigger/triggerext_hooks.cpp create mode 100644 src/extensions/trigger/triggerext_hooks.h diff --git a/src/extensions/extension_hooks.cpp b/src/extensions/extension_hooks.cpp index b35cbb336..73e7512f8 100644 --- a/src/extensions/extension_hooks.cpp +++ b/src/extensions/extension_hooks.cpp @@ -70,7 +70,7 @@ //#include "teamtypeext_hooks.h" #include "terrainext_hooks.h" #include "terraintypeext_hooks.h" -//#include "triggerext_hooks.h" +#include "triggerext_hooks.h" #include "triggertypeext_hooks.h" #include "unittypeext_hooks.h" //#include "voxelanimext_hooks.h" @@ -201,7 +201,7 @@ void Extension_Hooks() //TeamTypeClassExtension_Hooks(); // Not yet implemented TerrainClassExtension_Hooks(); TerrainTypeClassExtension_Hooks(); - //TriggerTypeExtension_Hooks(); // Not yet implemented + TriggerClassExtension_Hooks(); TriggerTypeClassExtension_Hooks(); // Not yet implemented UnitTypeClassExtension_Hooks(); //VoxelAnimClassExtension_Hooks(); // Not yet implemented diff --git a/src/extensions/taction/tactionext_hooks.cpp b/src/extensions/taction/tactionext_hooks.cpp index e9a4f0525..0bf99a3bf 100644 --- a/src/extensions/taction/tactionext_hooks.cpp +++ b/src/extensions/taction/tactionext_hooks.cpp @@ -26,6 +26,10 @@ * ******************************************************************************/ #include "tactionext_hooks.h" +#include "tibsun_globals.h" +#include "trigger.h" +#include "triggertype.h" +#include "scenario.h" #include "fatal.h" #include "debughandler.h" #include "asserthandler.h" @@ -34,6 +38,52 @@ #include "hooker_macros.h" +/** + * #issue-299 + * + * Fixes the issue with the current difficulty not being checked + * when enabling triggers. + * + * @see: TriggerClass and TriggerTypeClass for the other parts of this fix. + * + * @author: CCHyper + */ +DECLARE_PATCH(_TActionClass_Operator_Enable_Trigger_For_Difficulty_Patch) +{ + GET_REGISTER_STATIC(int, trigger_index, edi); + static TriggerClass *trigger; + + /** + * This is direct port of the code from Red Alert 2, which looks to fix this issue. + */ + + /** + * We need to re-fetch the trigger from the vector as the + * register is reused by this point. + */ + trigger = Triggers[trigger_index]; + if (trigger) { + + /** + * Set this trigger to be disabled if it is marked as disabled + * for this current mission difficulty. + */ + if (Scen->Difficulty == DIFF_EASY && !trigger->Class->Easy + || Scen->Difficulty == DIFF_NORMAL && !trigger->Class->Normal + || Scen->Difficulty == DIFF_HARD && !trigger->Class->Hard) { + + trigger->Disable(); + + } else { + + trigger->Enable(); + } + } + + JMP(0x0061A611); +} + + /** * Main function for patching the hooks. */ @@ -51,4 +101,6 @@ void TActionClassExtension_Hooks() * @author: CCHyper */ Patch_Dword(0x00619552+2, (0x007E4820+4)); // Foot vector to Technos vector. + + Patch_Jump(0x0061A60C, &_TActionClass_Operator_Enable_Trigger_For_Difficulty_Patch); } diff --git a/src/extensions/trigger/triggerext_hooks.cpp b/src/extensions/trigger/triggerext_hooks.cpp new file mode 100644 index 000000000..48561c653 --- /dev/null +++ b/src/extensions/trigger/triggerext_hooks.cpp @@ -0,0 +1,87 @@ +/******************************************************************************* +/* O P E N S O U R C E -- V I N I F E R A ** +/******************************************************************************* + * + * @project Vinifera + * + * @file TRIGGEREXT_HOOKS.CPP + * + * @author CCHyper + * + * @brief Contains the hooks for the extended TriggerClass. + * + * @license Vinifera is free software: you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version + * 3 of the License, or (at your option) any later version. + * + * Vinifera is distributed in the hope that it will be + * useful, but WITHOUT ANY WARRANTY; without even the implied + * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public + * License along with this program. + * If not, see . + * + ******************************************************************************/ +#include "sideext_hooks.h" +#include "tibsun_globals.h" +#include "trigger.h" +#include "triggertype.h" +#include "scenario.h" +#include "fatal.h" +#include "debughandler.h" +#include "asserthandler.h" + +#include "hooker.h" +#include "hooker_macros.h" + + +/** + * #issue-299 + * + * Fixes the issue with the current difficulty not being checked + * when enabling triggers. + * + * @see: TriggerTypeClass and TActionClass for the other parts of this fix. + * + * @author: CCHyper + */ +DECLARE_PATCH(_TriggerClass_Constructor_Enabled_For_Difficulty_Patch) +{ + GET_REGISTER_STATIC(TriggerClass *, this_ptr, esi); + + /** + * This is direct port of the code from Red Alert 2, which looks to fix this issue. + */ + + if (this_ptr->Class) { + + this_ptr->Reset(); + + /** + * Set this trigger to be disabled if; + * - The class instance is marked as inactive. + * - It is marked as disabled for this current mission difficulty. + */ + if (!this_ptr->Class->Enabled + || (Scen->Difficulty == DIFF_EASY && !this_ptr->Class->Easy) + || (Scen->Difficulty == DIFF_NORMAL && !this_ptr->Class->Normal) + || (Scen->Difficulty == DIFF_HARD && !this_ptr->Class->Hard)) { + + this_ptr->IsEnabled = false; + } + } + + JMP(0x00649188); +} + + +/** + * Main function for patching the hooks. + */ +void TriggerClassExtension_Hooks() +{ + Patch_Jump(0x00649171, &_TriggerClass_Constructor_Enabled_For_Difficulty_Patch); +} diff --git a/src/extensions/trigger/triggerext_hooks.h b/src/extensions/trigger/triggerext_hooks.h new file mode 100644 index 000000000..2caa569a1 --- /dev/null +++ b/src/extensions/trigger/triggerext_hooks.h @@ -0,0 +1,31 @@ +/******************************************************************************* +/* O P E N S O U R C E -- V I N I F E R A ** +/******************************************************************************* + * + * @project Vinifera + * + * @file TRIGGEREXT_HOOKS.H + * + * @author CCHyper + * + * @brief Contains the hooks for the extended TriggerClass. + * + * @license Vinifera is free software: you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation, either version + * 3 of the License, or (at your option) any later version. + * + * Vinifera is distributed in the hope that it will be + * useful, but WITHOUT ANY WARRANTY; without even the implied + * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR + * PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public + * License along with this program. + * If not, see . + * + ******************************************************************************/ +#pragma once + + +void TriggerClassExtension_Hooks();