diff --git a/libultraship/libultraship/Lib/Fast3D/gfx_dxgi.cpp b/libultraship/libultraship/Lib/Fast3D/gfx_dxgi.cpp index 1f2517c77..c74322e88 100644 --- a/libultraship/libultraship/Lib/Fast3D/gfx_dxgi.cpp +++ b/libultraship/libultraship/Lib/Fast3D/gfx_dxgi.cpp @@ -31,6 +31,7 @@ #define DECLARE_GFX_DXGI_FUNCTIONS #include "gfx_dxgi.h" +#include "../../GameSettings.h" #define WINCLASS_NAME L"N64GAME" #define GFX_API_NAME "DirectX" @@ -271,8 +272,9 @@ static LRESULT CALLBACK gfx_dxgi_wnd_proc(HWND h_wnd, UINT message, WPARAM w_par break; case WM_DROPFILES: DragQueryFileA((HDROP)w_param, 0, fileName, 256); - CVar_SetString("gDroppedFile", fileName); + CVar_SetString("gSpoilerLog", fileName); CVar_SetS32("gDroppedNewSpoilerFile", 1); + Game::SaveSettings(); break; case WM_SYSKEYDOWN: if ((w_param == VK_RETURN) && ((l_param & 1 << 30) == 0)) { diff --git a/libultraship/libultraship/Lib/Fast3D/gfx_sdl2.cpp b/libultraship/libultraship/Lib/Fast3D/gfx_sdl2.cpp index 637c1937c..4a866c68a 100644 --- a/libultraship/libultraship/Lib/Fast3D/gfx_sdl2.cpp +++ b/libultraship/libultraship/Lib/Fast3D/gfx_sdl2.cpp @@ -28,6 +28,7 @@ #include #endif #include +#include "../../GameSettings.h" #define GFX_API_NAME "SDL2 - OpenGL" @@ -252,8 +253,9 @@ static void gfx_sdl_handle_events(void) { } break; case SDL_DROPFILE: - CVar_SetString("gDroppedFile", event.drop.file); + CVar_SetString("gSpoilerLog", event.drop.file); CVar_SetS32("gDroppedNewSpoilerFile", 1); + Game::SaveSettings(); break; case SDL_QUIT: SDL_Quit(); // bandaid fix for linux window closing issue diff --git a/libultraship/libultraship/SohImGuiImpl.cpp b/libultraship/libultraship/SohImGuiImpl.cpp index 48958193e..860aab64d 100644 --- a/libultraship/libultraship/SohImGuiImpl.cpp +++ b/libultraship/libultraship/SohImGuiImpl.cpp @@ -1035,10 +1035,9 @@ namespace SohImGui { { EnhancementCheckbox("Enable Randomizer", "gRandomizer"); - if (ImGui::Button("Generate Seed") && CVar_GetS32("gRandomizer", 0) != 0) { + if (ImGui::Button("Generate Seed")) { RandoMain::GenerateRando(); - // gSpoilerData = GetSpoilerData(); - // ParseItemLocations(gSpoilerData); + Game::LoadSettings(); } ImGui::EndMenu(); diff --git a/soh/include/functions.h b/soh/include/functions.h index 4631cdb92..de2569ed1 100644 --- a/soh/include/functions.h +++ b/soh/include/functions.h @@ -446,6 +446,7 @@ u32 Actor_TextboxIsClosing(Actor* actor, GlobalContext* globalCtx); s8 func_8002F368(GlobalContext* globalCtx); void Actor_GetScreenPos(GlobalContext* globalCtx, Actor* actor, s16* x, s16* y); u32 Actor_HasParent(Actor* actor, GlobalContext* globalCtx); +s32 GiveItemWithoutActor(GlobalContext* globalCtx, s32 getItemId); s32 func_8002F434(Actor* actor, GlobalContext* globalCtx, s32 getItemId, f32 xzRange, f32 yRange); void func_8002F554(Actor* actor, GlobalContext* globalCtx, s32 getItemId); void func_8002F580(Actor* actor, GlobalContext* globalCtx); diff --git a/soh/include/randomizer/rando_main.cpp b/soh/include/randomizer/rando_main.cpp index 7afc1deac..fc47e1ebd 100644 --- a/soh/include/randomizer/rando_main.cpp +++ b/soh/include/randomizer/rando_main.cpp @@ -17,5 +17,6 @@ void RandoMain::GenerateRando() { std::string fileName = GenerateRandomizer(); CVar_SetString("gSpoilerLog", fileName.c_str()); + CVar_SetS32("gDroppedNewSpoilerFile", 1); Game::SaveSettings(); } \ No newline at end of file diff --git a/soh/soh/Enhancements/randomizer.cpp b/soh/soh/Enhancements/randomizer.cpp index 200b7c7c2..661a63e1a 100644 --- a/soh/soh/Enhancements/randomizer.cpp +++ b/soh/soh/Enhancements/randomizer.cpp @@ -1119,14 +1119,14 @@ void Randomizer::LoadItemLocations(const char* spoilerFileName) { for (auto itemLocation : gSaveContext.itemLocations) { this->itemLocations[itemLocation.check] = itemLocation.get; } - } else { + } /* else { u16 index = 0; for (auto itemLocation : this->itemLocations) { gSaveContext.itemLocations[index].check = itemLocation.first; gSaveContext.itemLocations[index].get = itemLocation.second; index++; } - } + }*/ } std::string sanitize(std::string stringValue) { @@ -1149,8 +1149,6 @@ std::string sanitize(std::string stringValue) { } void Randomizer::ParseItemLocationsFile(const char* spoilerFileName) { - // todo pull this in from cvar or something - std::ifstream spoilerFileStream(sanitize(spoilerFileName)); if (!spoilerFileStream) return; @@ -1197,7 +1195,6 @@ void Randomizer::ParseItemLocationsFile(const char* spoilerFileName) { } if (success) { - CVar_SetS32("gRandomizer", 1); CVar_SetS32("gDroppedNewSpoilerFile", 0); Game::SaveSettings(); } @@ -1372,6 +1369,13 @@ GetItemID Randomizer::GetItemFromGet(RandomizerGet randoGet, GetItemID ogItemId) case 1: return GI_WALLET_GIANT; } + case RG_PROGRESSIVE_OCARINA: + switch (INV_CONTENT(ITEM_OCARINA_FAIRY) == ITEM_NONE) { + case 1: + return GI_OCARINA_FAIRY; + case 0: + return GI_OCARINA_OOT; + } case RG_RECOVERY_HEART: return GI_HEART; case RG_GREEN_RUPEE: diff --git a/soh/src/code/z_actor.c b/soh/src/code/z_actor.c index bdb2fe78c..0e5b960f6 100644 --- a/soh/src/code/z_actor.c +++ b/soh/src/code/z_actor.c @@ -1923,6 +1923,24 @@ u32 Actor_HasParent(Actor* actor, GlobalContext* globalCtx) { } } +s32 GiveItemWithoutActor(GlobalContext* globalCtx, s32 getItemId) { + Player* player = GET_PLAYER(globalCtx); + + if (!(player->stateFlags1 & 0x3C7080) && Player_GetExplosiveHeld(player) < 0) { + if (((player->heldActor != NULL) && (getItemId > GI_NONE) && (getItemId < GI_MAX)) || + (!(player->stateFlags1 & 0x20000800))) { + if ((getItemId != GI_NONE)) { + player->getItemId = getItemId; + player->interactRangeActor = &player->actor; + player->getItemDirection = player->actor.shape.rot.y; + return true; + } + } + } + + return false; +} + s32 func_8002F434(Actor* actor, GlobalContext* globalCtx, s32 getItemId, f32 xzRange, f32 yRange) { Player* player = GET_PLAYER(globalCtx); diff --git a/soh/src/code/z_demo.c b/soh/src/code/z_demo.c index 43da57efc..275ab3c57 100644 --- a/soh/src/code/z_demo.c +++ b/soh/src/code/z_demo.c @@ -2090,10 +2090,12 @@ void Cutscene_HandleConditionalTriggers(GlobalContext* globalCtx) { Flags_SetEventChkInf(0xAA); gSaveContext.cutsceneIndex = 0xFFF0; } else if ((gSaveContext.entranceIndex == 0x05E0) && !Flags_GetEventChkInf(0xC1)) { - Flags_SetEventChkInf(0xC1); - Item_Give(globalCtx, ITEM_OCARINA_FAIRY); - gSaveContext.entranceIndex = 0x011E; - gSaveContext.cutsceneIndex = 0xFFF0; + if (!gSaveContext.n64ddFlag) { + Flags_SetEventChkInf(0xC1); + Item_Give(globalCtx, ITEM_OCARINA_FAIRY); + gSaveContext.entranceIndex = 0x011E; + gSaveContext.cutsceneIndex = 0xFFF0; + } } else if (CHECK_QUEST_ITEM(QUEST_MEDALLION_SPIRIT) && CHECK_QUEST_ITEM(QUEST_MEDALLION_SHADOW) && LINK_IS_ADULT && !Flags_GetEventChkInf(0xC4) && (gEntranceTable[((void)0, gSaveContext.entranceIndex)].scene == SCENE_TOKINOMA)) { diff --git a/soh/src/code/z_play.c b/soh/src/code/z_play.c index f0ccc2f15..3ad63512a 100644 --- a/soh/src/code/z_play.c +++ b/soh/src/code/z_play.c @@ -193,53 +193,14 @@ void Gameplay_Destroy(GameState* thisx) { gGlobalCtx = NULL; } -void GiveLinksPocketMedallion() { - GetItemID getItemId = GetRandomizedItemIdFromKnownCheck(RC_LINKS_POCKET, RG_NONE); +void GivePlayerRandoRewardSariaGift(GlobalContext* globalCtx, RandomizerCheck check) { + Player* player = GET_PLAYER(globalCtx); + GetItemID getItemId = GetRandomizedItemIdFromKnownCheck(check, GI_ZELDAS_LULLABY); - s16 item; - - u8 medallion = 0; - - switch (getItemId) { - case GI_MEDALLION_FOREST: - item = ITEM_MEDALLION_FOREST; - medallion = 1; - break; - case GI_MEDALLION_FIRE: - item = ITEM_MEDALLION_FIRE; - medallion = 1; - break; - case GI_MEDALLION_WATER: - item = ITEM_MEDALLION_WATER; - medallion = 1; - break; - case GI_MEDALLION_SHADOW: - item = ITEM_MEDALLION_SHADOW; - medallion = 1; - break; - case GI_MEDALLION_SPIRIT: - item = ITEM_MEDALLION_SPIRIT; - medallion = 1; - break; - case GI_MEDALLION_LIGHT: - item = ITEM_MEDALLION_LIGHT; - medallion = 1; - break; - case GI_STONE_KOKIRI: - item = ITEM_KOKIRI_EMERALD; - break; - case GI_STONE_GORON: - item = ITEM_GORON_RUBY; - break; - case GI_STONE_ZORA: - item = ITEM_ZORA_SAPPHIRE; - break; - } - - if (medallion == 1) { - gSaveContext.inventory.questItems |= gBitFlags[item - ITEM_MEDALLION_FOREST + QUEST_MEDALLION_FOREST]; - } else { - gSaveContext.inventory.questItems |= gBitFlags[item - ITEM_KOKIRI_EMERALD + QUEST_KOKIRI_EMERALD]; + if (gSaveContext.entranceIndex == 0x05E0 && !Flags_GetEventChkInf(0xC1) && player != NULL && + !Player_InBlockingCsMode(globalCtx, player)) { + GiveItemWithoutActor(globalCtx, getItemId); + Flags_SetEventChkInf(0xC1); } } @@ -1095,6 +1056,8 @@ skip: Environment_Update(globalCtx, &globalCtx->envCtx, &globalCtx->lightCtx, &globalCtx->pauseCtx, &globalCtx->msgCtx, &globalCtx->gameOverCtx, globalCtx->state.gfxCtx); + + GivePlayerRandoRewardSariaGift(globalCtx, RC_LW_GIFT_FROM_SARIA); } void Gameplay_DrawOverlayElements(GlobalContext* globalCtx) { diff --git a/soh/src/code/z_sram.c b/soh/src/code/z_sram.c index b184c7871..a16808ce2 100644 --- a/soh/src/code/z_sram.c +++ b/soh/src/code/z_sram.c @@ -676,6 +676,56 @@ void Sram_VerifyAndLoadAllSaves(FileChooseContext* fileChooseCtx, SramContext* s osSyncPrintf("now_life=%d, %d, %d\n", fileChooseCtx->health[0], fileChooseCtx->health[1], fileChooseCtx->health[2]); } +void GiveLinksPocketMedallion() { + GetItemID getItemId = GetRandomizedItemIdFromKnownCheck(RC_LINKS_POCKET, RG_NONE); + + s16 item; + + u8 medallion = 0; + + switch (getItemId) { + case GI_MEDALLION_FOREST: + item = ITEM_MEDALLION_FOREST; + medallion = 1; + break; + case GI_MEDALLION_FIRE: + item = ITEM_MEDALLION_FIRE; + medallion = 1; + break; + case GI_MEDALLION_WATER: + item = ITEM_MEDALLION_WATER; + medallion = 1; + break; + case GI_MEDALLION_SHADOW: + item = ITEM_MEDALLION_SHADOW; + medallion = 1; + break; + case GI_MEDALLION_SPIRIT: + item = ITEM_MEDALLION_SPIRIT; + medallion = 1; + break; + case GI_MEDALLION_LIGHT: + item = ITEM_MEDALLION_LIGHT; + medallion = 1; + break; + case GI_STONE_KOKIRI: + item = ITEM_KOKIRI_EMERALD; + break; + case GI_STONE_GORON: + item = ITEM_GORON_RUBY; + break; + case GI_STONE_ZORA: + item = ITEM_ZORA_SAPPHIRE; + break; + } + + if (medallion == 1) { + gSaveContext.inventory.questItems |= gBitFlags[item - ITEM_MEDALLION_FOREST + QUEST_MEDALLION_FOREST]; + } else { + gSaveContext.inventory.questItems |= gBitFlags[item - ITEM_KOKIRI_EMERALD + QUEST_KOKIRI_EMERALD]; + } +} + void Sram_InitSave(FileChooseContext* fileChooseCtx, SramContext* sramCtx) { u16 offset; u16 j; @@ -713,10 +763,21 @@ void Sram_InitSave(FileChooseContext* fileChooseCtx, SramContext* sramCtx) { osSyncPrintf("newf=%x,%x,%x,%x,%x,%x\n", gSaveContext.newf[0], gSaveContext.newf[1], gSaveContext.newf[2], gSaveContext.newf[3], gSaveContext.newf[4], gSaveContext.newf[5]); osSyncPrintf("\n$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$$\n"); - - if (gSaveContext.n64ddFlag) { - GiveLinksPocketMedallion(); + + // If the save file is a randomizer one + if (CVar_GetS32("gRandomizer", 0) != 0) { + // Set N64DD Flags for save file + fileChooseCtx->n64ddFlags[fileChooseCtx->buttonIndex] = 1; + fileChooseCtx->n64ddFlag = 1; + gSaveContext.n64ddFlag = 1; + + // Set Cutscene flags to skip them + gSaveContext.infTable[0] |= 1; gSaveContext.cutsceneIndex = 0; + Flags_SetEventChkInf(5); + + // Give Link's pocket item + GiveLinksPocketMedallion(); } ptr = (u16*)&gSaveContext; diff --git a/soh/src/overlays/actors/ovl_En_Ma1/z_en_ma1.c b/soh/src/overlays/actors/ovl_En_Ma1/z_en_ma1.c index 2b1fb9c97..afaa3a36c 100644 --- a/soh/src/overlays/actors/ovl_En_Ma1/z_en_ma1.c +++ b/soh/src/overlays/actors/ovl_En_Ma1/z_en_ma1.c @@ -273,8 +273,10 @@ void EnMa1_Init(Actor* thisx, GlobalContext* globalCtx) { Collider_SetCylinder(globalCtx, &this->collider, &this->actor, &sCylinderInit); CollisionCheck_SetInfo2(&this->actor.colChkInfo, DamageTable_Get(22), &sColChkInfoInit); - if (gSaveContext.n64ddFlag) { + if (gSaveContext.n64ddFlag) { // Skip Malon's multiple textboxes before getting an item gSaveContext.infTable[8] |= 0x800; + gSaveContext.infTable[8] |= 0x10; + gSaveContext.eventChkInf[1] |= 1; } if (!func_80AA08C4(this, globalCtx)) { @@ -287,11 +289,11 @@ void EnMa1_Init(Actor* thisx, GlobalContext* globalCtx) { this->actor.targetMode = 6; this->unk_1E8.unk_00 = 0; - if (!(gSaveContext.eventChkInf[1] & 0x10) || CHECK_QUEST_ITEM(QUEST_SONG_EPONA)) { + if (!(gSaveContext.eventChkInf[1] & 0x10) || (CHECK_QUEST_ITEM(QUEST_SONG_EPONA) && !gSaveContext.n64ddFlag)) { this->actionFunc = func_80AA0D88; EnMa1_ChangeAnim(this, ENMA1_ANIM_2); } else { - if (gSaveContext.n64ddFlag) { // Straight to singing textbox + if (gSaveContext.n64ddFlag) { // Skip straight to "let's sing it together" textbox in the ranch gSaveContext.eventChkInf[1] |= 0x40; } @@ -320,8 +322,7 @@ void func_80AA0D88(EnMa1* this, GlobalContext* globalCtx) { if ((globalCtx->sceneNum == SCENE_SPOT15) && (gSaveContext.eventChkInf[1] & 0x10)) { Actor_Kill(&this->actor); - } else if (!(gSaveContext.eventChkInf[1] & 0x10) || CHECK_QUEST_ITEM(QUEST_SONG_EPONA) || - (gSaveContext.n64ddFlag && Flags_GetTreasure(globalCtx, 0x1F))) { + } else if (!(gSaveContext.eventChkInf[1] & 0x10) || (CHECK_QUEST_ITEM(QUEST_SONG_EPONA) && !gSaveContext.n64ddFlag)) { if (this->unk_1E8.unk_00 == 2) { this->actionFunc = func_80AA0EA0; globalCtx->msgCtx.stateTimer = 4; diff --git a/soh/src/overlays/actors/ovl_En_Owl/z_en_owl.c b/soh/src/overlays/actors/ovl_En_Owl/z_en_owl.c index aef838499..fcace47f1 100644 --- a/soh/src/overlays/actors/ovl_En_Owl/z_en_owl.c +++ b/soh/src/overlays/actors/ovl_En_Owl/z_en_owl.c @@ -136,7 +136,7 @@ void EnOwl_Init(Actor* thisx, GlobalContext* globalCtx) { // "conversation owl %4x no = %d, sv = %d" osSyncPrintf(VT_FGCOL(CYAN) " 会話フクロウ %4x no = %d, sv = %d\n" VT_RST, this->actor.params, owlType, switchFlag); - if ((owlType != OWL_DEFAULT) && (switchFlag < 0x20) && Flags_GetSwitch(globalCtx, switchFlag)) { + if (((owlType != OWL_DEFAULT) && (switchFlag < 0x20) && Flags_GetSwitch(globalCtx, switchFlag)) || gSaveContext.n64ddFlag) { osSyncPrintf("savebitでフクロウ退避\n"); // "Save owl with savebit" Actor_Kill(&this->actor); return; diff --git a/soh/src/overlays/gamestates/ovl_file_choose/z_file_choose.c b/soh/src/overlays/gamestates/ovl_file_choose/z_file_choose.c index f0f31b609..e0b9fc2fb 100644 --- a/soh/src/overlays/gamestates/ovl_file_choose/z_file_choose.c +++ b/soh/src/overlays/gamestates/ovl_file_choose/z_file_choose.c @@ -234,6 +234,11 @@ void FileChoose_UpdateMainMenu(GameState* thisx) { Input* input = &this->state.input[0]; bool dpad = CVar_GetS32("gDpadPauseName", 0); + if (CVar_GetS32("gDroppedNewSpoilerFile", 0) != 0) { + const char* fileLoc = CVar_GetString("gSpoilerLog", ""); + LoadItemLocations(fileLoc); + } + if (CHECK_BTN_ALL(input->press.button, BTN_START) || CHECK_BTN_ALL(input->press.button, BTN_A)) { if (this->buttonIndex <= FS_BTN_MAIN_FILE_3) { osSyncPrintf("REGCK_ALL[%x]=%x,%x,%x,%x,%x,%x\n", this->buttonIndex, @@ -1534,9 +1539,6 @@ void FileChoose_LoadGame(GameState* thisx) { this->state.running = false; } - const char* fileLoc = CVar_GetString("gSpoilerLog", ""); - LoadItemLocations(fileLoc); - gSaveContext.respawn[0].entranceIndex = -1; gSaveContext.respawnFlag = 0; gSaveContext.seqId = (u8)NA_BGM_DISABLED; @@ -1959,6 +1961,9 @@ void FileChoose_Init(GameState* thisx) { size_t size = (u32)_title_staticSegmentRomEnd - (u32)_title_staticSegmentRomStart; s32 pad; + const char* fileLoc = CVar_GetString("gSpoilerLog", ""); + LoadItemLocations(fileLoc); + SREG(30) = 1; osSyncPrintf("SIZE=%x\n", size); diff --git a/soh/src/overlays/gamestates/ovl_file_choose/z_file_nameset_PAL.c b/soh/src/overlays/gamestates/ovl_file_choose/z_file_nameset_PAL.c index c36ee957a..3d1b3b004 100644 --- a/soh/src/overlays/gamestates/ovl_file_choose/z_file_nameset_PAL.c +++ b/soh/src/overlays/gamestates/ovl_file_choose/z_file_nameset_PAL.c @@ -441,18 +441,10 @@ void FileChoose_DrawNameEntry(GameState* thisx) { this->n64ddFlag = 0; - if (CVar_GetS32("gRandomizer", 0) != 0) { - this->n64ddFlags[this->buttonIndex] = 1; - this->n64ddFlag = 1; - gSaveContext.n64ddFlag = 1; - } - dayTime = ((void)0, gSaveContext.dayTime); Sram_InitSave(this, &this->sramCtx); - // todo: fill link's pocket here - gSaveContext.dayTime = dayTime; this->configMode = CM_NAME_ENTRY_TO_MAIN; this->nameBoxAlpha[this->buttonIndex] = this->nameAlpha[this->buttonIndex] = 200;