From dcfcf50a802a6e2635cd694f14a11e718f51dd67 Mon Sep 17 00:00:00 2001 From: arthurtilly <32559225+arthurtilly@users.noreply.github.com> Date: Fri, 15 Dec 2023 17:24:03 +1300 Subject: [PATCH] wall fix (#734) --- data/behavior_data.c | 2 +- src/engine/surface_collision.c | 31 ++++++++++++++++--------------- src/engine/surface_load.c | 14 -------------- 3 files changed, 17 insertions(+), 30 deletions(-) diff --git a/data/behavior_data.c b/data/behavior_data.c index 2e2c2dc1..07803591 100644 --- a/data/behavior_data.c +++ b/data/behavior_data.c @@ -5873,7 +5873,7 @@ const BehaviorScript bhvRacingPenguin[] = { OR_INT(oFlags, (OBJ_FLAG_COMPUTE_ANGLE_TO_MARIO | OBJ_FLAG_ACTIVE_FROM_AFAR | OBJ_FLAG_COMPUTE_DIST_TO_MARIO | OBJ_FLAG_SET_FACE_YAW_TO_MOVE_YAW | OBJ_FLAG_UPDATE_GFX_POS_AND_ANGLE)), LOAD_ANIMATIONS(oAnimations, penguin_seg5_anims_05008B74), ANIMATE(PENGUIN_ANIM_IDLE), - SET_OBJ_PHYSICS(/*Wall hitbox radius*/ 300, /*Gravity*/ -800, /*Bounciness*/ -5, /*Drag strength*/ 0, /*Friction*/ 0, /*Buoyancy*/ 0, /*Unused*/ 0, 0), + SET_OBJ_PHYSICS(/*Wall hitbox radius*/ 200, /*Gravity*/ -800, /*Bounciness*/ -5, /*Drag strength*/ 0, /*Friction*/ 0, /*Buoyancy*/ 0, /*Unused*/ 0, 0), SCALE(/*Unused*/ 0, /*Field*/ 400), CALL_NATIVE(bhv_racing_penguin_init), BEGIN_LOOP(), diff --git a/src/engine/surface_collision.c b/src/engine/surface_collision.c index 007c5748..8b54ef8a 100644 --- a/src/engine/surface_collision.c +++ b/src/engine/surface_collision.c @@ -63,11 +63,6 @@ static s32 find_wall_collisions_from_list(struct SurfaceNode *surfaceNode, struc TerrainData type = SURFACE_DEFAULT; s32 numCols = 0; - // Max collision radius = 200 - if (radius > 200) { - radius = 200; - } - f32 margin_radius = radius - 1.0f; // Stay in this loop until out of walls. @@ -216,19 +211,25 @@ s32 find_wall_collisions(struct WallCollisionData *colData) { } // World (level) consists of a 16x16 grid. Find where the collision is on the grid (round toward -inf) - s32 cellX = GET_CELL_COORD(x); - s32 cellZ = GET_CELL_COORD(z); + s32 minCellX = GET_CELL_COORD(x - colData->radius); + s32 minCellZ = GET_CELL_COORD(z - colData->radius); + s32 maxCellX = GET_CELL_COORD(x + colData->radius); + s32 maxCellZ = GET_CELL_COORD(z + colData->radius); - if (!(gCollisionFlags & COLLISION_FLAG_EXCLUDE_DYNAMIC)) { - // Check for surfaces belonging to objects. - node = gDynamicSurfacePartition[cellZ][cellX][SPATIAL_PARTITION_WALLS].next; - numCollisions += find_wall_collisions_from_list(node, colData); + for (s32 cellX = minCellX; cellX <= maxCellX; cellX++) { + for (s32 cellZ = minCellZ; cellZ <= maxCellZ; cellZ++) { + if (!(gCollisionFlags & COLLISION_FLAG_EXCLUDE_DYNAMIC)) { + // Check for surfaces belonging to objects. + node = gDynamicSurfacePartition[cellZ][cellX][SPATIAL_PARTITION_WALLS].next; + numCollisions += find_wall_collisions_from_list(node, colData); + } + + // Check for surfaces that are a part of level geometry. + node = gStaticSurfacePartition[cellZ][cellX][SPATIAL_PARTITION_WALLS].next; + numCollisions += find_wall_collisions_from_list(node, colData); + } } - // Check for surfaces that are a part of level geometry. - node = gStaticSurfacePartition[cellZ][cellX][SPATIAL_PARTITION_WALLS].next; - numCollisions += find_wall_collisions_from_list(node, colData); - gCollisionFlags &= ~(COLLISION_FLAG_RETURN_FIRST | COLLISION_FLAG_EXCLUDE_DYNAMIC | COLLISION_FLAG_INCLUDE_INTANGIBLE); #ifdef VANILLA_DEBUG // Increment the debug tracker. diff --git a/src/engine/surface_load.c b/src/engine/surface_load.c index 4474bbb2..f2444fb7 100644 --- a/src/engine/surface_load.c +++ b/src/engine/surface_load.c @@ -187,13 +187,6 @@ static s32 lower_cell_index(s32 coord) { // [0, NUM_CELLS) s32 index = coord / CELL_SIZE; - // Include extra cell if close to boundary - //! Some wall checks are larger than the buffer, meaning wall checks can - // miss walls that are near a cell border. - if (coord % CELL_SIZE < 50) { - index--; - } - // Potentially > NUM_CELLS - 1, but since the upper index is <= NUM_CELLS - 1, not exploitable return MAX(0, index); } @@ -213,13 +206,6 @@ static s32 upper_cell_index(s32 coord) { // [0, NUM_CELLS) s32 index = coord / CELL_SIZE; - // Include extra cell if close to boundary - //! Some wall checks are larger than the buffer, meaning wall checks can - // miss walls that are near a cell border. - if (coord % CELL_SIZE > CELL_SIZE - 50) { - index++; - } - // Potentially < 0, but since lower index is >= 0, not exploitable return MIN((NUM_CELLS - 1), index); }