diff --git a/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_64 b/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_64
index 47ca211a96..e33491d5af 100644
Binary files a/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_64 and b/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_64 differ
diff --git a/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_shaded_64 b/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_shaded_64
new file mode 100644
index 0000000000..dca2158b4b
Binary files /dev/null and b/soh/assets/custom/objects/object_xmas_tree/LeavesAlpha_shaded_64 differ
diff --git a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL
index 2bac0e0983..c343cfe2a0 100644
--- a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL
+++ b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL
@@ -3,6 +3,8 @@
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_1 b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_1
index 889e5aa4f5..ff4e066a5b 100644
--- a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_1
+++ b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_1
@@ -1,104 +1,6 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
@@ -112,7 +14,7 @@
-
+
@@ -125,7 +27,93 @@
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_2 b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_2
new file mode 100644
index 0000000000..561d3ac5ef
--- /dev/null
+++ b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_tri_2
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_1 b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_1
index bec46bbab6..01ed88a145 100644
--- a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_1
+++ b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_1
@@ -1,39 +1,10 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
@@ -44,12 +15,12 @@
+
+
-
-
@@ -60,12 +31,12 @@
+
+
-
-
@@ -79,9 +50,7 @@
-
-
@@ -94,10 +63,10 @@
-
-
+
+
@@ -110,10 +79,10 @@
-
-
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_2 b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_2
new file mode 100644
index 0000000000..fd03778f89
--- /dev/null
+++ b/soh/assets/custom/objects/object_xmas_tree/gXmasTreeDL_vtx_2
@@ -0,0 +1,29 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeGreen b/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeGreen
index 69c9c11e5f..119341c701 100644
--- a/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeGreen
+++ b/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeGreen
@@ -1,20 +1,21 @@
-
+
-
+
-
+
+
diff --git a/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeTip b/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeTip
new file mode 100644
index 0000000000..9baaadbf55
--- /dev/null
+++ b/soh/assets/custom/objects/object_xmas_tree/mat_gXmasTreeDL_f3dlite_TreeTip
@@ -0,0 +1,21 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/soh/soh/Enhancements/debugger/debugSaveEditor.cpp b/soh/soh/Enhancements/debugger/debugSaveEditor.cpp
index 2762b5a1b0..b357363ac9 100644
--- a/soh/soh/Enhancements/debugger/debugSaveEditor.cpp
+++ b/soh/soh/Enhancements/debugger/debugSaveEditor.cpp
@@ -517,11 +517,6 @@ void DrawInfoTab() {
if (IS_RANDO && OTRGlobals::Instance->gRandomizer->GetRandoSettingValue(RSK_TRIFORCE_HUNT)) {
ImGui::InputScalar("Triforce Pieces", ImGuiDataType_U8, &gSaveContext.triforcePiecesCollected);
UIWidgets::InsertHelpHoverText("Currently obtained Triforce Pieces. For Triforce Hunt.");
-
- bool thFlag = gSaveContext.grantBossKey != 0;
- if (ImGui::Checkbox("Finished Triforce Hunt", &thFlag)) {
- gSaveContext.grantBossKey = thFlag;
- }
}
ImGui::PushItemWidth(ImGui::GetFontSize() * 10);
diff --git a/soh/soh/Enhancements/debugger/debugSaveEditor.h b/soh/soh/Enhancements/debugger/debugSaveEditor.h
index 42c9c91c0f..01557efefe 100644
--- a/soh/soh/Enhancements/debugger/debugSaveEditor.h
+++ b/soh/soh/Enhancements/debugger/debugSaveEditor.h
@@ -505,6 +505,7 @@ const std::vector flagTables = {
{ RAND_INF_CHILD_FISHING, "RAND_INF_CHILD_FISHING" },
{ RAND_INF_ADULT_FISHING, "RAND_INF_ADULT_FISHING" },
{ RAND_INF_10_BIG_POES, "RAND_INF_10_BIG_POES" },
+ { RAND_INF_GRANT_GANONS_BOSSKEY, "RAND_INF_GRANT_GANONS_BOSSKEY" },
} },
};
diff --git a/soh/soh/Enhancements/mods.cpp b/soh/soh/Enhancements/mods.cpp
index 9bb8aefb23..f4b62363d4 100644
--- a/soh/soh/Enhancements/mods.cpp
+++ b/soh/soh/Enhancements/mods.cpp
@@ -665,13 +665,6 @@ void RegisterTriforceHunt() {
triforcePieceScale = 0.0f;
GameInteractor::State::TriforceHuntPieceGiven = 0;
}
-
- // Give Boss Key when player loads back into the savefile.
- if (gSaveContext.grantBossKey &&
- (1 << 0 & gSaveContext.inventory.dungeonItems[SCENE_GANONS_TOWER]) == 0) {
- GetItemEntry getItemEntry = ItemTableManager::Instance->RetrieveItemEntry(MOD_RANDOMIZER, RG_GANONS_CASTLE_BOSS_KEY);
- GiveItemEntryWithoutActor(gPlayState, getItemEntry);
- }
}
if (currentPieces >= requiredPieces && eventTimer >= 1 && eventTimer <= 30) {
@@ -711,6 +704,18 @@ void RegisterTriforceHunt() {
});
}
+void RegisterGrantGanonsBossKey() {
+ GameInteractor::Instance->RegisterGameHook([]() {
+ // Triforce Hunt needs the check if the player isn't being teleported to the credits scene.
+ if (!GameInteractor::IsGameplayPaused() && Flags_GetRandomizerInf(RAND_INF_GRANT_GANONS_BOSSKEY) &&
+ gPlayState->sceneLoadFlag != 0x14 && (1 << 0 & gSaveContext.inventory.dungeonItems[SCENE_GANONS_TOWER]) == 0) {
+ GetItemEntry getItemEntry =
+ ItemTableManager::Instance->RetrieveItemEntry(MOD_RANDOMIZER, RG_GANONS_CASTLE_BOSS_KEY);
+ GiveItemEntryWithoutActor(gPlayState, getItemEntry);
+ }
+ });
+}
+
//this map is used for enemies that can be uniquely identified by their id
//and that are always counted
//enemies that can't be uniquely identified by their id
@@ -1096,6 +1101,7 @@ void InitMods() {
RegisterMenuPathFix();
RegisterMirrorModeHandler();
RegisterTriforceHunt();
+ RegisterGrantGanonsBossKey();
RegisterEnemyDefeatCounts();
RegisterAltTrapTypes();
RegisterRandomizerSheikSpawn();
diff --git a/soh/soh/Enhancements/randomizer/randomizer_inf.h b/soh/soh/Enhancements/randomizer/randomizer_inf.h
index 33c206b470..8d4ec98012 100644
--- a/soh/soh/Enhancements/randomizer/randomizer_inf.h
+++ b/soh/soh/Enhancements/randomizer/randomizer_inf.h
@@ -159,6 +159,7 @@ typedef enum {
RAND_INF_CHILD_FISHING,
RAND_INF_ADULT_FISHING,
RAND_INF_10_BIG_POES,
+ RAND_INF_GRANT_GANONS_BOSSKEY,
// If you add anything to this list, you need to update the size of randomizerInf in z64save.h to be ceil(RAND_INF_MAX / 16)
diff --git a/soh/src/overlays/actors/ovl_En_ChristmasTree/z_en_christmastree.c b/soh/src/overlays/actors/ovl_En_ChristmasTree/z_en_christmastree.c
index fdc58fb27d..9d9f65190b 100644
--- a/soh/src/overlays/actors/ovl_En_ChristmasTree/z_en_christmastree.c
+++ b/soh/src/overlays/actors/ovl_En_ChristmasTree/z_en_christmastree.c
@@ -77,7 +77,7 @@ void EnChristmasTree_Talk(EnChristmasTree* this, PlayState* play) {
if (gSaveContext.triforcePiecesCollected >= Randomizer_GetSettingValue(RSK_TRIFORCE_HUNT_PIECES_REQUIRED)) {
gSaveContext.sohStats.itemTimestamp[TIMESTAMP_TRIFORCE_COMPLETED] = GAMEPLAYSTAT_TOTAL_TIME;
gSaveContext.sohStats.gameComplete = 1;
- gSaveContext.grantBossKey = 1;
+ Flags_SetRandomizerInf(RAND_INF_GRANT_GANONS_BOSSKEY);
Play_PerformSave(play);
GameInteractor_SetTriforceHuntCreditsWarpActive(true);
}