mirror of
https://github.com/HarbourMasters/Shipwright
synced 2026-06-26 10:41:53 -04:00
Vanilla bugfix, Deku Shield burning drop crash (#6810)
This commit is contained in:
@@ -3,6 +3,9 @@
|
||||
#include "soh/ShipInit.hpp"
|
||||
|
||||
extern "C" {
|
||||
#include "macros.h"
|
||||
#include "functions.h"
|
||||
#include "variables.h"
|
||||
extern void Player_UseItem(PlayState*, Player*, s32);
|
||||
extern PlayState* gPlayState;
|
||||
}
|
||||
@@ -20,6 +23,17 @@ void RegisterFixOutsideTotCrash() {
|
||||
});
|
||||
}
|
||||
|
||||
// Vanilla bug: `Actor_Item_Shield` (dropped Deku Shield when burning) assumes that segment 12
|
||||
// contains Link display list `gCullBackDList`. If an actor is drawn between player and shield
|
||||
// that uses segment 12 (such as Jabu-Jabu tentacles), the game will crash on Deku Shield drop.
|
||||
// Fix: Re-set segment 12 to the required display list.
|
||||
void RegisterFixDekuShieldDropCrash() {
|
||||
COND_VB_SHOULD(VB_ITEMSHIELD_DRAW, true, {
|
||||
GraphicsContext* __gfxCtx = gPlayState->state.gfxCtx;
|
||||
gSPSegment(POLY_OPA_DISP++, 0x0C, (uintptr_t)SEGMENTED_TO_VIRTUAL(gCullBackDList));
|
||||
});
|
||||
}
|
||||
|
||||
// Vanilla bug: If Hookshot doesn't spawn, player is softlocked. (eg. use as child, no memory left)
|
||||
// Fix: Change item to none if no spawn. (Ranged weapon state is removed by `Player_InitItemAction`)
|
||||
void RegisterPreventHookshotNoSpawnSoftlock() {
|
||||
@@ -45,5 +59,6 @@ void RegisterPreventHookshotParentSoftlock() {
|
||||
}
|
||||
|
||||
static RegisterShipInitFunc initFuncFixOutsideTotCrash(RegisterFixOutsideTotCrash, { "" });
|
||||
static RegisterShipInitFunc initFuncFixDekuShieldDropCrash(RegisterFixDekuShieldDropCrash, { "" });
|
||||
static RegisterShipInitFunc initFuncHookshotNospawnSoftlock(RegisterPreventHookshotNoSpawnSoftlock, { "" });
|
||||
static RegisterShipInitFunc initFuncHookshotParentSoftlock(RegisterPreventHookshotParentSoftlock, { "" });
|
||||
|
||||
@@ -3066,6 +3066,14 @@ typedef enum {
|
||||
// - `*EnItem00`
|
||||
VB_ITEM00_KILL,
|
||||
|
||||
// #### `result`
|
||||
// ```c
|
||||
// true
|
||||
// ```
|
||||
// #### `args`
|
||||
// - none
|
||||
VB_ITEMSHIELD_DRAW,
|
||||
|
||||
// #### `result`
|
||||
// ```c
|
||||
// true
|
||||
|
||||
@@ -7,6 +7,8 @@
|
||||
#include "vt.h"
|
||||
#include "z_item_shield.h"
|
||||
#include "objects/object_link_child/object_link_child.h"
|
||||
#include "soh/Enhancements/game-interactor/GameInteractor.h"
|
||||
#include "soh/Enhancements/game-interactor/GameInteractor_Hooks.h"
|
||||
|
||||
#define FLAGS ACTOR_FLAG_UPDATE_CULLING_DISABLED
|
||||
|
||||
@@ -221,6 +223,7 @@ void ItemShield_Draw(Actor* thisx, PlayState* play) {
|
||||
if (!(this->unk_19C & 2)) {
|
||||
OPEN_DISPS(play->state.gfxCtx);
|
||||
Gfx_SetupDL_25Opa(play->state.gfxCtx);
|
||||
GameInteractor_Should(VB_ITEMSHIELD_DRAW, true);
|
||||
gSPMatrix(POLY_OPA_DISP++, MATRIX_NEWMTX(play->state.gfxCtx), G_MTX_NOPUSH | G_MTX_LOAD | G_MTX_MODELVIEW);
|
||||
gSPDisplayList(POLY_OPA_DISP++, SEGMENTED_TO_VIRTUAL(gLinkChildDekuShieldDL));
|
||||
CLOSE_DISPS(play->state.gfxCtx);
|
||||
|
||||
Reference in New Issue
Block a user