diff --git a/include/config.h b/include/config.h index 4790cfa1..848112bb 100644 --- a/include/config.h +++ b/include/config.h @@ -123,6 +123,8 @@ // Visual debug enables some collision visuals. Tapping Right on the dpad will cycle between visual hitboxes, visual surfaces, both, and neither. // If puppyprint is enabled, then this can be cycled only while the screen is active. //#define VISUAL_DEBUG +// Number of supported areas per level. +#define AREA_COUNT 8 // BUG/GAME QOL FIXES // Fix instant warp offset not working when warping across different areas diff --git a/include/level_commands.h b/include/level_commands.h index 8d1c01b7..940706a4 100644 --- a/include/level_commands.h +++ b/include/level_commands.h @@ -219,6 +219,12 @@ CMD_PTR(romEnd) #endif +#define CHANGE_AREA_SKYBOX(area, segStart, segEnd) \ + CMD_BBH(0x3E, 0x0C, area), \ + CMD_PTR(segStart), \ + CMD_PTR(segEnd) + + #define INIT_LEVEL() \ CMD_BBH(0x1B, 0x04, 0x0000) diff --git a/src/engine/level_script.c b/src/engine/level_script.c index 6a4944c5..e656482e 100644 --- a/src/engine/level_script.c +++ b/src/engine/level_script.c @@ -304,11 +304,22 @@ static void level_cmd_load_yay0_texture(void) { sCurrentCmd = CMD_NEXT; } +static void level_cmd_change_area_skybox(int area, u8 *start, u8 *end) { + u8 areaCheck = CMD_GET(s16, 2); + gAreaSkyboxStart[areaCheck-1] = CMD_GET(void *, 4); + gAreaSkyboxEnd[areaCheck-1] = CMD_GET(void *, 8); + sCurrentCmd = CMD_NEXT; +} + static void level_cmd_init_level(void) { init_graph_node_start(NULL, (struct GraphNodeStart *) &gObjParentGraphNode); clear_objects(); clear_areas(); main_pool_push_state(); + for (u8 clearPointers = 0; clearPointers < AREA_COUNT; clearPointers++) { + gAreaSkyboxStart[clearPointers] = 0; + gAreaSkyboxEnd[clearPointers] = 0; + } sCurrentCmd = CMD_NEXT; } @@ -783,9 +794,9 @@ static void level_cmd_get_or_set_var(void) { sCurrentCmd = CMD_NEXT; } -#ifdef PUPPYCAM static void level_cmd_puppyvolume(void) { +#ifdef PUPPYCAM if ((sPuppyVolumeStack[gPuppyVolumeCount] = mem_pool_alloc(gPuppyMemoryPool,sizeof(struct sPuppyVolume))) == NULL) { sCurrentCmd = CMD_NEXT; @@ -815,9 +826,10 @@ static void level_cmd_puppyvolume(void) sPuppyVolumeStack[gPuppyVolumeCount]->room = CMD_GET(s16, 34); gPuppyVolumeCount++; +#endif sCurrentCmd = CMD_NEXT; } -#endif + static void (*LevelScriptJumpTable[])(void) = { /*00*/ level_cmd_load_and_execute, @@ -881,9 +893,8 @@ static void (*LevelScriptJumpTable[])(void) = { /*3A*/ level_cmd_3A, /*3B*/ level_cmd_create_whirlpool, /*3C*/ level_cmd_get_or_set_var, - #ifdef PUPPYCAM - /*3E*/ level_cmd_puppyvolume, - #endif + /*3D*/ level_cmd_puppyvolume, + /*3E*/ level_cmd_change_area_skybox, }; struct LevelCommand *level_script_execute(struct LevelCommand *cmd) { diff --git a/src/game/area.c b/src/game/area.c index 63cedc91..ce9fefd3 100644 --- a/src/game/area.c +++ b/src/game/area.c @@ -228,7 +228,7 @@ void load_area(s32 index) { if (gCurrentArea == NULL && gAreaData[index].unk04 != NULL) { gCurrentArea = &gAreaData[index]; gCurrAreaIndex = gCurrentArea->index; - + if (gCurrentArea->terrainData != NULL) { load_area_terrain(index, gCurrentArea->terrainData, gCurrentArea->surfaceRooms, gCurrentArea->macroObjects); @@ -239,7 +239,7 @@ void load_area(s32 index) { } load_obj_warp_nodes(); - geo_call_global_function_nodes(&gCurrentArea->unk04->node, GEO_CONTEXT_AREA_LOAD); + geo_call_global_function_nodes(&gCurrentArea->unk04->node, GEO_CONTEXT_AREA_LOAD); } } @@ -262,6 +262,9 @@ void load_mario_area(void) { gCurrentArea->flags |= 0x01; spawn_objects_from_info(0, gMarioSpawnInfo); } + if (gAreaSkyboxStart[gCurrAreaIndex-1]) { + load_segment_decompress(0x0A, gAreaSkyboxStart[gCurrAreaIndex-1], gAreaSkyboxEnd[gCurrAreaIndex-1]); + } } void unload_mario_area(void) { diff --git a/src/game/game_init.c b/src/game/game_init.c index 87c2fa06..e081e277 100644 --- a/src/game/game_init.c +++ b/src/game/game_init.c @@ -86,6 +86,8 @@ u32 gGlobalTimer = 0; #ifdef WIDE s16 gWidescreen; #endif +u8 *gAreaSkyboxStart[AREA_COUNT-1]; +u8 *gAreaSkyboxEnd[AREA_COUNT-1]; // Framebuffer rendering values (max 3) u16 sRenderedFramebuffer = 0; diff --git a/src/game/game_init.h b/src/game/game_init.h index 84a31755..0d451764 100644 --- a/src/game/game_init.h +++ b/src/game/game_init.h @@ -49,6 +49,8 @@ extern u8 gBorderHeight; #ifdef CUSTOM_DEBUG extern u8 gCustomDebugMode; #endif +extern u8 *gAreaSkyboxStart[AREA_COUNT-1]; +extern u8 *gAreaSkyboxEnd[AREA_COUNT-1]; #ifdef EEP extern s8 gEepromProbe; #endif