diff --git a/code/mm.ld b/code/mm.ld index 83781cc3..a9e2b2ee 100644 --- a/code/mm.ld +++ b/code/mm.ld @@ -67,7 +67,7 @@ SECTIONS{ *(.patch_DoNotRemoveKeys) } - .patch_DoNotGiveSwordBackOnReset 0x1C98FC : { + .patch_DoNotGiveSwordBackOnReset 0x1C98DC : { *(.patch_DoNotGiveSwordBackOnReset) } @@ -75,6 +75,10 @@ SECTIONS{ *(.patch_RemoveItemBUsabilityOnReset) } + .patch_RemoveSwordFlagsOnReset 0x1C9900 : { + *(.patch_RemoveSwordFlagsOnReset) + } + .patch_RemoveDekuMaskCheckSoT 0x1D8008 : { *(.patch_RemoveDekuMaskCheckSoT) } @@ -163,6 +167,10 @@ SECTIONS{ *(.patch_SecondZoraSwimCheck) } + .patch_ForceSwordUpgradeOnHuman 0x233D88 : { + *(.patch_ForceSwordUpgradeOnHuman) + } + .patch_CheckDungeonItems 0x233F30 : { *(.patch_CheckDungeonItems) } diff --git a/code/source/asm/hooks.s b/code/source/asm/hooks.s index 343b0841..5e9acb66 100644 --- a/code/source/asm/hooks.s +++ b/code/source/asm/hooks.s @@ -78,6 +78,21 @@ hook_ChangeSOHToCustomText: pop {r0-r2, lr} b 0x186814 +.global hook_DoNotGiveSwordBackOnReset +hook_DoNotGiveSwordBackOnReset: + bhi 0x1C9958 @ original instruction, if gilded sword ignore these. + push {r0-r12, lr} + bl SongOfTimeSwordPlacement @ See rnd/link.cpp + pop {r0-r12, lr} + bx lr + +.global hook_DoNotGiveSwordBackOnResetTwo +hook_DoNotGiveSwordBackOnResetTwo: + push {r0-r12, lr} + bl SongOfTimeSwordPlacement @ See rnd/link.cpp + pop {r0-r12, lr} + bx lr + .global hook_SpawnFastElegyStatues hook_SpawnFastElegyStatues: push {r0-r12, lr} diff --git a/code/source/asm/patches.s b/code/source/asm/patches.s index 08250c90..c6b2b0c0 100644 --- a/code/source/asm/patches.s +++ b/code/source/asm/patches.s @@ -115,13 +115,16 @@ patch_DoNotRemoveKeys: .section .patch_DoNotGiveSwordBackOnReset .global patch_DoNotGiveSwordBackOnReset patch_DoNotGiveSwordBackOnReset: - nop - nop - nop + bl hook_DoNotGiveSwordBackOnReset .section .patch_RemoveItemBUsabilityOnReset .global patch_RemoveItemBUsabilityOnReset patch_RemoveItemBUsabilityOnReset: + bl hook_DoNotGiveSwordBackOnResetTwo + +.section .patch_RemoveSwordFlagsOnReset +.global patch_RemoveSwordFlagsOnReset +patch_RemoveSwordFlagsOnReset: nop .section .patch_RemoveDekuMaskCheckSoT @@ -145,6 +148,11 @@ patch_SpawnFastElegyStatues: patch_CheckCurrentInventoryOverrideItem: b hook_CheckCurrentInventory +.section .patch_ForceSwordUpgradeOnHuman +.global patch_ForceSwordUpgradeOnHuman +patch_ForceSwordUpgradeOnHuman: + mov r0,#0x0 + .section .patch_CheckDungeonItems .global patch_CheckDungeonItems patch_CheckDungeonItems: diff --git a/code/source/rnd/item_effect.cpp b/code/source/rnd/item_effect.cpp index da8c2b4e..d1204cab 100644 --- a/code/source/rnd/item_effect.cpp +++ b/code/source/rnd/item_effect.cpp @@ -41,10 +41,12 @@ namespace rnd { } comData->save.player.razor_sword_hp = 100; // Set to 100 hits. Maybe randomize? comData->save.equipment.sword_shield.sword = game::SwordType::RazorSword; // Set sword to razor. + comData->save.equipment.data[0].item_btn_b = game::ItemId::RazorSword; } void ItemEffect_GiveGildedSword(game::CommonData* comData, s16 arg1, s16 arg2) { comData->save.equipment.sword_shield.sword = game::SwordType::GildedSword; // Set sword to gilded. + comData->save.equipment.data[0].item_btn_b = game::ItemId::GildedSword; } void ItemEffect_GiveBottle(game::CommonData* comData, s16 bottleItemId, s16 arg2) { diff --git a/code/source/rnd/item_override.cpp b/code/source/rnd/item_override.cpp index fb4ae16b..0cd4203b 100644 --- a/code/source/rnd/item_override.cpp +++ b/code/source/rnd/item_override.cpp @@ -42,10 +42,10 @@ namespace rnd { rItemOverrides[0].key.type = ItemOverride_Type::OVR_COLLECTABLE; rItemOverrides[0].value.getItemId = 0x26; rItemOverrides[0].value.looksLikeItemId = 0x26; - rItemOverrides[1].key.scene = 0x26; + rItemOverrides[1].key.scene = 0x38; rItemOverrides[1].key.type = ItemOverride_Type::OVR_COLLECTABLE; - rItemOverrides[1].value.getItemId = 0xB9; - rItemOverrides[1].value.looksLikeItemId = 0xB9; + rItemOverrides[1].value.getItemId = 0x38; + rItemOverrides[1].value.looksLikeItemId = 0x38; rItemOverrides[2].key.scene = 0x12; rItemOverrides[2].key.type = ItemOverride_Type::OVR_COLLECTABLE; rItemOverrides[2].value.getItemId = 0x37; diff --git a/code/source/rnd/link.cpp b/code/source/rnd/link.cpp index c50ed555..4b39ed6c 100644 --- a/code/source/rnd/link.cpp +++ b/code/source/rnd/link.cpp @@ -292,6 +292,31 @@ namespace rnd::link { game::SaveData& saveData = game::GetCommonData().save; return static_cast(saveData.inventory.masks[17]); } + + void SongOfTimeSwordPlacement() { + game::SaveData& saveData = game::GetCommonData().save; + if (gSettingsContext.startingKokiriSword == (u8)StartingSwordSetting::STARTINGSWORD_NONE && + saveData.equipment.sword_shield.sword == game::SwordType::NoSword) { + return; + } + +#if defined ENABLE_DEBUG || defined DEBUG_PRINT + rnd::util::Print("%s: Sword is %u and starting sword is %u\n", __func__, saveData.equipment.sword_shield.sword, + gSettingsContext.startingKokiriSword); +#endif + // Check sword/shield flag to see what sword to give back. Once we do that, set the form[0] of player + // equipment to that sword and return. + if (saveData.equipment.sword_shield.sword == game::SwordType::NoSword && + gSettingsContext.startingKokiriSword == (u8)StartingSwordSetting::STARTINGSWORD_KOKIRI) { + saveData.equipment.data[0].item_btn_b = game::ItemId::KokiriSword; + saveData.equipment.sword_shield.sword = game::SwordType::KokiriSword; + } else if (saveData.equipment.sword_shield.sword == game::SwordType::NoSword && + gSettingsContext.startingKokiriSword == (u8)StartingSwordSetting::STARTINGSWORD_RAZOR) { + saveData.equipment.data[0].item_btn_b = game::ItemId::RazorSword; + saveData.equipment.sword_shield.sword = game::SwordType::RazorSword; + } + return; + } } } // namespace rnd::link \ No newline at end of file diff --git a/code/source/rnd/savefile.cpp b/code/source/rnd/savefile.cpp index 7429e996..5b48d0fd 100644 --- a/code/source/rnd/savefile.cpp +++ b/code/source/rnd/savefile.cpp @@ -264,10 +264,10 @@ namespace rnd { if (gSettingsContext.skipBombersMinigame) { // Not sure if bombers code is used elsewhere in the game's code saveData.bomberscode[0] = 0x01; - saveData.bomberscode[1] = 0x01; - saveData.bomberscode[2] = 0x01; - saveData.bomberscode[3] = 0x01; - saveData.bomberscode[4] = 0x01; + saveData.bomberscode[1] = 0x02; + saveData.bomberscode[2] = 0x03; + saveData.bomberscode[3] = 0x04; + saveData.bomberscode[4] = 0x05; saveData.clock_town_temp_flags.bomber_open_hideout = 1; // Currently gets reset by Song of time } @@ -509,7 +509,7 @@ namespace rnd { } if (gSettingsContext.startingKokiriSword == (u8)StartingSwordSetting::STARTINGSWORD_NONE) { equipmentData.sword_shield.sword = game::SwordType::NoSword; - saveData.equipment.data->item_btn_b = game::ItemId::None; + saveData.equipment.data[0].item_btn_b = game::ItemId::None; } else if (gSettingsContext.startingKokiriSword == (u8)StartingSwordSetting::STARTINGSWORD_KOKIRI) { equipmentData.sword_shield.sword = game::SwordType::KokiriSword; saveData.equipment.data[0].item_btn_b = game::ItemId::KokiriSword;