diff --git a/mm/2s2h/GameInteractor/GameInteractor.h b/mm/2s2h/GameInteractor/GameInteractor.h index 84c7e0784d..940fef5084 100644 --- a/mm/2s2h/GameInteractor/GameInteractor.h +++ b/mm/2s2h/GameInteractor/GameInteractor.h @@ -257,13 +257,15 @@ typedef enum { VB_SET_CAMERA_AT_EYE, VB_SET_CAMERA_FOV, VB_USE_ITEM_CONSIDER_ITEM_ACTION, - VB_ENEMY_DROP_COLLECTIBLE, + VB_DROP_COLLECTIBLE, + VB_TREE_DROP_COLLECTIBLE, VB_DRAW_SLIME_RANDO_ITEM, VB_ENABLE_OBJECT_DEPENDENCY, VB_OBJ_MURE2_SET_CHILD_ROOM, VB_OBJ_MURE3_DROP_COLLECTIBLE, VB_SET_PLAYER_CYLINDER_OC_FLAGS, VB_GORON_RACE_RUBBERBANDING, + VB_APPLY_BONK_TO_ACTOR, } GIVanillaBehavior; typedef enum { diff --git a/mm/2s2h/Rando/ActorBehavior/ActorBehavior.cpp b/mm/2s2h/Rando/ActorBehavior/ActorBehavior.cpp index 4689fc867c..7982bc924a 100644 --- a/mm/2s2h/Rando/ActorBehavior/ActorBehavior.cpp +++ b/mm/2s2h/Rando/ActorBehavior/ActorBehavior.cpp @@ -125,6 +125,7 @@ void Rando::ActorBehavior::OnFileLoad() { Rando::ActorBehavior::InitObjMoonStoneBehavior(); Rando::ActorBehavior::InitObjSnowballBehavior(); Rando::ActorBehavior::InitObjTaruBehavior(); + Rando::ActorBehavior::InitObjTreeBehavior(); Rando::ActorBehavior::InitObjTsuboBehavior(); Rando::ActorBehavior::InitObjWarpstoneBehavior(); Rando::ActorBehavior::InitPlayerBehavior(); diff --git a/mm/2s2h/Rando/ActorBehavior/ActorBehavior.h b/mm/2s2h/Rando/ActorBehavior/ActorBehavior.h index 019a08a442..84cc0b0bb3 100644 --- a/mm/2s2h/Rando/ActorBehavior/ActorBehavior.h +++ b/mm/2s2h/Rando/ActorBehavior/ActorBehavior.h @@ -94,6 +94,7 @@ void InitObjGrassBehavior(); void InitObjMoonStoneBehavior(); void InitObjSnowballBehavior(); void InitObjTaruBehavior(); +void InitObjTreeBehavior(); void InitObjTsuboBehavior(); void InitObjWarpstoneBehavior(); void InitPlayerBehavior(); diff --git a/mm/2s2h/Rando/ActorBehavior/EnemyDrops.cpp b/mm/2s2h/Rando/ActorBehavior/EnemyDrops.cpp index ff540678b5..462b2cb790 100644 --- a/mm/2s2h/Rando/ActorBehavior/EnemyDrops.cpp +++ b/mm/2s2h/Rando/ActorBehavior/EnemyDrops.cpp @@ -91,7 +91,7 @@ void SpawnEnemyDrop(Vec3f position, Actor* actor, RandoCheckId randoCheckId) { } void Rando::ActorBehavior::InitEnemyDropBehavior() { - COND_VB_SHOULD(VB_ENEMY_DROP_COLLECTIBLE, IS_RANDO, { + COND_VB_SHOULD(VB_DROP_COLLECTIBLE, IS_RANDO, { Vec3f position = va_arg(args, Vec3f); if (RANDO_SAVE_OPTIONS[RO_SHUFFLE_ENEMY_DROPS] == RO_GENERIC_OFF) { diff --git a/mm/2s2h/Rando/ActorBehavior/ObjTree.cpp b/mm/2s2h/Rando/ActorBehavior/ObjTree.cpp new file mode 100644 index 0000000000..19ec52b514 --- /dev/null +++ b/mm/2s2h/Rando/ActorBehavior/ObjTree.cpp @@ -0,0 +1,239 @@ +#include "ActorBehavior.h" +#include +#include "2s2h/CustomItem/CustomItem.h" +#include "assets/2s2h_assets.h" +#include "2s2h/ObjectExtension/ActorListIndex.h" +#include "2s2h/ShipUtils.h" + +extern "C" { +#include "variables.h" +} + +std::map, RandoCheckId> manInTheTreeRupeeMap = { + { { 3508.0f, 1879.0f }, RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01 }, + { { 3488.0f, 1909.0f }, RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02 }, +}; + +std::map, RandoCheckId> treeActorIdMap = { + // Beneath the Well + { { SCENE_REDEAD, 9, 3 }, RC_BENEATH_THE_WELL_TREE }, + + // Cucco Shack + { { SCENE_F01C, 0, 12 }, RC_CUCCO_SHACK_TREE }, + + // Gorman Track + { { SCENE_KOEPONARACE, 0, 11 }, RC_GORMAN_TRACK_TREE_01 }, + { { SCENE_KOEPONARACE, 0, 12 }, RC_GORMAN_TRACK_TREE_02 }, + { { SCENE_KOEPONARACE, 0, 13 }, RC_GORMAN_TRACK_TREE_03 }, + { { SCENE_KOEPONARACE, 0, 14 }, RC_GORMAN_TRACK_TREE_04 }, + { { SCENE_KOEPONARACE, 0, 15 }, RC_GORMAN_TRACK_TREE_05 }, + { { SCENE_KOEPONARACE, 0, 16 }, RC_GORMAN_TRACK_TREE_06 }, + { { SCENE_KOEPONARACE, 0, 17 }, RC_GORMAN_TRACK_TREE_07 }, + { { SCENE_KOEPONARACE, 0, 18 }, RC_GORMAN_TRACK_TREE_08 }, + { { SCENE_KOEPONARACE, 0, 19 }, RC_GORMAN_TRACK_TREE_09 }, + { { SCENE_KOEPONARACE, 0, 20 }, RC_GORMAN_TRACK_TREE_10 }, + { { SCENE_KOEPONARACE, 0, 21 }, RC_GORMAN_TRACK_TREE_11 }, + { { SCENE_KOEPONARACE, 0, 22 }, RC_GORMAN_TRACK_TREE_12 }, + { { SCENE_KOEPONARACE, 0, 23 }, RC_GORMAN_TRACK_TREE_13 }, + { { SCENE_KOEPONARACE, 0, 24 }, RC_GORMAN_TRACK_TREE_14 }, + { { SCENE_KOEPONARACE, 0, 25 }, RC_GORMAN_TRACK_TREE_15 }, + { { SCENE_KOEPONARACE, 0, 26 }, RC_GORMAN_TRACK_TREE_16 }, + { { SCENE_KOEPONARACE, 0, 27 }, RC_GORMAN_TRACK_TREE_17 }, + { { SCENE_KOEPONARACE, 0, 28 }, RC_GORMAN_TRACK_TREE_18 }, + { { SCENE_KOEPONARACE, 0, 29 }, RC_GORMAN_TRACK_TREE_19 }, + { { SCENE_KOEPONARACE, 0, 30 }, RC_GORMAN_TRACK_TREE_20 }, + { { SCENE_KOEPONARACE, 0, 31 }, RC_GORMAN_TRACK_TREE_21 }, + { { SCENE_KOEPONARACE, 0, 32 }, RC_GORMAN_TRACK_TREE_22 }, + { { SCENE_KOEPONARACE, 0, 33 }, RC_GORMAN_TRACK_TREE_23 }, + { { SCENE_KOEPONARACE, 0, 34 }, RC_GORMAN_TRACK_TREE_24 }, + { { SCENE_KOEPONARACE, 0, 35 }, RC_GORMAN_TRACK_TREE_25 }, + + // Great Bay Coast + { { SCENE_30GYOSON, 0, 10 }, RC_GREAT_BAY_COAST_TREE_01 }, + { { SCENE_30GYOSON, 0, 11 }, RC_GREAT_BAY_COAST_TREE_02 }, + { { SCENE_30GYOSON, 0, 12 }, RC_GREAT_BAY_COAST_TREE_03 }, + { { SCENE_30GYOSON, 0, 13 }, RC_GREAT_BAY_COAST_TREE_04 }, + + // Path to Mountain Village + { { SCENE_13HUBUKINOMITI, 0, 14 }, RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_01 }, + { { SCENE_13HUBUKINOMITI, 0, 15 }, RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_02 }, + { { SCENE_13HUBUKINOMITI, 0, 16 }, RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_03 }, + { { SCENE_13HUBUKINOMITI, 0, 17 }, RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_04 }, + + // Path to Snowhead + { { SCENE_14YUKIDAMANOMITI, 0, 22 }, RC_PATH_TO_SNOWHEAD_TREE_01 }, + { { SCENE_14YUKIDAMANOMITI, 0, 23 }, RC_PATH_TO_SNOWHEAD_TREE_02 }, + { { SCENE_14YUKIDAMANOMITI, 0, 24 }, RC_PATH_TO_SNOWHEAD_TREE_03 }, + { { SCENE_14YUKIDAMANOMITI, 0, 25 }, RC_PATH_TO_SNOWHEAD_TREE_04 }, + + // Road to Southern Swamp + { { SCENE_24KEMONOMITI, 0, 26 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_01 }, + { { SCENE_24KEMONOMITI, 0, 27 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_02 }, + { { SCENE_24KEMONOMITI, 0, 28 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_03 }, + { { SCENE_24KEMONOMITI, 0, 29 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_04 }, + { { SCENE_24KEMONOMITI, 0, 30 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_05 }, + { { SCENE_24KEMONOMITI, 0, 31 }, RC_ROAD_TO_SOUTHERN_SWAMP_TREE_06 }, + + // Romani Ranch + { { SCENE_F01, 0, 20 }, RC_ROMANI_RANCH_TREE_01 }, + { { SCENE_F01, 0, 21 }, RC_ROMANI_RANCH_TREE_02 }, + { { SCENE_F01, 0, 22 }, RC_ROMANI_RANCH_TREE_03 }, + { { SCENE_F01, 0, 23 }, RC_ROMANI_RANCH_TREE_04 }, + { { SCENE_F01, 0, 24 }, RC_ROMANI_RANCH_TREE_05 }, + { { SCENE_F01, 0, 25 }, RC_ROMANI_RANCH_TREE_06 }, + { { SCENE_F01, 0, 26 }, RC_ROMANI_RANCH_TREE_07 }, + + // Termina Field + // RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01 also handles RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02 + { { SCENE_00KEIKOKU, 0, 167 }, RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01 }, + { { SCENE_00KEIKOKU, 0, 168 }, RC_TERMINA_FIELD_TREE_01 }, + { { SCENE_00KEIKOKU, 0, 169 }, RC_TERMINA_FIELD_TREE_02 }, + + // Path to Goron Village + { { SCENE_17SETUGEN2, 0, 7 }, RC_TWIN_ISLANDS_SPRING_TREE_01 }, + { { SCENE_17SETUGEN2, 0, 8 }, RC_TWIN_ISLANDS_SPRING_TREE_02 }, + { { SCENE_17SETUGEN2, 0, 9 }, RC_TWIN_ISLANDS_SPRING_TREE_03 }, + { { SCENE_17SETUGEN, 0, 7 }, RC_TWIN_ISLANDS_TREE_01 }, + { { SCENE_17SETUGEN, 0, 8 }, RC_TWIN_ISLANDS_TREE_02 }, + { { SCENE_17SETUGEN, 0, 9 }, RC_TWIN_ISLANDS_TREE_03 }, + + // Zora Cape + { { SCENE_31MISAKI, 0, 24 }, RC_ZORA_CAPE_TREE_01 }, + { { SCENE_31MISAKI, 0, 25 }, RC_ZORA_CAPE_TREE_02 }, + { { SCENE_31MISAKI, 0, 26 }, RC_ZORA_CAPE_TREE_03 }, + { { SCENE_31MISAKI, 0, 27 }, RC_ZORA_CAPE_TREE_04 }, + { { SCENE_31MISAKI, 0, 28 }, RC_ZORA_CAPE_TREE_05 }, +}; + +std::map currentlySpawnedItems; + +void ApplyGravityToSpawnedItem(RandoCheckId randoCheckId) { + auto findItem = currentlySpawnedItems.find(randoCheckId); + if (findItem != currentlySpawnedItems.end()) { + findItem->second->actor.gravity = -1.4f; + } +} + +void SpawnTreeDrop(Vec3f pos, RandoCheckId randoCheckId) { + int customItemFlags = CustomItem::KILL_ON_TOUCH | CustomItem::ABLE_TO_ZORA_RANG; + + if (RANDO_SAVE_OPTIONS[RO_PEEK_TREE_DROPS] == RO_GENERIC_OFF) { + customItemFlags |= CustomItem::TOSS_ON_SPAWN; + } + + EnItem00* spawnedItem = CustomItem::Spawn( + pos.x - 20.0f, pos.y + 200.0f, pos.z + 25.0f, 0, customItemFlags, randoCheckId, + [](Actor* actor, PlayState* play) { + RandoSaveCheck& randoSaveCheck = RANDO_SAVE_CHECKS[CUSTOM_ITEM_PARAM]; + randoSaveCheck.eligible = true; + }, + [](Actor* actor, PlayState* play) { + auto& randoSaveCheck = RANDO_SAVE_CHECKS[CUSTOM_ITEM_PARAM]; + Matrix_Scale(30.0f, 30.0f, 30.0f, MTXMODE_APPLY); + Rando::DrawItem(Rando::ConvertItem(randoSaveCheck.randoItemId, (RandoCheckId)CUSTOM_ITEM_PARAM), actor); + }); + + auto findItem = currentlySpawnedItems.find(randoCheckId); + if (findItem == currentlySpawnedItems.end()) { + currentlySpawnedItems.insert({ randoCheckId, spawnedItem }); + } + + if (randoCheckId == RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01) { + pos.x += 40.0f; + SpawnTreeDrop(pos, RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02); + } +} + +void IdentifyTree(Actor* actor, bool* should) { + s16 actorListIndex = GetActorListIndex(actor); + RandoCheckId randoCheckId = RC_UNKNOWN; + + auto it = treeActorIdMap.find({ gPlayState->sceneId, gPlayState->roomCtx.curRoom.num, actorListIndex }); + if (it != treeActorIdMap.end()) { + randoCheckId = it->second; + } + + if (!RANDO_SAVE_CHECKS[randoCheckId].shuffled || RANDO_SAVE_CHECKS[randoCheckId].cycleObtained) { + return; + } + + if (!RANDO_SAVE_CHECKS[randoCheckId].obtained && RANDO_SAVE_OPTIONS[RO_PEEK_TREE_DROPS] == RO_GENERIC_ON) { + SpawnTreeDrop(actor->world.pos, randoCheckId); + } + + Rando::ActorBehavior::GetObjectRandoCheckId(actor); +} + +void Rando::ActorBehavior::InitObjTreeBehavior() { + COND_ID_HOOK(ShouldActorInit, ACTOR_EN_WOOD02, IS_RANDO, IdentifyTree); + COND_ID_HOOK(ShouldActorInit, ACTOR_OBJ_TREE, IS_RANDO, IdentifyTree); + COND_ID_HOOK(ShouldActorInit, ACTOR_OBJ_YASI, IS_RANDO, IdentifyTree); + COND_ID_HOOK(ShouldActorInit, ACTOR_EN_SNOWWD, IS_RANDO, IdentifyTree); + + COND_VB_SHOULD(VB_APPLY_BONK_TO_ACTOR, IS_RANDO, { + Actor* tree = va_arg(args, Actor*); + if (tree == nullptr) { + return; + } + + if (tree->id != ACTOR_EN_WOOD02 && tree->id != ACTOR_OBJ_TREE && tree->id != ACTOR_OBJ_YASI && + tree->id != ACTOR_EN_SNOWWD) { + return; + } + RandoCheckId randoCheckId = GetObjectRandoCheckId(tree); + if (randoCheckId == RC_UNKNOWN) { + return; + } + + if (!RANDO_SAVE_CHECKS[randoCheckId].obtained) { + if (RANDO_SAVE_OPTIONS[RO_PEEK_TREE_DROPS] == RO_GENERIC_ON) { + ApplyGravityToSpawnedItem(randoCheckId); + } else { + SpawnTreeDrop(tree->world.pos, randoCheckId); + } + } + }); + + COND_VB_SHOULD(VB_TREE_DROP_COLLECTIBLE, IS_RANDO, { + Actor* tree = va_arg(args, Actor*); + + if (RANDO_SAVE_OPTIONS[RO_SHUFFLE_TREE_DROPS] != RO_GENERIC_OFF) { + if (tree != NULL) { + RandoCheckId randoCheckId = GetObjectRandoCheckId(tree); + if (randoCheckId == RC_UNKNOWN) { + return; + } + + if (!RANDO_SAVE_CHECKS[randoCheckId].obtained) { + ApplyGravityToSpawnedItem(randoCheckId); + *should = false; + } + } + } + }); + + COND_VB_SHOULD(VB_DROP_COLLECTIBLE, IS_RANDO, { + Vec3f position = va_arg(args, Vec3f); + RandoCheckId randoCheckId = RC_UNKNOWN; + + if (RANDO_SAVE_OPTIONS[RO_SHUFFLE_TREE_DROPS] == RO_GENERIC_OFF) { + return; + } + + if (gPlayState->sceneId == SCENE_00KEIKOKU) { + auto it = manInTheTreeRupeeMap.find({ position.x, position.z }); + if (it == manInTheTreeRupeeMap.end()) { + return; + } else { + randoCheckId = it->second; + } + } + + if (!RANDO_SAVE_CHECKS[randoCheckId].obtained) { + ApplyGravityToSpawnedItem(randoCheckId); + *should = false; + } + }); + + COND_HOOK(OnSceneInit, IS_RANDO, [](s16 sceneId, s8 spawnNum) { currentlySpawnedItems.clear(); }); +} diff --git a/mm/2s2h/Rando/CheckTracker/CheckTracker.cpp b/mm/2s2h/Rando/CheckTracker/CheckTracker.cpp index 48dfddb947..0075bac624 100644 --- a/mm/2s2h/Rando/CheckTracker/CheckTracker.cpp +++ b/mm/2s2h/Rando/CheckTracker/CheckTracker.cpp @@ -84,6 +84,7 @@ std::vector checkTypeIconList = { /*RCTYPE_SONG*/ gItemIconSongNoteTex, /*RCTYPE_STRAY_FAIRY*/ gStrayFairyGreatBayIconTex, /*RCTYPE_TINGLE_SHOP*/ gItemIconAdultsWalletTex, + /*RCTYPE_TREE*/ gItemIconDekuStickTex, }; static constexpr ImVec4 tintColor = {}; diff --git a/mm/2s2h/Rando/Logic/Regions/BeneathTheWell.cpp b/mm/2s2h/Rando/Logic/Regions/BeneathTheWell.cpp index 5fc4076220..a88baa9ce9 100644 --- a/mm/2s2h/Rando/Logic/Regions/BeneathTheWell.cpp +++ b/mm/2s2h/Rando/Logic/Regions/BeneathTheWell.cpp @@ -50,7 +50,8 @@ static RegisterShipInitFunc initFunc([]() { }; Regions[RR_BENEATH_THE_WELL_COW_ROOM] = RandoRegion{ .name = "Cow Room", .sceneId = SCENE_REDEAD, .checks = { - CHECK(RC_BENEATH_THE_WELL_COW, CAN_PLAY_SONG(EPONA)) + CHECK(RC_BENEATH_THE_WELL_COW, CAN_PLAY_SONG(EPONA)), + CHECK(RC_BENEATH_THE_WELL_TREE, true), }, .connections = { CONNECTION(RR_BENEATH_THE_WELL_RIGHT_FIRE_KEESE, true), diff --git a/mm/2s2h/Rando/Logic/Regions/MilkRoad.cpp b/mm/2s2h/Rando/Logic/Regions/MilkRoad.cpp index 00dd79a67e..7a2c419659 100644 --- a/mm/2s2h/Rando/Logic/Regions/MilkRoad.cpp +++ b/mm/2s2h/Rando/Logic/Regions/MilkRoad.cpp @@ -13,6 +13,7 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_CUCCO_SHACK_LARGE_CRATE_01, true), CHECK(RC_CUCCO_SHACK_LARGE_CRATE_02, true), CHECK(RC_CUCCO_SHACK_LARGE_CRATE_03, true), + CHECK(RC_CUCCO_SHACK_TREE, true), }, .exits = { // TO FROM EXIT(ENTRANCE(ROMANI_RANCH, 4), ENTRANCE(CUCCO_SHACK, 0), true), @@ -77,6 +78,31 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_GORMAN_TRACK_GRASS_22, true), CHECK(RC_GORMAN_TRACK_GRASS_23, true), CHECK(RC_GORMAN_TRACK_GRASS_24, true), + CHECK(RC_GORMAN_TRACK_TREE_01, true), + CHECK(RC_GORMAN_TRACK_TREE_02, true), + CHECK(RC_GORMAN_TRACK_TREE_03, true), + CHECK(RC_GORMAN_TRACK_TREE_04, true), + CHECK(RC_GORMAN_TRACK_TREE_05, true), + CHECK(RC_GORMAN_TRACK_TREE_06, true), + CHECK(RC_GORMAN_TRACK_TREE_07, true), + CHECK(RC_GORMAN_TRACK_TREE_08, true), + CHECK(RC_GORMAN_TRACK_TREE_09, true), + CHECK(RC_GORMAN_TRACK_TREE_10, true), + CHECK(RC_GORMAN_TRACK_TREE_11, true), + CHECK(RC_GORMAN_TRACK_TREE_12, true), + CHECK(RC_GORMAN_TRACK_TREE_13, true), + CHECK(RC_GORMAN_TRACK_TREE_14, true), + CHECK(RC_GORMAN_TRACK_TREE_15, true), + CHECK(RC_GORMAN_TRACK_TREE_16, true), + CHECK(RC_GORMAN_TRACK_TREE_17, true), + CHECK(RC_GORMAN_TRACK_TREE_18, true), + CHECK(RC_GORMAN_TRACK_TREE_19, true), + CHECK(RC_GORMAN_TRACK_TREE_20, true), + CHECK(RC_GORMAN_TRACK_TREE_21, true), + CHECK(RC_GORMAN_TRACK_TREE_22, true), + CHECK(RC_GORMAN_TRACK_TREE_23, true), + CHECK(RC_GORMAN_TRACK_TREE_24, true), + CHECK(RC_GORMAN_TRACK_TREE_25, true), }, .exits = { // TO FROM EXIT(ENTRANCE(MILK_ROAD, 2), ENTRANCE(GORMAN_TRACK, 3), RANDO_EVENTS[RE_COWS_FROM_ALIENS]), @@ -186,6 +212,13 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_ROMANI_RANCH_GRASS_55, true), CHECK(RC_ROMANI_RANCH_GRASS_56, true), CHECK(RC_ROMANI_RANCH_GRASS_57, true), + CHECK(RC_ROMANI_RANCH_TREE_01, true), + CHECK(RC_ROMANI_RANCH_TREE_02, true), + CHECK(RC_ROMANI_RANCH_TREE_03, true), + CHECK(RC_ROMANI_RANCH_TREE_04, true), + CHECK(RC_ROMANI_RANCH_TREE_05, true), + CHECK(RC_ROMANI_RANCH_TREE_06, true), + CHECK(RC_ROMANI_RANCH_TREE_07, true), }, .exits = { // TO FROM EXIT(ENTRANCE(MILK_ROAD, 1), ENTRANCE(ROMANI_RANCH, 0), true), diff --git a/mm/2s2h/Rando/Logic/Regions/North.cpp b/mm/2s2h/Rando/Logic/Regions/North.cpp index 6cc57fef7d..535beefe9d 100644 --- a/mm/2s2h/Rando/Logic/Regions/North.cpp +++ b/mm/2s2h/Rando/Logic/Regions/North.cpp @@ -355,6 +355,12 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_TWIN_ISLANDS_SMALL_SNOWBALL_04, CAN_BE_GORON || HAS_ITEM(ITEM_HOOKSHOT)), CHECK(RC_TWIN_ISLANDS_SMALL_SNOWBALL_05, CAN_BE_GORON || HAS_ITEM(ITEM_HOOKSHOT)), CHECK(RC_TWIN_ISLANDS_SMALL_SNOWBALL_06, CAN_BE_GORON || HAS_ITEM(ITEM_HOOKSHOT)), + CHECK(RC_TWIN_ISLANDS_SPRING_TREE_01, RANDO_EVENTS[RE_CLEARED_SNOWHEAD_TEMPLE]), + CHECK(RC_TWIN_ISLANDS_SPRING_TREE_02, RANDO_EVENTS[RE_CLEARED_SNOWHEAD_TEMPLE]), + CHECK(RC_TWIN_ISLANDS_SPRING_TREE_03, RANDO_EVENTS[RE_CLEARED_SNOWHEAD_TEMPLE] && (CAN_BE_GORON || HAS_ITEM(ITEM_HOOKSHOT))), + CHECK(RC_TWIN_ISLANDS_TREE_01, true), + CHECK(RC_TWIN_ISLANDS_TREE_02, true), + CHECK(RC_TWIN_ISLANDS_TREE_03, CAN_BE_GORON || HAS_ITEM(ITEM_HOOKSHOT)), }, .exits = { // TO FROM EXIT(ENTRANCE(GROTTOS, 5), ENTRANCE(PATH_TO_GORON_VILLAGE_WINTER, 0), RANDO_EVENTS[RE_CLEARED_SNOWHEAD_TEMPLE] || CAN_USE_MAGIC_ARROW(FIRE)), // TODO: Grotto mapping Hot spring @@ -380,6 +386,8 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_SMALL_SNOWBALL_01, true), CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_SMALL_SNOWBALL_02, true), CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_SMALL_SNOWBALL_03, true), + CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_01, true), + CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_02, true), }, .exits = { // TO FROM EXIT(ENTRANCE(TERMINA_FIELD, 3), ENTRANCE(PATH_TO_MOUNTAIN_VILLAGE, 0), true), @@ -398,6 +406,8 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_LARGE_SNOWBALL_10, CanKillEnemy(ACTOR_OBJ_SNOWBALL)), CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_LARGE_SNOWBALL_11, CanKillEnemy(ACTOR_OBJ_SNOWBALL)), CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_SMALL_SNOWBALL_04, true), + CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_03, true), + CHECK(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_04, true), }, .exits = { // TO FROM EXIT(ENTRANCE(MOUNTAIN_VILLAGE_WINTER, 6), ENTRANCE(PATH_TO_MOUNTAIN_VILLAGE, 1), true), @@ -429,6 +439,9 @@ static RegisterShipInitFunc initFunc([]() { }, }; Regions[RR_PATH_TO_SNOWHEAD_LOWER] = RandoRegion{ .sceneId = SCENE_14YUKIDAMANOMITI, + .checks = { + CHECK(RC_PATH_TO_SNOWHEAD_TREE_04, true), + }, .exits = { // TO FROM EXIT(ENTRANCE(MOUNTAIN_VILLAGE_WINTER, 4), ENTRANCE(PATH_TO_SNOWHEAD, 0), true), }, @@ -454,6 +467,9 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_PATH_TO_SNOWHEAD_SMALL_SNOWBALL_01, true), CHECK(RC_PATH_TO_SNOWHEAD_SMALL_SNOWBALL_02, true), CHECK(RC_PATH_TO_SNOWHEAD_SMALL_SNOWBALL_03, true), + CHECK(RC_PATH_TO_SNOWHEAD_TREE_01, true), + CHECK(RC_PATH_TO_SNOWHEAD_TREE_02, true), + CHECK(RC_PATH_TO_SNOWHEAD_TREE_03, true), }, .exits = { // TO FROM EXIT(ENTRANCE(SNOWHEAD, 0), ENTRANCE(PATH_TO_SNOWHEAD, 1), true), diff --git a/mm/2s2h/Rando/Logic/Regions/South.cpp b/mm/2s2h/Rando/Logic/Regions/South.cpp index 378177bb55..1e83beb815 100644 --- a/mm/2s2h/Rando/Logic/Regions/South.cpp +++ b/mm/2s2h/Rando/Logic/Regions/South.cpp @@ -247,6 +247,12 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_GRASS_18, true), CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_GRASS_19, true), CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_GRASS_20, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_01, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_02, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_03, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_04, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_05, true), + CHECK(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_06, true), }, .exits = { // TO FROM EXIT(ENTRANCE(TERMINA_FIELD, 1), ENTRANCE(ROAD_TO_SOUTHERN_SWAMP, 0), true), diff --git a/mm/2s2h/Rando/Logic/Regions/TerminaField.cpp b/mm/2s2h/Rando/Logic/Regions/TerminaField.cpp index 0eeb63bf6e..9fadbd03e8 100644 --- a/mm/2s2h/Rando/Logic/Regions/TerminaField.cpp +++ b/mm/2s2h/Rando/Logic/Regions/TerminaField.cpp @@ -487,6 +487,10 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_TERMINA_FIELD_GRASS_214, true), CHECK(RC_TERMINA_FIELD_GRASS_215, true), CHECK(RC_TERMINA_FIELD_GRASS_216, true), + CHECK(RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01, true), + CHECK(RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02, true), + CHECK(RC_TERMINA_FIELD_TREE_01, true), + CHECK(RC_TERMINA_FIELD_TREE_02, true), }, .exits = { // TO FROM EXIT(ENTRANCE(GROTTOS, 0), ENTRANCE(TERMINA_FIELD, 0), CAN_USE_EXPLOSIVE || CAN_BE_GORON), // TODO: Grotto mapping Gossip Stone #3 diff --git a/mm/2s2h/Rando/Logic/Regions/West.cpp b/mm/2s2h/Rando/Logic/Regions/West.cpp index 355ff7e70b..a5e29d46fa 100644 --- a/mm/2s2h/Rando/Logic/Regions/West.cpp +++ b/mm/2s2h/Rando/Logic/Regions/West.cpp @@ -121,7 +121,6 @@ static RegisterShipInitFunc initFunc([]() { }; Regions[RR_GREAT_BAY_COAST] = RandoRegion{ .sceneId = SCENE_30GYOSON, .checks = { - CHECK(RC_GREAT_BAY_COAST_FISHERMAN_MINIGAME, RANDO_EVENTS[RE_CLEARED_GREAT_BAY_TEMPLE] && (HAS_ITEM(ITEM_HOOKSHOT) || CAN_USE_MAGIC_ARROW(ICE))), CHECK(RC_GREAT_BAY_COAST_MIKAU, CAN_USE_ABILITY(SWIM) && CAN_PLAY_SONG(HEALING)), CHECK(RC_GREAT_BAY_COAST_POT_03, true), CHECK(RC_GREAT_BAY_COAST_POT_04, true), @@ -130,6 +129,9 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_GREAT_BAY_COAST_GRASS_03, true), CHECK(RC_GREAT_BAY_COAST_GRASS_04, true), CHECK(RC_GREAT_BAY_COAST_GRASS_05, true), + CHECK(RC_GREAT_BAY_COAST_TREE_02, true), + CHECK(RC_GREAT_BAY_COAST_TREE_03, true), + CHECK(RC_GREAT_BAY_COAST_TREE_04, true), }, .exits = { // TO FROM EXIT(ENTRANCE(TERMINA_FIELD, 2), ENTRANCE(GREAT_BAY_COAST, 0), true), @@ -169,6 +171,15 @@ static RegisterShipInitFunc initFunc([]() { ENTRANCE(GREAT_BAY_COAST, 11), // From Song of Soaring }, }; + Regions[RR_GREAT_BAY_COAST_MINIGAME_PLATFORMS] = RandoRegion{ .sceneId = SCENE_30GYOSON, + .checks = { + CHECK(RC_GREAT_BAY_COAST_FISHERMAN_MINIGAME, RANDO_EVENTS[RE_CLEARED_GREAT_BAY_TEMPLE]), + CHECK(RC_GREAT_BAY_COAST_TREE_01, true), + }, + .connections = { + CONNECTION(RR_GREAT_BAY_COAST_CLIFFSIDE, CAN_USE_ABILITY(SWIM)), + }, + }; Regions[RR_GREAT_BAY_COAST_CLIFFSIDE] = RandoRegion{ .sceneId = SCENE_30GYOSON, .checks = { CHECK(RC_GREAT_BAY_COAST_PIECE_OF_HEART, CAN_HOOK_SCARECROW && CAN_GROW_BEAN_PLANT), @@ -183,6 +194,7 @@ static RegisterShipInitFunc initFunc([]() { .connections = { CONNECTION(RR_GREAT_BAY_COAST_COW_GROTTO, CAN_HOOK_SCARECROW && CAN_GROW_BEAN_PLANT), // TODO: Grotto mapping CONNECTION(RR_GREAT_BAY_COAST, CAN_USE_ABILITY(SWIM)), + CONNECTION(RR_GREAT_BAY_COAST_MINIGAME_PLATFORMS, RANDO_EVENTS[RE_CLEARED_GREAT_BAY_TEMPLE] && (HAS_ITEM(ITEM_HOOKSHOT) || CAN_USE_MAGIC_ARROW(ICE))), }, }; Regions[RR_GREAT_BAY_GREAT_FAIRY_FOUNTAIN] = RandoRegion{ .sceneId = SCENE_YOUSEI_IZUMI, @@ -316,6 +328,11 @@ static RegisterShipInitFunc initFunc([]() { CHECK(RC_ZORA_CAPE_WATERFALL_PIECE_OF_HEART, CAN_BE_ZORA && CAN_USE_ABILITY(SWIM)), CHECK(RC_ZORA_CAPE_NEAR_BEAVERS_POT_01, true), CHECK(RC_ZORA_CAPE_NEAR_BEAVERS_POT_02, true), + CHECK(RC_ZORA_CAPE_TREE_01, true), + CHECK(RC_ZORA_CAPE_TREE_02, true), + CHECK(RC_ZORA_CAPE_TREE_03, HAS_ITEM(ITEM_HOOKSHOT)), + CHECK(RC_ZORA_CAPE_TREE_04, HAS_ITEM(ITEM_HOOKSHOT)), + CHECK(RC_ZORA_CAPE_TREE_05, HAS_ITEM(ITEM_HOOKSHOT)), }, .exits = { // TO FROM EXIT(ENTRANCE(GREAT_BAY_COAST, 1), ENTRANCE(ZORA_CAPE, 0), true), diff --git a/mm/2s2h/Rando/Menu.cpp b/mm/2s2h/Rando/Menu.cpp index 4f489d03ad..082a8f756e 100644 --- a/mm/2s2h/Rando/Menu.cpp +++ b/mm/2s2h/Rando/Menu.cpp @@ -206,9 +206,8 @@ static void DrawLogicConditionsTab() { static void DrawShufflesTab() { f32 columnWidth = ImGui::GetContentRegionAvail().x / 3 - (ImGui::GetStyle().ItemSpacing.x * 2); - f32 halfHeight = ImGui::GetContentRegionAvail().y / 2 - (ImGui::GetStyle().ItemSpacing.y * 2); ImGui::SeparatorText("Shuffle Options"); - ImGui::BeginChild("randoShufflesColumn1", ImVec2(columnWidth, halfHeight)); + ImGui::BeginChild("randoShufflesColumn1", ImVec2(columnWidth, 0)); CVarCheckbox("Shuffle Songs", "gPlaceholderBool", CheckboxOptions({ { .disabled = true, .disabledTooltip = "Coming Soon" } }).DefaultValue(true)); CVarCheckbox("Shuffle Owl Statues", Rando::StaticData::Options[RO_SHUFFLE_OWL_STATUES].cvar); @@ -229,12 +228,19 @@ static void DrawShufflesTab() { .DefaultValue(STRAY_FAIRY_SCATTERED_TOTAL)); ImGui::EndChild(); ImGui::SameLine(); - ImGui::BeginChild("randoShufflesColumn2", ImVec2(columnWidth, halfHeight)); + ImGui::BeginChild("randoShufflesColumn2", ImVec2(columnWidth, 0)); CVarCheckbox("Shuffle Pot Drops", Rando::StaticData::Options[RO_SHUFFLE_POT_DROPS].cvar); CVarCheckbox("Shuffle Crate Drops", Rando::StaticData::Options[RO_SHUFFLE_CRATE_DROPS].cvar); CVarCheckbox("Shuffle Barrel Drops", Rando::StaticData::Options[RO_SHUFFLE_BARREL_DROPS].cvar); CVarCheckbox("Shuffle Snowball Drops", Rando::StaticData::Options[RO_SHUFFLE_SNOWBALL_DROPS].cvar); CVarCheckbox("Shuffle Grass Drops", Rando::StaticData::Options[RO_SHUFFLE_GRASS_DROPS].cvar); + CVarCheckbox("Shuffle Tree Drops", Rando::StaticData::Options[RO_SHUFFLE_TREE_DROPS].cvar); + CVarCheckbox("Peek Tree Drops", Rando::StaticData::Options[RO_PEEK_TREE_DROPS].cvar, + CheckboxOptions( + { { .disabled = (bool)!CVarGetInteger(Rando::StaticData::Options[RO_SHUFFLE_TREE_DROPS].cvar, 0), + .disabledTooltip = "Shuffle Tree Drops is Disabled." } }) + .Tooltip("Spawns the Trees Shuffled item near the top of the tree.\n" + "- Can be collected with Zora Boomerang.")); CVarCheckbox("Shuffle Frogs", Rando::StaticData::Options[RO_SHUFFLE_FROGS].cvar); CVarCheckbox("Shuffle Hive Drops", "gPlaceholderBool", CheckboxOptions({ { .disabled = true, .disabledTooltip = "Coming Soon" } })); @@ -243,7 +249,7 @@ static void DrawShufflesTab() { CheckboxOptions({ { .disabled = true, .disabledTooltip = "Coming Soon" } })); ImGui::EndChild(); ImGui::SameLine(); - ImGui::BeginChild("randoLocationsColumn3", ImVec2(columnWidth, halfHeight)); + ImGui::BeginChild("randoLocationsColumn3", ImVec2(columnWidth, 0)); CVarCheckbox("Triforce Hunt", Rando::StaticData::Options[RO_SHUFFLE_TRIFORCE_PIECES].cvar); ImGui::BeginDisabled(!CVarGetInteger(Rando::StaticData::Options[RO_SHUFFLE_TRIFORCE_PIECES].cvar, RO_GENERIC_OFF)); CVarSliderInt( diff --git a/mm/2s2h/Rando/MiscBehavior/OnFileCreate.cpp b/mm/2s2h/Rando/MiscBehavior/OnFileCreate.cpp index 9891be4ba2..e37bbd6187 100644 --- a/mm/2s2h/Rando/MiscBehavior/OnFileCreate.cpp +++ b/mm/2s2h/Rando/MiscBehavior/OnFileCreate.cpp @@ -158,6 +158,11 @@ void Rando::MiscBehavior::OnFileCreate(s16 fileNum) { continue; } + if (randoStaticCheck.randoCheckType == RCTYPE_TREE && + RANDO_SAVE_OPTIONS[RO_SHUFFLE_TREE_DROPS] == RO_GENERIC_NO) { + continue; + } + if (randoStaticCheck.randoCheckType == RCTYPE_FREESTANDING && RANDO_SAVE_OPTIONS[RO_SHUFFLE_FREESTANDING_ITEMS] == RO_GENERIC_NO) { continue; diff --git a/mm/2s2h/Rando/StaticData/Checks.cpp b/mm/2s2h/Rando/StaticData/Checks.cpp index 74cc8ab249..96dc61aae6 100644 --- a/mm/2s2h/Rando/StaticData/Checks.cpp +++ b/mm/2s2h/Rando/StaticData/Checks.cpp @@ -2269,6 +2269,76 @@ std::map Checks = { RC(RC_ENEMY_DROP_TEKTITE, RCTYPE_ENEMY_DROP, SCENE_SPOT00, FLAG_NONE, 0x0, RI_JUNK), RC(RC_ENEMY_DROP_WOLFOS, RCTYPE_ENEMY_DROP, SCENE_SPOT00, FLAG_NONE, 0x0, RI_JUNK), RC(RC_ENEMY_DROP_WALLMASTER, RCTYPE_ENEMY_DROP, SCENE_SPOT00, FLAG_NONE, 0x0, RI_JUNK), + + // Trees + RC(RC_BENEATH_THE_WELL_TREE, RCTYPE_TREE, SCENE_REDEAD, FLAG_NONE, 0x0, RI_NONE), + RC(RC_CUCCO_SHACK_TREE, RCTYPE_TREE, SCENE_F01C, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_01, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_02, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_03, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_04, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_05, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_06, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_07, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_08, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_09, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_10, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_11, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_12, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_13, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_14, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_15, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_16, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_17, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_18, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_19, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_20, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_21, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_22, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_23, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_24, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GORMAN_TRACK_TREE_25, RCTYPE_TREE, SCENE_KOEPONARACE, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GREAT_BAY_COAST_TREE_01, RCTYPE_TREE, SCENE_30GYOSON, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GREAT_BAY_COAST_TREE_02, RCTYPE_TREE, SCENE_30GYOSON, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GREAT_BAY_COAST_TREE_03, RCTYPE_TREE, SCENE_30GYOSON, FLAG_NONE, 0x0, RI_NONE), + RC(RC_GREAT_BAY_COAST_TREE_04, RCTYPE_TREE, SCENE_30GYOSON, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_01, RCTYPE_TREE, SCENE_13HUBUKINOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_02, RCTYPE_TREE, SCENE_13HUBUKINOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_03, RCTYPE_TREE, SCENE_13HUBUKINOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_04, RCTYPE_TREE, SCENE_13HUBUKINOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_SNOWHEAD_TREE_01, RCTYPE_TREE, SCENE_14YUKIDAMANOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_SNOWHEAD_TREE_02, RCTYPE_TREE, SCENE_14YUKIDAMANOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_SNOWHEAD_TREE_03, RCTYPE_TREE, SCENE_14YUKIDAMANOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_PATH_TO_SNOWHEAD_TREE_04, RCTYPE_TREE, SCENE_14YUKIDAMANOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_01, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_02, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_03, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_04, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_05, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROAD_TO_SOUTHERN_SWAMP_TREE_06, RCTYPE_TREE, SCENE_24KEMONOMITI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_01, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_02, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_03, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_04, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_05, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_06, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ROMANI_RANCH_TREE_07, RCTYPE_TREE, SCENE_F01, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01, RCTYPE_TREE, SCENE_00KEIKOKU, FLAG_NONE, 0x0, RI_RUPEE_RED), + RC(RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02, RCTYPE_TREE, SCENE_00KEIKOKU, FLAG_NONE, 0x0, RI_RUPEE_RED), + RC(RC_TERMINA_FIELD_TREE_01, RCTYPE_TREE, SCENE_00KEIKOKU, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TERMINA_FIELD_TREE_02, RCTYPE_TREE, SCENE_00KEIKOKU, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_SPRING_TREE_01, RCTYPE_TREE, SCENE_17SETUGEN2, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_SPRING_TREE_02, RCTYPE_TREE, SCENE_17SETUGEN2, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_SPRING_TREE_03, RCTYPE_TREE, SCENE_17SETUGEN2, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_TREE_01, RCTYPE_TREE, SCENE_17SETUGEN, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_TREE_02, RCTYPE_TREE, SCENE_17SETUGEN, FLAG_NONE, 0x0, RI_NONE), + RC(RC_TWIN_ISLANDS_TREE_03, RCTYPE_TREE, SCENE_17SETUGEN, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ZORA_CAPE_TREE_01, RCTYPE_TREE, SCENE_31MISAKI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ZORA_CAPE_TREE_02, RCTYPE_TREE, SCENE_31MISAKI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ZORA_CAPE_TREE_03, RCTYPE_TREE, SCENE_31MISAKI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ZORA_CAPE_TREE_04, RCTYPE_TREE, SCENE_31MISAKI, FLAG_NONE, 0x0, RI_NONE), + RC(RC_ZORA_CAPE_TREE_05, RCTYPE_TREE, SCENE_31MISAKI, FLAG_NONE, 0x0, RI_NONE), + }; // clang-format on diff --git a/mm/2s2h/Rando/StaticData/Options.cpp b/mm/2s2h/Rando/StaticData/Options.cpp index 16410bc142..3fe31a3e61 100644 --- a/mm/2s2h/Rando/StaticData/Options.cpp +++ b/mm/2s2h/Rando/StaticData/Options.cpp @@ -26,6 +26,7 @@ std::map Options = { RO(RO_TRAP_AMOUNT, 5), RO(RO_LOGIC, RO_LOGIC_GLITCHLESS), RO(RO_MINIMUM_STRAY_FAIRIES, STRAY_FAIRY_SCATTERED_TOTAL), + RO(RO_PEEK_TREE_DROPS, RO_GENERIC_OFF), RO(RO_PLENTIFUL_ITEMS, RO_GENERIC_OFF), RO(RO_SHUFFLE_BARREL_DROPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_BOSS_REMAINS, RO_GENERIC_OFF), @@ -37,13 +38,14 @@ std::map Options = { RO(RO_SHUFFLE_FROGS, RO_GENERIC_OFF), RO(RO_SHUFFLE_GOLD_SKULLTULAS, RO_GENERIC_OFF), RO(RO_SHUFFLE_GRASS_DROPS, RO_GENERIC_OFF), - RO(RO_SHUFFLE_TRAPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_OWL_STATUES, RO_GENERIC_OFF), RO(RO_SHUFFLE_POT_DROPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_SHOPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_SNOWBALL_DROPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_SWIM, RO_GENERIC_OFF), RO(RO_SHUFFLE_TINGLE_SHOPS, RO_GENERIC_OFF), + RO(RO_SHUFFLE_TRAPS, RO_GENERIC_OFF), + RO(RO_SHUFFLE_TREE_DROPS, RO_GENERIC_OFF), RO(RO_SHUFFLE_TRIFORCE_PIECES, RO_GENERIC_OFF), RO(RO_STARTING_CONSUMABLES, RO_GENERIC_OFF), RO(RO_STARTING_HEALTH, 3), diff --git a/mm/2s2h/Rando/Types.h b/mm/2s2h/Rando/Types.h index 9b5267b06a..19c8038a87 100644 --- a/mm/2s2h/Rando/Types.h +++ b/mm/2s2h/Rando/Types.h @@ -23,6 +23,7 @@ typedef enum { RCTYPE_SONG, RCTYPE_STRAY_FAIRY, RCTYPE_TINGLE_SHOP, + RCTYPE_TREE, RCTYPE_MAX, } RandoCheckType; @@ -2274,6 +2275,74 @@ typedef enum { RC_ENEMY_DROP_WOLFOS, RC_ENEMY_DROP_WALLMASTER, + RC_BENEATH_THE_WELL_TREE, + RC_CUCCO_SHACK_TREE, + RC_GORMAN_TRACK_TREE_01, + RC_GORMAN_TRACK_TREE_02, + RC_GORMAN_TRACK_TREE_03, + RC_GORMAN_TRACK_TREE_04, + RC_GORMAN_TRACK_TREE_05, + RC_GORMAN_TRACK_TREE_06, + RC_GORMAN_TRACK_TREE_07, + RC_GORMAN_TRACK_TREE_08, + RC_GORMAN_TRACK_TREE_09, + RC_GORMAN_TRACK_TREE_10, + RC_GORMAN_TRACK_TREE_11, + RC_GORMAN_TRACK_TREE_12, + RC_GORMAN_TRACK_TREE_13, + RC_GORMAN_TRACK_TREE_14, + RC_GORMAN_TRACK_TREE_15, + RC_GORMAN_TRACK_TREE_16, + RC_GORMAN_TRACK_TREE_17, + RC_GORMAN_TRACK_TREE_18, + RC_GORMAN_TRACK_TREE_19, + RC_GORMAN_TRACK_TREE_20, + RC_GORMAN_TRACK_TREE_21, + RC_GORMAN_TRACK_TREE_22, + RC_GORMAN_TRACK_TREE_23, + RC_GORMAN_TRACK_TREE_24, + RC_GORMAN_TRACK_TREE_25, + RC_GREAT_BAY_COAST_TREE_01, + RC_GREAT_BAY_COAST_TREE_02, + RC_GREAT_BAY_COAST_TREE_03, + RC_GREAT_BAY_COAST_TREE_04, + RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_01, + RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_02, + RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_03, + RC_PATH_TO_MOUNTAIN_VILLAGE_TREE_04, + RC_PATH_TO_SNOWHEAD_TREE_01, + RC_PATH_TO_SNOWHEAD_TREE_02, + RC_PATH_TO_SNOWHEAD_TREE_03, + RC_PATH_TO_SNOWHEAD_TREE_04, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_01, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_02, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_03, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_04, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_05, + RC_ROAD_TO_SOUTHERN_SWAMP_TREE_06, + RC_ROMANI_RANCH_TREE_01, + RC_ROMANI_RANCH_TREE_02, + RC_ROMANI_RANCH_TREE_03, + RC_ROMANI_RANCH_TREE_04, + RC_ROMANI_RANCH_TREE_05, + RC_ROMANI_RANCH_TREE_06, + RC_ROMANI_RANCH_TREE_07, + RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_01, + RC_TERMINA_FIELD_MAN_IN_THE_TREE_RUPEE_02, + RC_TERMINA_FIELD_TREE_01, + RC_TERMINA_FIELD_TREE_02, + RC_TWIN_ISLANDS_SPRING_TREE_01, + RC_TWIN_ISLANDS_SPRING_TREE_02, + RC_TWIN_ISLANDS_SPRING_TREE_03, + RC_TWIN_ISLANDS_TREE_01, + RC_TWIN_ISLANDS_TREE_02, + RC_TWIN_ISLANDS_TREE_03, + RC_ZORA_CAPE_TREE_01, + RC_ZORA_CAPE_TREE_02, + RC_ZORA_CAPE_TREE_03, + RC_ZORA_CAPE_TREE_04, + RC_ZORA_CAPE_TREE_05, + RC_MAX, } RandoCheckId; @@ -2531,6 +2600,7 @@ typedef enum { RR_GREAT_BAY_COAST_FISHERMAN_GROTTO, RR_GREAT_BAY_COAST, RR_GREAT_BAY_COAST_MARINE_LAB_EXTERIOR, + RR_GREAT_BAY_COAST_MINIGAME_PLATFORMS, RR_GREAT_BAY_COAST_PIRATE_LEDGE, RR_GREAT_BAY_GREAT_FAIRY_FOUNTAIN, RR_GREAT_BAY_TEMPLE_BABA_CHEST_ROOM, @@ -2794,9 +2864,9 @@ typedef enum { RO_HINTS_OATH_TO_ORDER, RO_HINTS_PURCHASEABLE, RO_HINTS_SPIDER_HOUSES, - RO_TRAP_AMOUNT, RO_LOGIC, RO_MINIMUM_STRAY_FAIRIES, + RO_PEEK_TREE_DROPS, RO_PLENTIFUL_ITEMS, RO_SHUFFLE_BARREL_DROPS, RO_SHUFFLE_BOSS_REMAINS, @@ -2806,22 +2876,25 @@ typedef enum { RO_SHUFFLE_ENEMY_DROPS, RO_SHUFFLE_FREESTANDING_ITEMS, RO_SHUFFLE_FROGS, - RO_SHUFFLE_GRASS_DROPS, RO_SHUFFLE_GOLD_SKULLTULAS, - RO_SHUFFLE_TRAPS, + RO_SHUFFLE_GRASS_DROPS, RO_SHUFFLE_OWL_STATUES, RO_SHUFFLE_POT_DROPS, RO_SHUFFLE_SHOPS, RO_SHUFFLE_SNOWBALL_DROPS, RO_SHUFFLE_SWIM, RO_SHUFFLE_TINGLE_SHOPS, + RO_SHUFFLE_TRAPS, + RO_SHUFFLE_TREE_DROPS, RO_SHUFFLE_TRIFORCE_PIECES, RO_STARTING_CONSUMABLES, RO_STARTING_HEALTH, RO_STARTING_MAPS_AND_COMPASSES, RO_STARTING_RUPEES, + RO_TRAP_AMOUNT, RO_TRIFORCE_PIECES_MAX, RO_TRIFORCE_PIECES_REQUIRED, + RO_MAX, } RandoOptionId; diff --git a/mm/src/code/z_en_item00.c b/mm/src/code/z_en_item00.c index 3af9d8133b..27244601a4 100644 --- a/mm/src/code/z_en_item00.c +++ b/mm/src/code/z_en_item00.c @@ -929,7 +929,7 @@ Actor* Item_DropCollectible(PlayState* play, Vec3f* spawnPos, u32 params) { s32 paramFF = params & 0xFF; s32 i; - if ((GameInteractor_Should(VB_ENEMY_DROP_COLLECTIBLE, true, *spawnPos))) { + if ((GameInteractor_Should(VB_DROP_COLLECTIBLE, true, *spawnPos))) { params &= 0x7FFF; newParamFF = params & 0xFF; @@ -1337,7 +1337,7 @@ u8 sDropTableAmounts[DROP_TABLE_SIZE * DROP_TABLE_NUMBER] = { }; void Item_DropCollectibleRandom(PlayState* play, Actor* fromActor, Vec3f* spawnPos, s16 params) { - if (!(GameInteractor_Should(VB_ENEMY_DROP_COLLECTIBLE, true, *spawnPos))) { + if (!(GameInteractor_Should(VB_DROP_COLLECTIBLE, true, *spawnPos))) { return; } diff --git a/mm/src/overlays/actors/ovl_En_Snowwd/z_en_snowwd.c b/mm/src/overlays/actors/ovl_En_Snowwd/z_en_snowwd.c index d30ac8fc9e..75ba50a72f 100644 --- a/mm/src/overlays/actors/ovl_En_Snowwd/z_en_snowwd.c +++ b/mm/src/overlays/actors/ovl_En_Snowwd/z_en_snowwd.c @@ -6,6 +6,7 @@ #include "z_en_snowwd.h" #include "objects/object_snowwd/object_snowwd.h" +#include "GameInteractor/GameInteractor.h" #define FLAGS 0x00000000 @@ -85,7 +86,7 @@ void EnSnowwd_Idle(EnSnowwd* this, PlayState* play) { if (thisx->home.rot.y != 0) { this->timer = 21; thisx->home.rot.y = 0; - if (!SNOWWD_DROPPED_COLLECTIBLE(&this->actor)) { + if (GameInteractor_Should(VB_TREE_DROP_COLLECTIBLE, !SNOWWD_DROPPED_COLLECTIBLE(&this->actor), this->actor)) { if (SNOWWD_GET_DROP_TABLE(&this->actor) < 16) { pos = thisx->world.pos; pos.y += 200.0f; diff --git a/mm/src/overlays/actors/ovl_Obj_Yasi/z_obj_yasi.c b/mm/src/overlays/actors/ovl_Obj_Yasi/z_obj_yasi.c index 7469dc7820..4a1fffed57 100644 --- a/mm/src/overlays/actors/ovl_Obj_Yasi/z_obj_yasi.c +++ b/mm/src/overlays/actors/ovl_Obj_Yasi/z_obj_yasi.c @@ -6,6 +6,7 @@ #include "z_obj_yasi.h" #include "objects/object_obj_yasi/object_obj_yasi.h" +#include "GameInteractor/GameInteractor.h" #define FLAGS 0x00000000 @@ -62,7 +63,7 @@ void ObjYasi_Update(Actor* thisx, PlayState* play) { Vec3f dropPos; if (this->dyna.actor.home.rot.z != 0) { - if (CAN_DROP_NUT(thisx)) { + if (GameInteractor_Should(VB_TREE_DROP_COLLECTIBLE, CAN_DROP_NUT(thisx), thisx)) { if (Rand_ZeroOne() < 0.5f) { dropPos.x = this->dyna.actor.world.pos.x; dropPos.y = this->dyna.actor.world.pos.y + 280.0f; diff --git a/mm/src/overlays/actors/ovl_player_actor/z_player.c b/mm/src/overlays/actors/ovl_player_actor/z_player.c index 236028dd00..96ef16964f 100644 --- a/mm/src/overlays/actors/ovl_player_actor/z_player.c +++ b/mm/src/overlays/actors/ovl_player_actor/z_player.c @@ -10875,7 +10875,7 @@ s32 func_80840A30(PlayState* play, Player* this, f32* arg2, f32 arg3) { return true; } - if (cylinderOc != NULL) { + if (GameInteractor_Should(VB_APPLY_BONK_TO_ACTOR, cylinderOc != NULL, cylinderOc)) { cylinderOc->home.rot.y = 1; } else if (this->actor.wallBgId != BGCHECK_SCENE) { // i.e. was an actor DynaPolyActor* wallPolyActor = DynaPoly_GetActor(&play->colCtx, this->actor.wallBgId);