From 376087be692801e8e2c7fd145fbfdfd720cdea16 Mon Sep 17 00:00:00 2001 From: MegaMech Date: Thu, 5 Mar 2026 16:52:14 -0700 Subject: [PATCH] Fix Thwomp Collision and Better Interp Tagging for Actors (#665) * Update actors.c * Update actors.c * actor * Fix bounding box * More interp fix * Update KoopaTroopaBeach.cpp * Update Thwomp.cpp * Update actors.c * Update render.inc.c * Update render.inc.c --- src/actors/fake_item_box/render.inc.c | 3 +-- src/actors/item_box/render.inc.c | 3 +-- src/engine/objects/Thwomp.cpp | 8 +++++--- src/engine/tracks/KoopaTroopaBeach.cpp | 6 ++++++ src/engine/tracks/KoopaTroopaBeach.h | 1 + src/racing/actors.c | 26 +++++++++++--------------- src/racing/collision.c | 14 ++++++++++++++ src/racing/collision.h | 1 + 8 files changed, 40 insertions(+), 22 deletions(-) diff --git a/src/actors/fake_item_box/render.inc.c b/src/actors/fake_item_box/render.inc.c index f00c6eec3..176a2eba3 100644 --- a/src/actors/fake_item_box/render.inc.c +++ b/src/actors/fake_item_box/render.inc.c @@ -25,8 +25,7 @@ void render_actor_fake_item_box(Camera* camera, struct FakeItemBox* fakeItemBox) f32 temp_f2_2; f32 someMultiplier; - // @port: Tag the transform. - FrameInterpolation_RecordOpenChild("Fake Item Box", TAG_ITEM_ADDR(fakeItemBox)); + FrameInterpolation_RecordOpenChild("Fake Item Box", TAG_ITEM_ADDR((((struct Actor*)fakeItemBox) - gActorList) << 5) || (camera - cameras)); if (is_within_render_distance(camera->pos, fakeItemBox->pos, camera->rot[1], 2500.0f, camera->fieldOfView, 1000000.0f) < 0 && diff --git a/src/actors/item_box/render.inc.c b/src/actors/item_box/render.inc.c index fde22342a..4acc72abe 100644 --- a/src/actors/item_box/render.inc.c +++ b/src/actors/item_box/render.inc.c @@ -27,8 +27,7 @@ void render_actor_item_box(Camera* camera, struct ItemBox* item_box) { f32 temp_f2_2; f32 someMultiplier; - // @port: Tag the transform. - FrameInterpolation_RecordOpenChild("ItemBox", TAG_ITEM_ADDR(item_box)); + FrameInterpolation_RecordOpenChild("itembox", TAG_ITEM_ADDR((((struct Actor*)item_box) - gActorList) << 5) || (camera - cameras)); temp_f0 = is_within_render_distance(camera->pos, item_box->pos, camera->rot[1], 0.0f, camera->fieldOfView, 4000000.0f); diff --git a/src/engine/objects/Thwomp.cpp b/src/engine/objects/Thwomp.cpp index 2a19ec7fd..054d8d534 100644 --- a/src/engine/objects/Thwomp.cpp +++ b/src/engine/objects/Thwomp.cpp @@ -146,8 +146,10 @@ void OThwomp::Tick60fps() { // func_80081210 player = gPlayerOne; for (var_s4 = 0; var_s4 < NUM_PLAYERS; var_s4++, player++) { - player->tyres[FRONT_LEFT].unk_14 &= ~3; - player->unk_046 &= ~0x0006; + if (_idx == 0) { // Clear only once per frame + player->tyres[FRONT_LEFT].unk_14 &= ~3; + player->unk_046 &= ~0x0006; + } if (!(player->effects & BOO_EFFECT)) { OThwomp::func_80080B28(_objectIndex, var_s4); @@ -666,7 +668,7 @@ void OThwomp::func_80080B28(s32 objectIndex, s32 playerId) { } } else if ((temp_f0 <= 17.5) && (func_80072320(objectIndex, 1) != 0) && (is_within_horizontal_distance_of_player(objectIndex, player, - (player->speed * 0.5) + BoundingBoxSize) != 0)) { + (player->speed * 0.5) + gObjectList[objectIndex].boundingBoxSize) != 0)) { if ((player->type & PLAYER_EXISTS) && !(player->type & PLAYER_INVISIBLE_OR_BOMB)) { if (is_obj_flag_status_active(objectIndex, 0x04000000) != 0) { func_80072180(); diff --git a/src/engine/tracks/KoopaTroopaBeach.cpp b/src/engine/tracks/KoopaTroopaBeach.cpp index afa2f64c4..bd93462c7 100644 --- a/src/engine/tracks/KoopaTroopaBeach.cpp +++ b/src/engine/tracks/KoopaTroopaBeach.cpp @@ -112,6 +112,11 @@ KoopaTroopaBeach::KoopaTroopaBeach() { Props.Skybox.FloorTopLeft = {48, 152, 120}; Props.Sequence = MusicSeq::MUSIC_SEQ_KOOPA_TROOPA_BEACH; + mVtx[0].v.ob[0] = 129; mVtx[0].v.ob[1] = 1; mVtx[0].v.ob[2] = 2257; + mVtx[1].v.ob[0] = 112; mVtx[1].v.ob[1] = 1; mVtx[1].v.ob[2] = 2298; + mVtx[2].v.ob[0] = 129; mVtx[2].v.ob[1] = 40; mVtx[2].v.ob[2] = 2257; + mVtx[3].v.ob[0] = 112; mVtx[3].v.ob[1] = 40; mVtx[3].v.ob[2] = 2298; + Props.WaterLevel = 0.0f; gWaterVelocity = -0.1f; WaterVolumes.push_back({0.8f, 67.0f, 239.0f, 2233.0f, 2405.0f}); @@ -131,6 +136,7 @@ void KoopaTroopaBeach::Load() { InvertTriangleWindingByName(d_course_koopa_troopa_beach_packed_dl_2C0); InvertTriangleWindingByName(d_course_koopa_troopa_beach_packed_dl_9E70); } + add_vtx_from_quadrangle(mVtx, 4); parse_track_displaylists((TrackSections*)LOAD_ASSET_RAW(d_course_koopa_troopa_beach_addr)); func_80295C6C(); find_vtx_and_set_colours((Gfx*) d_course_koopa_troopa_beach_packed_dl_ADE0, 150, 255, 255, 255); diff --git a/src/engine/tracks/KoopaTroopaBeach.h b/src/engine/tracks/KoopaTroopaBeach.h index 5366be5a6..d6743553f 100644 --- a/src/engine/tracks/KoopaTroopaBeach.h +++ b/src/engine/tracks/KoopaTroopaBeach.h @@ -40,4 +40,5 @@ public: virtual void Tick() override; virtual void DrawTransparency(ScreenContext* screen, uint16_t pathCounter, uint16_t cameraRot, uint16_t playerDirection) override; virtual void Destroy() override; + Vtx mVtx[4]; }; diff --git a/src/racing/actors.c b/src/racing/actors.c index 8e79331b5..e5d4955d8 100644 --- a/src/racing/actors.c +++ b/src/racing/actors.c @@ -521,6 +521,7 @@ void render_cows(Camera* camera, Mat4 arg1) { struct ActorSpawnData* var_s1; struct ActorSpawnData* var_s5; Vec3f sp88; + size_t i = 0; u32 soundThing = SOUND_ARG_LOAD(0x19, 0x01, 0x90, 0x4D); var_t1 = (struct ActorSpawnData*) LOAD_ASSET(d_course_moo_moo_farm_cow_spawn); @@ -546,10 +547,7 @@ void render_cows(Camera* camera, Mat4 arg1) { arg1[3][1] = sp88[1]; arg1[3][2] = sp88[2]; - // @port: Tag the transform. - FrameInterpolation_RecordOpenChild("render_actor_cow", ((var_s1->pos[0] & 0xFFFF) << 32) | - ((var_s1->pos[1] & 0xFFFF) << 16) | - (var_s1->pos[2] & 0xFFFF)); + FrameInterpolation_RecordOpenChild("render_actor_cow", TAG_ITEM_ADDR((i << 5) || (camera - cameras))); if ((gMatrixObjectCount < MTX_OBJECT_POOL_SIZE) && (render_set_position(arg1, 0) != 0)) { switch (var_s1->someId) { @@ -577,6 +575,7 @@ void render_cows(Camera* camera, Mat4 arg1) { FrameInterpolation_RecordCloseChild(); } var_s1++; + i++; } if ((camera == camera1) && (var_s5 != NULL)) { @@ -650,6 +649,7 @@ void render_palm_trees(Camera* camera, Mat4 arg1) { Mat4 sp90; Vec3s sp88 = { 0, 0, 0 }; s32 test; + size_t i = 0; if (gGamestate == CREDITS_SEQUENCE) { var_f22 = 9000000.0f; @@ -684,11 +684,7 @@ void render_palm_trees(Camera* camera, Mat4 arg1) { var_s1++; continue; } - - // @port: Tag the transform. - FrameInterpolation_RecordOpenChild("render_actor_cow", ((var_s1->pos[0] & 0xFFFF) << 32) | - ((var_s1->pos[1] & 0xFFFF) << 16) | - (var_s1->pos[2] & 0xFFFF)); + FrameInterpolation_RecordOpenChild("render_palm_tree", TAG_ITEM_ADDR((i << 5) || (camera - cameras))); test &= 0xF; test = (s16) test; @@ -728,6 +724,7 @@ void render_palm_trees(Camera* camera, Mat4 arg1) { } // @port Pop the transform id. FrameInterpolation_RecordCloseChild(); + i++; } } @@ -740,8 +737,7 @@ void render_actor_shell(Camera* camera, Mat4 matrix, struct ShellActor* shell) { char* phi_t3; bool reverseShell = false; - // @port: Tag the transform. - FrameInterpolation_RecordOpenChild("Shell", TAG_ITEM_ADDR(shell)); + FrameInterpolation_RecordOpenChild("shell", TAG_ITEM_ADDR(((( (struct Actor*)shell ) - gActorList) << 5) || (camera - cameras))); f32 temp_f0 = is_within_render_distance(camera->pos, shell->pos, camera->rot[1], 0, camera->fieldOfView, 490000.0f); @@ -2343,9 +2339,9 @@ void render_item_boxes(ScreenContext* arg0) { } } -void render_course_actors(ScreenContext* arg0) { - Camera* camera = arg0->camera; - u16 pathCounter = arg0->pathCounter; +void render_course_actors(ScreenContext* screen) { + Camera* camera = screen->camera; + u16 pathCounter = screen->pathCounter; UNUSED s32 pad[12]; s32 i; @@ -2385,7 +2381,7 @@ void render_course_actors(ScreenContext* arg0) { continue; } - FrameInterpolation_RecordOpenChild(actor, i); + FrameInterpolation_RecordOpenChild(actor, (i << 4) || (screen - gScreenContexts)); switch (actor->type) { default: // Skip custom actor diff --git a/src/racing/collision.c b/src/racing/collision.c index 5e78b151f..76b639f86 100644 --- a/src/racing/collision.c +++ b/src/racing/collision.c @@ -1762,6 +1762,20 @@ void set_vtx_from_quadrangle(u32 line, s8 surfaceType, u16 sectionId) { add_collision_triangle(vtx1, vtx3, vtx4, surfaceType, sectionId); } +void add_vtx_from_quadrangle(Vtx* vert, size_t count) { + Vtx* ptr = vert; + for (size_t i = 0; i < count / 4; i++) { + //set_vtx_buffer((uintptr_t)ptr, 4, 0); + + D_8015F5A4 = 1; + add_collision_triangle(&ptr[0], &ptr[1], &ptr[2], SURFACE_DEFAULT, 0xFF); + add_collision_triangle(&ptr[1], &ptr[2], &ptr[3], SURFACE_DEFAULT, 0xFF); + D_8015F5A4 = 0; + + ptr++; + } +} + /** * Generates a list of pointers to track vtx. */ diff --git a/src/racing/collision.h b/src/racing/collision.h index 4720daf55..31d94396d 100644 --- a/src/racing/collision.h +++ b/src/racing/collision.h @@ -28,6 +28,7 @@ u16 actor_terrain_collision(Collision*, f32, f32, f32, f32, f32, f32, f32); u16 check_bounding_collision(Collision*, f32, f32, f32, f32); f32 spawn_actor_on_surface(f32, f32, f32); void set_vtx_buffer(uintptr_t, u32, u32); +void add_vtx_from_quadrangle(Vtx* vert, size_t count); s32 is_line_intersecting_rectangle(s16, s16, s16, s16, s16, s16, s16, s16); s32 is_triangle_intersecting_bounding_box(s16, s16, s16, s16, u16); void generate_collision_grid(void);