From 7514bdc08b85a6a52dda0112143fed51ef761b74 Mon Sep 17 00:00:00 2001 From: nclok1405 <155463060+nclok1405@users.noreply.github.com> Date: Fri, 20 Jun 2025 07:06:10 +0900 Subject: [PATCH] Convert enemy-specific cheats "No ReDead/Gibdo Freeze" and "Keese/Guay don't Target You" to hooks (#5597) --- .../Enhancements/Cheats/NoKeeseGuayTarget.cpp | 23 +++++++++++ .../Enhancements/Cheats/NoRedeadFreeze.cpp | 17 ++++++++ .../vanilla-behavior/GIVanillaBehavior.h | 40 +++++++++++++++++++ .../overlays/actors/ovl_En_Crow/z_en_crow.c | 4 +- .../actors/ovl_En_Firefly/z_en_firefly.c | 4 +- soh/src/overlays/actors/ovl_En_Rd/z_en_rd.c | 4 +- 6 files changed, 86 insertions(+), 6 deletions(-) create mode 100644 soh/soh/Enhancements/Cheats/NoKeeseGuayTarget.cpp create mode 100644 soh/soh/Enhancements/Cheats/NoRedeadFreeze.cpp diff --git a/soh/soh/Enhancements/Cheats/NoKeeseGuayTarget.cpp b/soh/soh/Enhancements/Cheats/NoKeeseGuayTarget.cpp new file mode 100644 index 000000000..911f3cd25 --- /dev/null +++ b/soh/soh/Enhancements/Cheats/NoKeeseGuayTarget.cpp @@ -0,0 +1,23 @@ +#include +#include "soh/Enhancements/game-interactor/GameInteractor_Hooks.h" +#include "soh/ShipInit.hpp" + +extern "C" { +#include "macros.h" +} + +static constexpr int32_t CVAR_NOKEESEGUAYTARGET_DEFAULT = 0; +#define CVAR_NOKEESEGUAYTARGET_NAME CVAR_CHEAT("NoKeeseGuayTarget") +#define CVAR_NOKEESEGUAYTARGET_VALUE CVarGetInteger(CVAR_NOKEESEGUAYTARGET_NAME, CVAR_NOKEESEGUAYTARGET_DEFAULT) + +void RegisterNoKeeseGuayTarget() { + // Dive Attack + COND_VB_SHOULD(VB_KEESE_DO_DIVE_ATTACK, CVAR_NOKEESEGUAYTARGET_VALUE, { *should = false; }); + COND_VB_SHOULD(VB_GUAY_DO_DIVE_ATTACK, CVAR_NOKEESEGUAYTARGET_VALUE, { *should = false; }); + + // Force Fly Away + COND_VB_SHOULD(VB_KEESE_FORCE_FLY_AWAY, CVAR_NOKEESEGUAYTARGET_VALUE, { *should = true; }); + COND_VB_SHOULD(VB_GUAY_FORCE_FLY_AWAY, CVAR_NOKEESEGUAYTARGET_VALUE, { *should = true; }); +} + +static RegisterShipInitFunc initFunc_NoKeeseGuayTarget(RegisterNoKeeseGuayTarget, { CVAR_NOKEESEGUAYTARGET_NAME }); diff --git a/soh/soh/Enhancements/Cheats/NoRedeadFreeze.cpp b/soh/soh/Enhancements/Cheats/NoRedeadFreeze.cpp new file mode 100644 index 000000000..ccc406104 --- /dev/null +++ b/soh/soh/Enhancements/Cheats/NoRedeadFreeze.cpp @@ -0,0 +1,17 @@ +#include +#include "soh/Enhancements/game-interactor/GameInteractor_Hooks.h" +#include "soh/ShipInit.hpp" + +extern "C" { +#include "macros.h" +} + +static constexpr int32_t CVAR_NOREDEADFREEZE_DEFAULT = 0; +#define CVAR_NOREDEADFREEZE_NAME CVAR_CHEAT("NoRedeadFreeze") +#define CVAR_NOREDEADFREEZE_VALUE CVarGetInteger(CVAR_NOREDEADFREEZE_NAME, CVAR_NOREDEADFREEZE_DEFAULT) + +void RegisterNoRedeadFreeze() { + COND_VB_SHOULD(VB_REDEAD_GIBDO_FREEZE_LINK, CVAR_NOREDEADFREEZE_VALUE, { *should = false; }); +} + +static RegisterShipInitFunc initFunc_NoRedeadFreeze(RegisterNoRedeadFreeze, { CVAR_NOREDEADFREEZE_NAME }); diff --git a/soh/soh/Enhancements/game-interactor/vanilla-behavior/GIVanillaBehavior.h b/soh/soh/Enhancements/game-interactor/vanilla-behavior/GIVanillaBehavior.h index c561a0dfe..186307aed 100644 --- a/soh/soh/Enhancements/game-interactor/vanilla-behavior/GIVanillaBehavior.h +++ b/soh/soh/Enhancements/game-interactor/vanilla-behavior/GIVanillaBehavior.h @@ -1111,6 +1111,22 @@ typedef enum { // - None VB_GTG_GATE_BE_OPEN, + // #### `result` + // ```c + // true + // ``` + // #### `args` + // - `*EnCrow` + VB_GUAY_DO_DIVE_ATTACK, + + // #### `result` + // ```c + // false + // ``` + // #### `args` + // - `*EnCrow` + VB_GUAY_FORCE_FLY_AWAY, + // #### `result` // ```c // true @@ -1199,6 +1215,22 @@ typedef enum { // - None VB_KALEIDO_UNPAUSE_CLOSE, + // #### `result` + // ```c + // true + // ``` + // #### `args` + // - `*EnFirefly` + VB_KEESE_DO_DIVE_ATTACK, + + // #### `result` + // ```c + // false + // ``` + // #### `args` + // - `*EnFirefly` + VB_KEESE_FORCE_FLY_AWAY, + // #### `result` // ```c // Flags_GetEventChkInf(EVENTCHKINF_KING_ZORA_MOVED) @@ -1713,6 +1745,14 @@ typedef enum { // - None VB_PREVENT_ADULT_STICK, + // #### `result` + // ```c + // true + // ``` + // #### `args` + // - `*EnRd` + VB_REDEAD_GIBDO_FREEZE_LINK, + // #### `result` // #### `result` // ```c diff --git a/soh/src/overlays/actors/ovl_En_Crow/z_en_crow.c b/soh/src/overlays/actors/ovl_En_Crow/z_en_crow.c index 7ab5fbd84..1d2e0d156 100644 --- a/soh/src/overlays/actors/ovl_En_Crow/z_en_crow.c +++ b/soh/src/overlays/actors/ovl_En_Crow/z_en_crow.c @@ -285,7 +285,7 @@ void EnCrow_FlyIdle(EnCrow* this, PlayState* play) { } if ((this->timer == 0) && (this->actor.xzDistToPlayer < 300.0f) && !(player->stateFlags1 & PLAYER_STATE1_ON_HORSE) && (this->actor.yDistToWater < -40.0f) && - (Player_GetMask(play) != PLAYER_MASK_SKULL) && !CVarGetInteger(CVAR_CHEAT("NoKeeseGuayTarget"), 0)) { + (Player_GetMask(play) != PLAYER_MASK_SKULL) && GameInteractor_Should(VB_GUAY_DO_DIVE_ATTACK, true, this)) { EnCrow_SetupDiveAttack(this); } } @@ -322,7 +322,7 @@ void EnCrow_DiveAttack(EnCrow* this, PlayState* play) { if ((this->timer == 0) || (Player_GetMask(play) == PLAYER_MASK_SKULL) || (this->collider.base.atFlags & AT_HIT) || (this->actor.bgCheckFlags & 9) || (player->stateFlags1 & PLAYER_STATE1_ON_HORSE) || - (this->actor.yDistToWater > -40.0f) || CVarGetInteger(CVAR_CHEAT("NoKeeseGuayTarget"), 0)) { + (this->actor.yDistToWater > -40.0f) || GameInteractor_Should(VB_GUAY_FORCE_FLY_AWAY, false, this)) { if (this->collider.base.atFlags & AT_HIT) { this->collider.base.atFlags &= ~AT_HIT; Audio_PlayActorSound2(&this->actor, NA_SE_EN_KAICHO_ATTACK); diff --git a/soh/src/overlays/actors/ovl_En_Firefly/z_en_firefly.c b/soh/src/overlays/actors/ovl_En_Firefly/z_en_firefly.c index ced99da23..cda0fb18a 100644 --- a/soh/src/overlays/actors/ovl_En_Firefly/z_en_firefly.c +++ b/soh/src/overlays/actors/ovl_En_Firefly/z_en_firefly.c @@ -416,7 +416,7 @@ void EnFirefly_FlyIdle(EnFirefly* this, PlayState* play) { Math_SmoothStepToS(&this->actor.shape.rot.y, this->actor.wallYaw, 2, 0xC00, 0x300); } if ((this->timer == 0) && (this->actor.xzDistToPlayer < 200.0f) && (Player_GetMask(play) != PLAYER_MASK_SKULL) && - !CVarGetInteger(CVAR_CHEAT("NoKeeseGuayTarget"), 0)) { + GameInteractor_Should(VB_KEESE_DO_DIVE_ATTACK, true, this)) { EnFirefly_SetupDiveAttack(this); } } @@ -495,7 +495,7 @@ void EnFirefly_DiveAttack(EnFirefly* this, PlayState* play) { Math_ScaledStepToS(&this->actor.shape.rot.x, this->targetPitch, 0x100); } if ((this->timer == 0) || (Player_GetMask(play) == PLAYER_MASK_SKULL) || - CVarGetInteger(CVAR_CHEAT("NoKeeseGuayTarget"), 0)) { + GameInteractor_Should(VB_KEESE_FORCE_FLY_AWAY, false, this)) { EnFirefly_SetupFlyAway(this); } } diff --git a/soh/src/overlays/actors/ovl_En_Rd/z_en_rd.c b/soh/src/overlays/actors/ovl_En_Rd/z_en_rd.c index e9b4ee2b6..062be3268 100644 --- a/soh/src/overlays/actors/ovl_En_Rd/z_en_rd.c +++ b/soh/src/overlays/actors/ovl_En_Rd/z_en_rd.c @@ -344,7 +344,7 @@ void func_80AE2C1C(EnRd* this, PlayState* play) { !(player->stateFlags2 & PLAYER_STATE2_GRABBED_BY_ENEMY)) { if (this->unk_306 == 0) { if (!(this->unk_312 & PLAYER_STATE2_GRABBED_BY_ENEMY) && - !CVarGetInteger(CVAR_CHEAT("NoRedeadFreeze"), 0)) { + GameInteractor_Should(VB_REDEAD_GIBDO_FREEZE_LINK, true, this)) { player->actor.freezeTimer = 40; Player_SetAutoLockOnActor(play, &this->actor); GET_PLAYER(play)->autoLockOnActor = &this->actor; @@ -575,7 +575,7 @@ void func_80AE3834(EnRd* this, PlayState* play) { s16 temp_v0 = this->actor.yawTowardsPlayer - this->actor.shape.rot.y - this->unk_30E - this->unk_310; if (ABS(temp_v0) < 0x2008) { - if (!(this->unk_312 & 0x80) && !CVarGetInteger(CVAR_CHEAT("NoRedeadFreeze"), 0)) { + if (!(this->unk_312 & 0x80) && GameInteractor_Should(VB_REDEAD_GIBDO_FREEZE_LINK, true, this)) { player->actor.freezeTimer = 60; func_800AA000(this->actor.xzDistToPlayer, 0xFF, 0x14, 0x96); Player_SetAutoLockOnActor(play, &this->actor);