From 3ae09a4bad495d16dec5719ee84c7fa6df1ac903 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 13:09:22 +0100 Subject: [PATCH 01/66] Decompiled FindGridShift() --- game/collide.cpp | 16 +++++++++++++++- game/collide.h | 2 +- 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 3599420..82a86f7 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -24,6 +24,20 @@ #include "game/control.h" #include "global/vars.h" +int __cdecl FindGridShift(int src, int dest) +{ + int srcShift, destShift; + srcShift = src >> WALL_SHIFT; + destShift = dest >> WALL_SHIFT; + if (srcShift == destShift) + return 0; + src &= 1023; + if (destShift <= srcShift) + return -1 - src; + else + return 1025 - src; +} + int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite) { int rxMin = x - coll->radius; int rxMax = x + coll->radius; @@ -196,7 +210,7 @@ void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID) { */ void Inject_Collide() { // INJECT(0x004128D0, GetCollisionInfo); -// INJECT(0x00412F90, FindGridShift); + INJECT(0x00412F90, FindGridShift); INJECT(0x00412FC0, CollideStaticObjects); INJECT(0x004133B0, GetNearByRooms); diff --git a/game/collide.h b/game/collide.h index 9d53b79..3e3e548 100644 --- a/game/collide.h +++ b/game/collide.h @@ -28,7 +28,7 @@ * Function list */ // 0x004128D0: GetCollisionInfo -// 0x00412F90: FindGridShift +int __cdecl FindGridShift(int src, int dest); // 0x00412F90 int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite); // 0x00412FC0 void __cdecl GetNearByRooms(int x, int y, int z, int r, int h, __int16 roomID); // 0x004133B0 From c5e4523db8935a4cfa5fcf2b556b953948ff5922 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 13:14:05 +0100 Subject: [PATCH 02/66] Decompiled ShiftItem() - Fixed FindGridShift() Code Style. --- game/collide.cpp | 14 +++++++++++--- game/collide.h | 2 +- 2 files changed, 12 insertions(+), 4 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 82a86f7..33c6663 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -24,8 +24,7 @@ #include "game/control.h" #include "global/vars.h" -int __cdecl FindGridShift(int src, int dest) -{ +int __cdecl FindGridShift(int src, int dest) { int srcShift, destShift; srcShift = src >> WALL_SHIFT; destShift = dest >> WALL_SHIFT; @@ -205,6 +204,15 @@ void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID) { DrawRoomsArray[DrawRoomsCount++] = roomID; } +void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { + item->pos.x += coll->shift.x; + item->pos.y += coll->shift.y; + item->pos.z += coll->shift.z; + coll->shift.z = 0; + coll->shift.y = 0; + coll->shift.x = 0; +} + /* * Inject function */ @@ -216,7 +224,7 @@ void Inject_Collide() { INJECT(0x004133B0, GetNearByRooms); INJECT(0x00413480, GetNewRoom); -// INJECT(0x004134E0, ShiftItem); + INJECT(0x004134E0, ShiftItem); // INJECT(0x00413520, UpdateLaraRoom); // INJECT(0x00413580, GetTiltType); // INJECT(0x00413620, LaraBaddieCollision); diff --git a/game/collide.h b/game/collide.h index 3e3e548..eb74875 100644 --- a/game/collide.h +++ b/game/collide.h @@ -34,7 +34,7 @@ int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 r void __cdecl GetNearByRooms(int x, int y, int z, int r, int h, __int16 roomID); // 0x004133B0 void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID); // 0x00413480 -// 0x004134E0: ShiftItem +void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 #define UpdateLaraRoom ((void(__cdecl*)(ITEM_INFO*, int)) 0x00413520) From e4b85526d89f187d5d8206b47cbc3255b90c82ac Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 13:24:59 +0100 Subject: [PATCH 03/66] Decompiled UpdateLaraRoom() - Added phd_math to have the same header file as @asasas9500 --- game/collide.cpp | 20 +++++++++++++++++++- game/collide.h | 2 +- 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 33c6663..7c3d048 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -21,6 +21,8 @@ #include "global/precompiled.h" #include "game/collide.h" +#include "3dsystem/phd_math.h" +#include "game/items.h" #include "game/control.h" #include "global/vars.h" @@ -213,6 +215,22 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { coll->shift.x = 0; } +void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { + FLOOR_INFO* floor; + int x, y, z; + short roomID; + + x = item->pos.x; + y = item->pos.y + height; + z = item->pos.z; + roomID = item->roomNumber; + floor = GetFloor(x, y, z, &roomID); + item->floor = GetHeight(floor, x, y, z); + if (item->roomNumber != roomID) { + ItemNewRoom(Lara.item_number, roomID); + } +} + /* * Inject function */ @@ -225,7 +243,7 @@ void Inject_Collide() { INJECT(0x00413480, GetNewRoom); INJECT(0x004134E0, ShiftItem); -// INJECT(0x00413520, UpdateLaraRoom); + INJECT(0x00413520, UpdateLaraRoom); // INJECT(0x00413580, GetTiltType); // INJECT(0x00413620, LaraBaddieCollision); // INJECT(0x004137C0, EffectSpaz); diff --git a/game/collide.h b/game/collide.h index eb74875..b5aa0e4 100644 --- a/game/collide.h +++ b/game/collide.h @@ -36,7 +36,7 @@ void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID); // 0x00413480 void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 -#define UpdateLaraRoom ((void(__cdecl*)(ITEM_INFO*, int)) 0x00413520) +void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 // 0x00413580: GetTiltType // 0x00413620: LaraBaddieCollision From 67b33b31f81a8869bee910fa05f0001334da7a1c Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 14:20:13 +0100 Subject: [PATCH 04/66] Decompiled GetTiltType() - Fixed FLOOR_INFO structure: pitRoom and skyRoom where not unsigned ! - Fixed another code style for FindGridShift() --- game/collide.cpp | 34 +++++++++++++++++++++++++++------- game/collide.h | 2 +- global/types.h | 6 +++--- 3 files changed, 31 insertions(+), 11 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 7c3d048..6add3e2 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -30,13 +30,15 @@ int __cdecl FindGridShift(int src, int dest) { int srcShift, destShift; srcShift = src >> WALL_SHIFT; destShift = dest >> WALL_SHIFT; - if (srcShift == destShift) - return 0; + if (srcShift == destShift) { + return 0; + } src &= 1023; - if (destShift <= srcShift) - return -1 - src; - else - return 1025 - src; + if (destShift <= srcShift) { + return -1 - src; + } else { + return 1025 - src; + } } int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite) { @@ -231,6 +233,24 @@ void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { } } +short __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { + short* data; + unsigned char i; + + for (i = floor->pitRoom; i != 255; i = floor->pitRoom) { + floor = &RoomInfo[i].floor[((z - RoomInfo[i].z) >> WALL_SHIFT) + RoomInfo[i].xSize * ((x - RoomInfo[i].x) >> WALL_SHIFT)]; + } + if (floor->index == 0) { + return 0; + } + data = &FloorData[floor->index]; + if (y + 512 >= floor->floor << 8 && *(BYTE*)data == 2) { + return data[1]; + } else { + return 0; + } +} + /* * Inject function */ @@ -244,7 +264,7 @@ void Inject_Collide() { INJECT(0x004134E0, ShiftItem); INJECT(0x00413520, UpdateLaraRoom); -// INJECT(0x00413580, GetTiltType); + INJECT(0x00413580, GetTiltType); // INJECT(0x00413620, LaraBaddieCollision); // INJECT(0x004137C0, EffectSpaz); // INJECT(0x00413840, CreatureCollision); diff --git a/game/collide.h b/game/collide.h index b5aa0e4..cd03681 100644 --- a/game/collide.h +++ b/game/collide.h @@ -38,7 +38,7 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 -// 0x00413580: GetTiltType +//short __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 // 0x00413620: LaraBaddieCollision // 0x004137C0: EffectSpaz diff --git a/global/types.h b/global/types.h index 47f91ee..861cc4f 100644 --- a/global/types.h +++ b/global/types.h @@ -1833,11 +1833,11 @@ typedef struct DoorInfos_t { } DOOR_INFOS; typedef struct FloorInfo_t { - __int16 index; + __int16 index; __int16 box; - char pitRoom; + unsigned char pitRoom; char floor; - char skyRoom; + unsigned char skyRoom; char ceiling; } FLOOR_INFO; From 24a0813f2a2d9108be4cf4fa3629c54fb224d989 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 14:21:59 +0100 Subject: [PATCH 05/66] Fixed GetTiltType() - This function used short instead of __int16 --- game/collide.cpp | 4 ++-- game/collide.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 6add3e2..0abe0f1 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -233,8 +233,8 @@ void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { } } -short __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { - short* data; +__int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { + __int16* data; unsigned char i; for (i = floor->pitRoom; i != 255; i = floor->pitRoom) { diff --git a/game/collide.h b/game/collide.h index cd03681..c296162 100644 --- a/game/collide.h +++ b/game/collide.h @@ -38,7 +38,7 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 -//short __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 +__int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 // 0x00413620: LaraBaddieCollision // 0x004137C0: EffectSpaz From 2e2003c3963c74c19613911b7c723994990f02be Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 14:35:02 +0100 Subject: [PATCH 06/66] Decompiled LaraBaddieCollision() --- game/collide.cpp | 59 +++++++++++++++++++++++++++++++++++++++++++++++- game/collide.h | 4 ++-- 2 files changed, 60 insertions(+), 3 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 0abe0f1..ef0531f 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -251,6 +251,63 @@ __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { } } +void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { + DOOR_INFOS* doors; + DOOR_INFO* door; + ITEM_INFO* item; + OBJECT_INFO* obj; + int x, y, z; + __int16 roomArray[20]; + __int16 roomCount; + __int16 itemID; + __int16 i; + + laraitem->hit_status = 0; + Lara.hit_direction = -1; + + // NOTE: added some nullptr check just in case something want wrong. + if (laraitem->hitPoints > 0) { + roomArray[0] = laraitem->roomNumber; + roomCount = 1; + doors = RoomInfo[roomArray[0]].doors; + if (doors) { + for (i = doors->wCount; i > 0; i--) { + door = doors[i].door; + if (door) { // NOTE: this check was not there in the original game + roomArray[roomCount++] = door->room; + } + } + } + if (roomCount > 0) { + itemID = RoomInfo[roomArray[0]].itemNumber; + if (itemID != -1) { + for (i = roomCount; i > 0; i--) { + item = &Items[itemID]; + if (item && item->collidable && item->status != ITEM_INVISIBLE) { // NOTE: "item" was not there in the original game + obj = &Objects[item->objectID]; + if (obj && obj->collision) { // NOTE: "obj" was not there in the original game + x = laraitem->pos.x - item->pos.x; + y = laraitem->pos.y - item->pos.y; + z = laraitem->pos.z - item->pos.z; + if (x > -4096 && x < 4096 && z > -4096 && z < 4096 && y > -4096 && y < 4096) { + obj->collision(itemID, laraitem, coll); + } + } + } + itemID = item->nextItem; + } + } + } + if (Lara.spaz_effect_count != 0) { + EffectSpaz(laraitem, coll); // NOTE: coll is not used ! + } + if (Lara.hit_direction == -1) { + Lara.hit_frame = 0; + } + InventoryChosen = -1; + } +} + /* * Inject function */ @@ -265,7 +322,7 @@ void Inject_Collide() { INJECT(0x004134E0, ShiftItem); INJECT(0x00413520, UpdateLaraRoom); INJECT(0x00413580, GetTiltType); -// INJECT(0x00413620, LaraBaddieCollision); + INJECT(0x00413620, LaraBaddieCollision); // INJECT(0x004137C0, EffectSpaz); // INJECT(0x00413840, CreatureCollision); // INJECT(0x004138C0, ObjectCollision); diff --git a/game/collide.h b/game/collide.h index c296162..62e36a0 100644 --- a/game/collide.h +++ b/game/collide.h @@ -39,8 +39,8 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 -// 0x00413620: LaraBaddieCollision -// 0x004137C0: EffectSpaz +void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413620 +#define EffectSpaz ((void(__cdecl*)(ITEM_INFO *, COLL_INFO *)) 0x004137C0) #define CreatureCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00413840) #define ObjectCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x004138C0) From be884fcf37c1ca1b1901000ea8fc89ad28fbdf0c Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 14:44:30 +0100 Subject: [PATCH 07/66] Fixed Tab For unknown reason CodeBlocks don't enable the tab character by default :x --- game/collide.cpp | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index ef0531f..004a338 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -27,17 +27,17 @@ #include "global/vars.h" int __cdecl FindGridShift(int src, int dest) { - int srcShift, destShift; + int srcShift, destShift; srcShift = src >> WALL_SHIFT; destShift = dest >> WALL_SHIFT; if (srcShift == destShift) { - return 0; + return 0; } src &= 1023; if (destShift <= srcShift) { - return -1 - src; + return -1 - src; } else { - return 1025 - src; + return 1025 - src; } } @@ -252,7 +252,7 @@ __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { } void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { - DOOR_INFOS* doors; + DOOR_INFOS* doors; DOOR_INFO* door; ITEM_INFO* item; OBJECT_INFO* obj; @@ -313,16 +313,16 @@ void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { */ void Inject_Collide() { // INJECT(0x004128D0, GetCollisionInfo); - INJECT(0x00412F90, FindGridShift); + INJECT(0x00412F90, FindGridShift); INJECT(0x00412FC0, CollideStaticObjects); INJECT(0x004133B0, GetNearByRooms); INJECT(0x00413480, GetNewRoom); - INJECT(0x004134E0, ShiftItem); - INJECT(0x00413520, UpdateLaraRoom); - INJECT(0x00413580, GetTiltType); - INJECT(0x00413620, LaraBaddieCollision); + INJECT(0x004134E0, ShiftItem); + INJECT(0x00413520, UpdateLaraRoom); + INJECT(0x00413580, GetTiltType); + INJECT(0x00413620, LaraBaddieCollision); // INJECT(0x004137C0, EffectSpaz); // INJECT(0x00413840, CreatureCollision); // INJECT(0x004138C0, ObjectCollision); From aac83ca0e0a90fc89b3b14992b6d20c98889b780 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 15:26:39 +0100 Subject: [PATCH 08/66] Decompiled EffectSpaz() - IDAPro is shit with structure then pointer, Lara.spaz_effect where Lara.last_pos.z + 2 --- game/collide.cpp | 14 +++++++++++++- game/collide.h | 2 +- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 004a338..1103964 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -24,6 +24,7 @@ #include "3dsystem/phd_math.h" #include "game/items.h" #include "game/control.h" +#include "game/sound.h" #include "global/vars.h" int __cdecl FindGridShift(int src, int dest) { @@ -308,6 +309,17 @@ void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { } } +void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll) { + Lara.hit_direction = (unsigned short)(laraitem->pos.rotY + 0x8000 - phd_atan(Lara.spaz_effect->pos.z - laraitem->pos.z, Lara.spaz_effect->pos.x - laraitem->pos.x) + 0x2000) >> W2V_SHIFT; + if (!Lara.hit_frame) { + PlaySoundEffect(31, &laraitem->pos, 0); + } + if (++Lara.hit_frame > 34) { + Lara.hit_frame = 34; + } + --Lara.spaz_effect_count; +} + /* * Inject function */ @@ -323,7 +335,7 @@ void Inject_Collide() { INJECT(0x00413520, UpdateLaraRoom); INJECT(0x00413580, GetTiltType); INJECT(0x00413620, LaraBaddieCollision); -// INJECT(0x004137C0, EffectSpaz); + INJECT(0x004137C0, EffectSpaz); // INJECT(0x00413840, CreatureCollision); // INJECT(0x004138C0, ObjectCollision); // INJECT(0x00413920, DoorCollision); diff --git a/game/collide.h b/game/collide.h index 62e36a0..ba50a78 100644 --- a/game/collide.h +++ b/game/collide.h @@ -40,7 +40,7 @@ void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413620 -#define EffectSpaz ((void(__cdecl*)(ITEM_INFO *, COLL_INFO *)) 0x004137C0) +void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004137C0 #define CreatureCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00413840) #define ObjectCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x004138C0) From cb2473c88ff199d52a6ac4bf58289ff93c167fa2 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 16:25:14 +0100 Subject: [PATCH 09/66] Decompiled CreatureCollision() - Added some define function. - Decompiled ObjectCollision() too. --- game/collide.cpp | 33 ++++++++++++++++++++++++++++++--- game/collide.h | 16 ++++++++-------- game/sphere.h | 2 +- 3 files changed, 39 insertions(+), 12 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 1103964..5cc72f2 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -25,6 +25,7 @@ #include "game/items.h" #include "game/control.h" #include "game/sound.h" +#include "game/sphere.h" #include "global/vars.h" int __cdecl FindGridShift(int src, int dest) { @@ -310,7 +311,7 @@ void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { } void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll) { - Lara.hit_direction = (unsigned short)(laraitem->pos.rotY + 0x8000 - phd_atan(Lara.spaz_effect->pos.z - laraitem->pos.z, Lara.spaz_effect->pos.x - laraitem->pos.x) + 0x2000) >> W2V_SHIFT; + Lara.hit_direction = (unsigned __int16)(laraitem->pos.rotY + PHD_180 - phd_atan(Lara.spaz_effect->pos.z - laraitem->pos.z, Lara.spaz_effect->pos.x - laraitem->pos.x) + PHD_90) >> W2V_SHIFT; if (!Lara.hit_frame) { PlaySoundEffect(31, &laraitem->pos, 0); } @@ -320,6 +321,32 @@ void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll) { --Lara.spaz_effect_count; } +void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { + ITEM_INFO* item; + + item = &Items[itemID]; + if (TestBoundsCollide(item, laraitem, coll->radius)) { + if (TestCollision(item, laraitem)) { + if (CHK_ANY(coll->flags, 0x8) && Lara.water_status != 1) { // NOTE: original checked "(Lara.water_status == 0) != 2" but it's always true ! + ItemPushLara(item, laraitem, coll, CHK_ANY(coll->flags, 0x10), FALSE); + } + } + } +} + +void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { + ITEM_INFO* item; + + item = &Items[itemID]; + if (TestBoundsCollide(item, laraitem, coll->radius)) { + if (TestCollision(item, laraitem)) { + if CHK_ANY(coll->flags, 0x8) { + ItemPushLara(item, laraitem, coll, FALSE, TRUE); + } + } + } +} + /* * Inject function */ @@ -336,8 +363,8 @@ void Inject_Collide() { INJECT(0x00413580, GetTiltType); INJECT(0x00413620, LaraBaddieCollision); INJECT(0x004137C0, EffectSpaz); -// INJECT(0x00413840, CreatureCollision); -// INJECT(0x004138C0, ObjectCollision); + INJECT(0x00413840, CreatureCollision); + INJECT(0x004138C0, ObjectCollision); // INJECT(0x00413920, DoorCollision); // INJECT(0x004139A0, TrapCollision); // INJECT(0x00413A10, ItemPushLara); diff --git a/game/collide.h b/game/collide.h index ba50a78..b840c0a 100644 --- a/game/collide.h +++ b/game/collide.h @@ -42,16 +42,16 @@ __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x004135 void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413620 void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004137C0 -#define CreatureCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00413840) -#define ObjectCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x004138C0) +void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413840 +void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004138C0 // 0x00413920: DoorCollision // 0x004139A0: TrapCollision -// 0x00413A10: ItemPushLara -// 0x00413D20: TestBoundsCollide -// 0x00413DF0: TestLaraPosition -// 0x00413F30: AlignLaraPosition -// 0x00414070: MoveLaraPosition -// 0x00414200: Move3DPosTo3DPos +#define ItemPushLara ((void(__cdecl*)(ITEM_INFO*, ITEM_INFO*, COLL_INFO*, BOOL, BOOL)) 0x00413A10) +#define TestBoundsCollide ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*, int)) 0x00413D20) +#define TestLaraPosition ((BOOL(__cdecl*)(__int16*, ITEM_INFO*, ITEM_INFO*)) 0x00413DF0) +#define AlignLaraPosition ((void(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00413F30) +#define MoveLaraPosition ((BOOL(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00414070) +#define Move3DPosTo3DPos ((BOOL(__cdecl*)(PHD_3DPOS*, PHD_3DPOS*, int, __int16)) 0x00414200) #endif // COLLIDE_H_INCLUDED diff --git a/game/sphere.h b/game/sphere.h index fc8431a..975c102 100644 --- a/game/sphere.h +++ b/game/sphere.h @@ -27,7 +27,7 @@ /* * Function list */ -// 0x0043FA60: TestCollision +#define TestCollision ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*)) 0x0043FA60) // 0x0043FB90: GetSpheres #define GetJointAbsPosition ((void(__cdecl*)(ITEM_INFO*, PHD_VECTOR*, int)) 0x0043FE70) From 13fa7be23c6b93218c56800538bf8f125d40e18e Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 16:37:31 +0100 Subject: [PATCH 10/66] Decompiled DoorCollision() --- game/collide.cpp | 19 ++++++++++++++++++- game/collide.h | 2 +- 2 files changed, 19 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 5cc72f2..aee277e 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -347,6 +347,23 @@ void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* col } } +void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { + ITEM_INFO* item; + + item = &Items[itemID]; + if (TestBoundsCollide(item, laraitem, coll->radius)) { + if (TestCollision(item, laraitem)) { + if CHK_ANY(coll->flags, 0x8) { + if (item->currentAnimState == item->goalAnimState) { + ItemPushLara(item, laraitem, coll, FALSE, TRUE); + } else { + ItemPushLara(item, laraitem, coll, CHK_ANY(coll->flags, 0x10), TRUE); + } + } + } + } +} + /* * Inject function */ @@ -365,7 +382,7 @@ void Inject_Collide() { INJECT(0x004137C0, EffectSpaz); INJECT(0x00413840, CreatureCollision); INJECT(0x004138C0, ObjectCollision); -// INJECT(0x00413920, DoorCollision); + INJECT(0x00413920, DoorCollision); // INJECT(0x004139A0, TrapCollision); // INJECT(0x00413A10, ItemPushLara); // INJECT(0x00413D20, TestBoundsCollide); diff --git a/game/collide.h b/game/collide.h index b840c0a..3caa6bf 100644 --- a/game/collide.h +++ b/game/collide.h @@ -45,7 +45,7 @@ void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004137C0 void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413840 void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004138C0 -// 0x00413920: DoorCollision +void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413920 // 0x004139A0: TrapCollision #define ItemPushLara ((void(__cdecl*)(ITEM_INFO*, ITEM_INFO*, COLL_INFO*, BOOL, BOOL)) 0x00413A10) #define TestBoundsCollide ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*, int)) 0x00413D20) From 3e82e1de5dec82ce007034e84f77098dba2cc56f Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 16:51:32 +0100 Subject: [PATCH 11/66] Decompiled TrapCollision() --- game/collide.cpp | 15 ++++++++++++++- game/collide.h | 2 +- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index aee277e..6ac60a2 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -364,6 +364,19 @@ void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) } } +void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { + ITEM_INFO* item; + + item = &Items[itemID]; + if (item->status == ITEM_ACTIVE) { + if (TestBoundsCollide(item, laraitem, coll->radius)) { + TestCollision(item, laraitem); + } + } else if (item->status != ITEM_INVISIBLE) { + ObjectCollision(itemID, laraitem, coll); + } +} + /* * Inject function */ @@ -383,7 +396,7 @@ void Inject_Collide() { INJECT(0x00413840, CreatureCollision); INJECT(0x004138C0, ObjectCollision); INJECT(0x00413920, DoorCollision); -// INJECT(0x004139A0, TrapCollision); + INJECT(0x004139A0, TrapCollision); // INJECT(0x00413A10, ItemPushLara); // INJECT(0x00413D20, TestBoundsCollide); // INJECT(0x00413DF0, TestLaraPosition); diff --git a/game/collide.h b/game/collide.h index 3caa6bf..6fc1f77 100644 --- a/game/collide.h +++ b/game/collide.h @@ -46,7 +46,7 @@ void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* c void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004138C0 void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413920 -// 0x004139A0: TrapCollision +void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004139A0 #define ItemPushLara ((void(__cdecl*)(ITEM_INFO*, ITEM_INFO*, COLL_INFO*, BOOL, BOOL)) 0x00413A10) #define TestBoundsCollide ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*, int)) 0x00413D20) #define TestLaraPosition ((BOOL(__cdecl*)(__int16*, ITEM_INFO*, ITEM_INFO*)) 0x00413DF0) From 8005bd050aa1ac9e03e70eabf7b0ca0b99ba519a Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 18:26:36 +0100 Subject: [PATCH 12/66] Decompiled ItemPushLara() and TestBoundsCollide() --- game/collide.cpp | 117 ++++++++++++++++++++++++++++++++++++++++++++++- game/collide.h | 6 +-- 2 files changed, 118 insertions(+), 5 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 6ac60a2..272e991 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -22,6 +22,7 @@ #include "global/precompiled.h" #include "game/collide.h" #include "3dsystem/phd_math.h" +#include "game/draw.h" #include "game/items.h" #include "game/control.h" #include "game/sound.h" @@ -377,6 +378,118 @@ void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) } } +void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush) { + int x, z, rx, rz; + int l, r, t, b; + int bndMin, bndMax; + int radius; + __int16* bounds; + __int16 c, s; + __int16 minx, maxx, minz, maxz; + __int16 oldFacing; + + x = laraitem->pos.x - item->pos.x; + z = laraitem->pos.z - item->pos.z; + s = phd_sin(item->pos.rotY); + c = phd_cos(item->pos.rotY); + rx = (x * c - z * s) >> W2V_SHIFT; + rz = (x * s + z * c) >> W2V_SHIFT; + bounds = GetBestFrame(item); + minx = bounds[0]; + maxx = bounds[1]; + minz = bounds[4]; + maxz = bounds[5]; + + if (bigpush) { + radius = coll->radius; + maxx += radius; + minz -= radius; + maxz += radius; + minx -= radius; + } + + if (rx >= minx && rx <= maxx && rz >= minz && rz <= maxz) { + l = rx - minx; + r = maxx - rx; + t = maxz - rz; + b = rz - minz; + + if (r <= l && r <= t && r <= b) { + rx += r; + } else if (l <= r && l <= t && l <= b) { + rx -= l; + } else if (t <= r && t <= l && t <= b) { + rz += t; + } else { + rz -= b; + } + + laraitem->pos.x = item->pos.x + ((rz * s + rx * c) >> W2V_SHIFT); + laraitem->pos.z = item->pos.z + ((rz * c - rx * s) >> W2V_SHIFT); + + bndMin = (bounds[1] + bounds[0]) / 2; + bndMax = (bounds[5] + bounds[4]) / 2; + rx -= (bndMax * s + bndMin * c) >> W2V_SHIFT; + rz -= (bndMax * c - bndMin * s) >> W2V_SHIFT; + + if (spazon && bounds[3] - bounds[2] > 256) { + Lara.hit_direction = (unsigned __int16)(laraitem->pos.rotY + PHD_180 - phd_atan(rz, rx) + PHD_90) >> W2V_SHIFT; + if (!Lara.hit_frame) { + PlaySoundEffect(31, &laraitem->pos, 0); + } + if (++Lara.hit_frame > 34) { + Lara.hit_frame = 34; + } + } + + x = coll->old.x; + z = coll->old.z; + oldFacing = coll->facing; + coll->badPos = -NO_HEIGHT; + coll->badNeg = -384; + coll->badCeiling = 0; + coll->facing = phd_atan(laraitem->pos.z - z, laraitem->pos.x - x); + GetCollisionInfo(coll, laraitem->pos.x, laraitem->pos.y, laraitem->pos.z, laraitem->roomNumber, 762); + coll->facing = oldFacing; + if (coll->collType == 0) { + coll->old.x = laraitem->pos.x; + coll->old.y = laraitem->pos.y; + coll->old.z = laraitem->pos.z; + UpdateLaraRoom(laraitem, -10); + } else { + laraitem->pos.x = coll->old.x; + laraitem->pos.z = coll->old.z; + } + } +} + +BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius) { + __int16 *boundItem; + __int16 *boundLara; + int x, z, s, c; + int rx, rz; + + boundItem = GetBestFrame(item); + boundLara = GetBestFrame(laraitem); + + if (item->pos.y + boundItem[3] > item->pos.y + boundLara[2] && item->pos.y + boundItem[2] < item->pos.y + boundLara[3]) { + c = phd_cos(item->pos.rotY); + s = phd_sin(item->pos.rotY); + x = laraitem->pos.x - item->pos.x; + z = laraitem->pos.z - item->pos.z; + rx = (c * x - s * z) >> W2V_SHIFT; + rz = (s * x + c * z) >> W2V_SHIFT; + if (rx >= boundItem[0] - radius && + rx <= radius + boundItem[1] && + rz >= boundItem[4] - radius && + rz <= radius + boundItem[5]) { + return TRUE; + } + } + + return FALSE; +} + /* * Inject function */ @@ -397,8 +510,8 @@ void Inject_Collide() { INJECT(0x004138C0, ObjectCollision); INJECT(0x00413920, DoorCollision); INJECT(0x004139A0, TrapCollision); -// INJECT(0x00413A10, ItemPushLara); -// INJECT(0x00413D20, TestBoundsCollide); + INJECT(0x00413A10, ItemPushLara); + INJECT(0x00413D20, TestBoundsCollide); // INJECT(0x00413DF0, TestLaraPosition); // INJECT(0x00413F30, AlignLaraPosition); // INJECT(0x00414070, MoveLaraPosition); diff --git a/game/collide.h b/game/collide.h index 6fc1f77..3c5231c 100644 --- a/game/collide.h +++ b/game/collide.h @@ -27,7 +27,7 @@ /* * Function list */ -// 0x004128D0: GetCollisionInfo +#define GetCollisionInfo ((void(__cdecl*)(COLL_INFO*, int, int, int, __int16, int)) 0x004128D0) int __cdecl FindGridShift(int src, int dest); // 0x00412F90 int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite); // 0x00412FC0 @@ -47,8 +47,8 @@ void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* col void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413920 void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004139A0 -#define ItemPushLara ((void(__cdecl*)(ITEM_INFO*, ITEM_INFO*, COLL_INFO*, BOOL, BOOL)) 0x00413A10) -#define TestBoundsCollide ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*, int)) 0x00413D20) +void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 +BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius); // 0x00413D20 #define TestLaraPosition ((BOOL(__cdecl*)(__int16*, ITEM_INFO*, ITEM_INFO*)) 0x00413DF0) #define AlignLaraPosition ((void(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00413F30) #define MoveLaraPosition ((BOOL(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00414070) From ac4422318ac5c4acb53647c51dbb4a71d2542eba Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 19:03:49 +0100 Subject: [PATCH 13/66] Decompiled TestLaraPosition() --- game/collide.cpp | 37 ++++++++++++++++++++++++++++++++++++- game/collide.h | 2 +- 2 files changed, 37 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 272e991..387acd7 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -22,6 +22,7 @@ #include "global/precompiled.h" #include "game/collide.h" #include "3dsystem/phd_math.h" +#include "3dsystem/3d_gen.h" #include "game/draw.h" #include "game/items.h" #include "game/control.h" @@ -490,6 +491,40 @@ BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius) return FALSE; } +BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem) { + int x, y, z; + int xBound, yBound, zBound; + short yRot, xRot, zRot; + + xRot = laraitem->pos.rotX - item->pos.rotX; + yRot = laraitem->pos.rotY - item->pos.rotY; + zRot = laraitem->pos.rotZ - item->pos.rotZ; + + if (xRot < bounds[6] || xRot > bounds[7] || + yRot < bounds[8] || yRot > bounds[9] || + zRot < bounds[10] || zRot > bounds[11]) { + return 0; + } + + x = laraitem->pos.x - item->pos.x; + y = laraitem->pos.y - item->pos.y; + z = laraitem->pos.z - item->pos.z; + + phd_PushUnitMatrix(); + phd_RotYXZ(item->pos.rotY, item->pos.rotX, item->pos.rotZ); + xBound = (x * PhdMatrixPtr->_00 + y * PhdMatrixPtr->_10 + z * PhdMatrixPtr->_20) >> W2V_SHIFT; + yBound = (x * PhdMatrixPtr->_01 + y * PhdMatrixPtr->_11 + z * PhdMatrixPtr->_21) >> W2V_SHIFT; + zBound = (x * PhdMatrixPtr->_02 + y * PhdMatrixPtr->_12 + z * PhdMatrixPtr->_22) >> W2V_SHIFT; + phd_PopMatrix(); + + return xBound >= bounds[0] + && xBound <= bounds[1] + && yBound >= bounds[2] + && yBound <= bounds[3] + && zBound >= bounds[4] + && zBound <= bounds[5]; +} + /* * Inject function */ @@ -512,7 +547,7 @@ void Inject_Collide() { INJECT(0x004139A0, TrapCollision); INJECT(0x00413A10, ItemPushLara); INJECT(0x00413D20, TestBoundsCollide); -// INJECT(0x00413DF0, TestLaraPosition); + INJECT(0x00413DF0, TestLaraPosition); // INJECT(0x00413F30, AlignLaraPosition); // INJECT(0x00414070, MoveLaraPosition); // INJECT(0x00414200, Move3DPosTo3DPos); diff --git a/game/collide.h b/game/collide.h index 3c5231c..cb06121 100644 --- a/game/collide.h +++ b/game/collide.h @@ -49,7 +49,7 @@ void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004139A0 void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius); // 0x00413D20 -#define TestLaraPosition ((BOOL(__cdecl*)(__int16*, ITEM_INFO*, ITEM_INFO*)) 0x00413DF0) +BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413DF0 #define AlignLaraPosition ((void(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00413F30) #define MoveLaraPosition ((BOOL(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00414070) #define Move3DPosTo3DPos ((BOOL(__cdecl*)(PHD_3DPOS*, PHD_3DPOS*, int, __int16)) 0x00414200) From 2251d4475f6b0e5541dee94ca61c8cf5e8f368f0 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 19:17:21 +0100 Subject: [PATCH 14/66] Decompiled AlignLaraPosition() --- game/collide.cpp | 31 ++++++++++++++++++++++++++++++- game/collide.h | 2 +- 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 387acd7..d1d637b 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -525,6 +525,35 @@ BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* larai && zBound <= bounds[5]; } +void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* laraitem) { + FLOOR_INFO* floor; + int x, y, z; + int height, ceiling; + __int16 roomID; + + laraitem->pos.rotX = item->pos.rotX; + laraitem->pos.rotY = item->pos.rotY; + laraitem->pos.rotZ = item->pos.rotZ; + + phd_PushUnitMatrix(); + phd_RotYXZ(item->pos.rotY, item->pos.rotX, item->pos.rotZ); + x = item->pos.x + ((vec->x * PhdMatrixPtr->_00 + vec->y * PhdMatrixPtr->_01 + vec->z * PhdMatrixPtr->_02) >> W2V_SHIFT); + y = item->pos.y + ((vec->x * PhdMatrixPtr->_10 + vec->y * PhdMatrixPtr->_11 + vec->z * PhdMatrixPtr->_12) >> W2V_SHIFT); + z = item->pos.z + ((vec->x * PhdMatrixPtr->_20 + vec->y * PhdMatrixPtr->_21 + vec->z * PhdMatrixPtr->_22) >> W2V_SHIFT); + phd_PopMatrix(); + + roomID = laraitem->roomNumber; + floor = GetFloor(x, y, z, &roomID); + height = GetHeight(floor, x, y, z); + ceiling = GetCeiling(floor, x, y, z); + + if (ABS(height - laraitem->pos.y) <= 256 && ABS(ceiling - laraitem->pos.y) >= 762) { + laraitem->pos.x = x; + laraitem->pos.y = y; + laraitem->pos.z = z; + } +} + /* * Inject function */ @@ -548,7 +577,7 @@ void Inject_Collide() { INJECT(0x00413A10, ItemPushLara); INJECT(0x00413D20, TestBoundsCollide); INJECT(0x00413DF0, TestLaraPosition); -// INJECT(0x00413F30, AlignLaraPosition); + INJECT(0x00413F30, AlignLaraPosition); // INJECT(0x00414070, MoveLaraPosition); // INJECT(0x00414200, Move3DPosTo3DPos); } diff --git a/game/collide.h b/game/collide.h index cb06121..e94f199 100644 --- a/game/collide.h +++ b/game/collide.h @@ -50,7 +50,7 @@ void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius); // 0x00413D20 BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413DF0 -#define AlignLaraPosition ((void(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00413F30) +void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413F30 #define MoveLaraPosition ((BOOL(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00414070) #define Move3DPosTo3DPos ((BOOL(__cdecl*)(PHD_3DPOS*, PHD_3DPOS*, int, __int16)) 0x00414200) From 0ab69ddd3f87015df9533b4f7f46ab9c897d670e Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 19:51:03 +0100 Subject: [PATCH 15/66] Decompiled MoveLaraPosition() --- game/collide.cpp | 47 ++++++++++++++++++++++++++++++++++++++++++----- game/collide.h | 4 ++-- 2 files changed, 44 insertions(+), 7 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index d1d637b..d4c0b7b 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -525,7 +525,7 @@ BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* larai && zBound <= bounds[5]; } -void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* laraitem) { +void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem) { FLOOR_INFO* floor; int x, y, z; int height, ceiling; @@ -537,9 +537,9 @@ void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* lara phd_PushUnitMatrix(); phd_RotYXZ(item->pos.rotY, item->pos.rotX, item->pos.rotZ); - x = item->pos.x + ((vec->x * PhdMatrixPtr->_00 + vec->y * PhdMatrixPtr->_01 + vec->z * PhdMatrixPtr->_02) >> W2V_SHIFT); - y = item->pos.y + ((vec->x * PhdMatrixPtr->_10 + vec->y * PhdMatrixPtr->_11 + vec->z * PhdMatrixPtr->_12) >> W2V_SHIFT); - z = item->pos.z + ((vec->x * PhdMatrixPtr->_20 + vec->y * PhdMatrixPtr->_21 + vec->z * PhdMatrixPtr->_22) >> W2V_SHIFT); + x = item->pos.x + ((pos->x * PhdMatrixPtr->_00 + pos->y * PhdMatrixPtr->_01 + pos->z * PhdMatrixPtr->_02) >> W2V_SHIFT); + y = item->pos.y + ((pos->x * PhdMatrixPtr->_10 + pos->y * PhdMatrixPtr->_11 + pos->z * PhdMatrixPtr->_12) >> W2V_SHIFT); + z = item->pos.z + ((pos->x * PhdMatrixPtr->_20 + pos->y * PhdMatrixPtr->_21 + pos->z * PhdMatrixPtr->_22) >> W2V_SHIFT); phd_PopMatrix(); roomID = laraitem->roomNumber; @@ -554,6 +554,43 @@ void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* lara } } +BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem) { + PHD_3DPOS newpos; + FLOOR_INFO* floor; + int height, distance; + int xDist, yDist, zDist; + __int16 roomID; + + newpos.rotX = item->pos.rotX; + newpos.rotY = item->pos.rotY; + newpos.rotZ = item->pos.rotZ; + + phd_PushUnitMatrix(); + phd_RotYXZ(item->pos.rotY, item->pos.rotX, item->pos.rotZ); + newpos.x = item->pos.x + ((pos->x * PhdMatrixPtr->_00 + pos->y * PhdMatrixPtr->_01 + pos->z * PhdMatrixPtr->_02) >> W2V_SHIFT); + newpos.y = item->pos.y + ((pos->x * PhdMatrixPtr->_10 + pos->y * PhdMatrixPtr->_11 + pos->z * PhdMatrixPtr->_12) >> W2V_SHIFT); + newpos.z = item->pos.z + ((pos->x * PhdMatrixPtr->_20 + pos->y * PhdMatrixPtr->_21 + pos->z * PhdMatrixPtr->_22) >> W2V_SHIFT); + phd_PopMatrix(); + + if (item->objectID != ID_FLARE_ITEM) { + return Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); + } + + roomID = laraitem->roomNumber; + floor = GetFloor(newpos.x, newpos.y, newpos.z, &roomID); + height = GetHeight(floor, newpos.x, newpos.y, newpos.z); + + if (ABS(height - laraitem->pos.y) > 512) { + return FALSE; + } + + zDist = SQR(newpos.z - laraitem->pos.z); + yDist = SQR(newpos.y - laraitem->pos.y); + xDist = SQR(newpos.x - laraitem->pos.z); + distance = phd_sqrt(xDist + yDist + zDist); + return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); +} + /* * Inject function */ @@ -578,6 +615,6 @@ void Inject_Collide() { INJECT(0x00413D20, TestBoundsCollide); INJECT(0x00413DF0, TestLaraPosition); INJECT(0x00413F30, AlignLaraPosition); -// INJECT(0x00414070, MoveLaraPosition); + INJECT(0x00414070, MoveLaraPosition); // INJECT(0x00414200, Move3DPosTo3DPos); } diff --git a/game/collide.h b/game/collide.h index e94f199..4729c78 100644 --- a/game/collide.h +++ b/game/collide.h @@ -50,8 +50,8 @@ void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius); // 0x00413D20 BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413DF0 -void __cdecl AlignLaraPosition(PHD_VECTOR* vec, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413F30 -#define MoveLaraPosition ((BOOL(__cdecl*)(PHD_VECTOR*, ITEM_INFO*, ITEM_INFO*)) 0x00414070) +void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413F30 +BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00414070 #define Move3DPosTo3DPos ((BOOL(__cdecl*)(PHD_3DPOS*, PHD_3DPOS*, int, __int16)) 0x00414200) #endif // COLLIDE_H_INCLUDED From e429379bc34a6de38bab59494467a05fef580822 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 20:05:30 +0100 Subject: [PATCH 16/66] Decompiled Move3DPosTo3DPos() Finished collide.cpp. PS: GetCollisionInfo() was already decompiled by @asasas9500 on PR #27 --- game/collide.cpp | 58 +++++++++++++++++++++++++++++++++++++++++++++++- game/collide.h | 2 +- 2 files changed, 58 insertions(+), 2 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index d4c0b7b..cbb2698 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -591,6 +591,62 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* larai return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); } +BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __int16 angleAdder) { + int x, y, z, distance; + short xRot, yRot, zRot; + + x = dest->x - src->x; + y = dest->y - src->y; + z = dest->z - src->z; + distance = phd_sqrt(SQR(z) + SQR(y) + SQR(x)); + if (velocity < distance) { + src->x += velocity * x / distance; + src->y += velocity * y / distance; + src->z += velocity * z / distance; + } else { + src->x = dest->x; + src->y = dest->y; + src->z = dest->z; + } + + xRot = dest->rotX - src->rotX; + yRot = dest->rotY - src->rotY; + zRot = dest->rotZ - src->rotZ; + if (xRot <= angleAdder) { + if (xRot >= -angleAdder) { + src->rotX = dest->rotX; + } else { + src->rotX -= angleAdder; + } + } else { + src->rotX += angleAdder; + } + if (yRot <= angleAdder) { + if (yRot >= -angleAdder) { + src->rotY = dest->rotY; + } else { + src->rotY -= angleAdder; + } + } else { + src->rotY += angleAdder; + } + if (zRot <= angleAdder) { + if (zRot >= -angleAdder) { + src->rotZ = dest->rotZ; + } else { + src->rotZ -= angleAdder; + } + } else { + src->rotZ += angleAdder; + } + return src->x == dest->x + && src->y == dest->y + && src->z == dest->z + && src->rotX == dest->rotX + && src->rotY == dest->rotY + && src->rotZ == dest->rotZ; +} + /* * Inject function */ @@ -616,5 +672,5 @@ void Inject_Collide() { INJECT(0x00413DF0, TestLaraPosition); INJECT(0x00413F30, AlignLaraPosition); INJECT(0x00414070, MoveLaraPosition); -// INJECT(0x00414200, Move3DPosTo3DPos); + INJECT(0x00414200, Move3DPosTo3DPos); } diff --git a/game/collide.h b/game/collide.h index 4729c78..40b1865 100644 --- a/game/collide.h +++ b/game/collide.h @@ -52,6 +52,6 @@ BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius) BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413DF0 void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413F30 BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00414070 -#define Move3DPosTo3DPos ((BOOL(__cdecl*)(PHD_3DPOS*, PHD_3DPOS*, int, __int16)) 0x00414200) +BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __int16 angleAdder); // 0x00414200 #endif // COLLIDE_H_INCLUDED From 290c8599d09d7bf910a1965aa1a57bc890d8dec5 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 20:16:59 +0100 Subject: [PATCH 17/66] Removing some empty line (collide) - Removing empty line between function in both .h and .cpp. - Fixed a short to __int16. --- game/collide.cpp | 4 +--- game/collide.h | 6 ------ 2 files changed, 1 insertion(+), 9 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index cbb2698..a39e536 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -593,7 +593,7 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* larai BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __int16 angleAdder) { int x, y, z, distance; - short xRot, yRot, zRot; + __int16 xRot, yRot, zRot; x = dest->x - src->x; y = dest->y - src->y; @@ -653,11 +653,9 @@ BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __i void Inject_Collide() { // INJECT(0x004128D0, GetCollisionInfo); INJECT(0x00412F90, FindGridShift); - INJECT(0x00412FC0, CollideStaticObjects); INJECT(0x004133B0, GetNearByRooms); INJECT(0x00413480, GetNewRoom); - INJECT(0x004134E0, ShiftItem); INJECT(0x00413520, UpdateLaraRoom); INJECT(0x00413580, GetTiltType); diff --git a/game/collide.h b/game/collide.h index 40b1865..452deec 100644 --- a/game/collide.h +++ b/game/collide.h @@ -29,22 +29,16 @@ */ #define GetCollisionInfo ((void(__cdecl*)(COLL_INFO*, int, int, int, __int16, int)) 0x004128D0) int __cdecl FindGridShift(int src, int dest); // 0x00412F90 - int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite); // 0x00412FC0 void __cdecl GetNearByRooms(int x, int y, int z, int r, int h, __int16 roomID); // 0x004133B0 void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID); // 0x00413480 - void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 - void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 - __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413620 void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004137C0 - void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413840 void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004138C0 - void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413920 void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004139A0 void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 From d6c46fddaf0e3855b2094fd67784a519fc47011e Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 20:19:04 +0100 Subject: [PATCH 18/66] Fixed missing tab Normally it was the last change. --- global/types.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/global/types.h b/global/types.h index 861cc4f..20bb191 100644 --- a/global/types.h +++ b/global/types.h @@ -1833,11 +1833,11 @@ typedef struct DoorInfos_t { } DOOR_INFOS; typedef struct FloorInfo_t { - __int16 index; + __int16 index; __int16 box; - unsigned char pitRoom; + unsigned char pitRoom; char floor; - unsigned char skyRoom; + unsigned char skyRoom; char ceiling; } FLOOR_INFO; From 1fc778984296c94404bf73bd344b98f993c53e69 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 20:29:34 +0100 Subject: [PATCH 19/66] Fixed another missing tab It was when i started and i found out about CodeBlocks not replacing space by tab --- game/collide.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index a39e536..03c023c 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -213,7 +213,7 @@ void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID) { } void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { - item->pos.x += coll->shift.x; + item->pos.x += coll->shift.x; item->pos.y += coll->shift.y; item->pos.z += coll->shift.z; coll->shift.z = 0; @@ -222,7 +222,7 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { } void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { - FLOOR_INFO* floor; + FLOOR_INFO* floor; int x, y, z; short roomID; @@ -245,13 +245,13 @@ __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { floor = &RoomInfo[i].floor[((z - RoomInfo[i].z) >> WALL_SHIFT) + RoomInfo[i].xSize * ((x - RoomInfo[i].x) >> WALL_SHIFT)]; } if (floor->index == 0) { - return 0; + return 0; } data = &FloorData[floor->index]; if (y + 512 >= floor->floor << 8 && *(BYTE*)data == 2) { - return data[1]; + return data[1]; } else { - return 0; + return 0; } } From 305f38a18c46cf6f5102148c6835a78db8cceba3 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 15 Mar 2022 20:34:36 +0100 Subject: [PATCH 20/66] Update TR2_progress.txt --- TR2_progress.txt | 32 ++++++++++++++++---------------- 1 file changed, 16 insertions(+), 16 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 7b8410a..3a5aaae 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -194,21 +194,21 @@ x function is unused / included in another function 0x00412FC0: + CollideStaticObjects 0x004133B0: + GetNearByRooms 0x00413480: + GetNewRoom -0x004134E0: ShiftItem -0x00413520: * UpdateLaraRoom -0x00413580: GetTiltType -0x00413620: LaraBaddieCollision -0x004137C0: EffectSpaz -0x00413840: * CreatureCollision -0x004138C0: * ObjectCollision -0x00413920: DoorCollision -0x004139A0: TrapCollision -0x00413A10: ItemPushLara -0x00413D20: TestBoundsCollide -0x00413DF0: TestLaraPosition -0x00413F30: AlignLaraPosition -0x00414070: MoveLaraPosition -0x00414200: Move3DPosTo3DPos +0x004134E0: + ShiftItem +0x00413520: + UpdateLaraRoom +0x00413580: + GetTiltType +0x00413620: + LaraBaddieCollision +0x004137C0: + EffectSpaz +0x00413840: + CreatureCollision +0x004138C0: + ObjectCollision +0x00413920: + DoorCollision +0x004139A0: + TrapCollision +0x00413A10: + ItemPushLara +0x00413D20: + TestBoundsCollide +0x00413DF0: + TestLaraPosition +0x00413F30: + AlignLaraPosition +0x00414070: + MoveLaraPosition +0x00414200: + Move3DPosTo3DPos game/control.cpp 0x00414370: + ControlPhase @@ -894,7 +894,7 @@ x function is unused / included in another function 0x0043FA30: + SOUND_Init game/sphere.cpp -0x0043FA60: TestCollision +0x0043FA60: * TestCollision 0x0043FB90: GetSpheres 0x0043FE70: * GetJointAbsPosition 0x00440010: * BaddieBiteEffect From f287657326604e2e04d6b15b605130915798581e Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Fri, 18 Mar 2022 09:48:00 +0100 Subject: [PATCH 21/66] Fixed some review from @asasas9500 - Fixed wrong variable type. - Fixed left pointer to right pointer. - Fixed missing "+" in TR2_progress.txt - Fixed missing LWS_Underwater in CreatureCollision() --- TR2_progress.txt | 2 +- game/collide.cpp | 83 +++++++++++++++++++++--------------------------- game/collide.h | 30 ++++++++--------- global/types.h | 4 +-- 4 files changed, 55 insertions(+), 64 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 3a5aaae..2b30807 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -190,7 +190,7 @@ x function is unused / included in another function game/collide.cpp 0x004128D0: GetCollisionInfo -0x00412F90: FindGridShift +0x00412F90: + FindGridShift 0x00412FC0: + CollideStaticObjects 0x004133B0: + GetNearByRooms 0x00413480: + GetNewRoom diff --git a/game/collide.cpp b/game/collide.cpp index 03c023c..5458aa1 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -21,8 +21,8 @@ #include "global/precompiled.h" #include "game/collide.h" -#include "3dsystem/phd_math.h" #include "3dsystem/3d_gen.h" +#include "3dsystem/phd_math.h" #include "game/draw.h" #include "game/items.h" #include "game/control.h" @@ -31,9 +31,8 @@ #include "global/vars.h" int __cdecl FindGridShift(int src, int dest) { - int srcShift, destShift; - srcShift = src >> WALL_SHIFT; - destShift = dest >> WALL_SHIFT; + int srcShift = src >> WALL_SHIFT; + int destShift = dest >> WALL_SHIFT; if (srcShift == destShift) { return 0; } @@ -212,7 +211,7 @@ void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID) { DrawRoomsArray[DrawRoomsCount++] = roomID; } -void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { +void __cdecl ShiftItem(ITEM_INFO *item, COLL_INFO *coll) { item->pos.x += coll->shift.x; item->pos.y += coll->shift.y; item->pos.z += coll->shift.z; @@ -221,10 +220,10 @@ void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll) { coll->shift.x = 0; } -void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { - FLOOR_INFO* floor; +void __cdecl UpdateLaraRoom(ITEM_INFO *item, int height) { + FLOOR_INFO *floor; int x, y, z; - short roomID; + __int16 roomID; x = item->pos.x; y = item->pos.y + height; @@ -237,9 +236,9 @@ void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height) { } } -__int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { - __int16* data; - unsigned char i; +__int16 __cdecl GetTiltType(FLOOR_INFO *floor, int x, int y, int z) { + __int16 *data; + BYTE i; for (i = floor->pitRoom; i != 255; i = floor->pitRoom) { floor = &RoomInfo[i].floor[((z - RoomInfo[i].z) >> WALL_SHIFT) + RoomInfo[i].xSize * ((x - RoomInfo[i].x) >> WALL_SHIFT)]; @@ -255,11 +254,11 @@ __int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z) { } } -void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { - DOOR_INFOS* doors; - DOOR_INFO* door; - ITEM_INFO* item; - OBJECT_INFO* obj; +void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll) { + DOOR_INFOS *doors; + DOOR_INFO *door; + ITEM_INFO *item; + OBJECT_INFO *obj; int x, y, z; __int16 roomArray[20]; __int16 roomCount; @@ -312,8 +311,8 @@ void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll) { } } -void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll) { - Lara.hit_direction = (unsigned __int16)(laraitem->pos.rotY + PHD_180 - phd_atan(Lara.spaz_effect->pos.z - laraitem->pos.z, Lara.spaz_effect->pos.x - laraitem->pos.x) + PHD_90) >> W2V_SHIFT; +void __cdecl EffectSpaz(ITEM_INFO *laraitem, COLL_INFO *coll) { + Lara.hit_direction = (UINT16)(laraitem->pos.rotY + PHD_180 - phd_atan(Lara.spaz_effect->pos.z - laraitem->pos.z, Lara.spaz_effect->pos.x - laraitem->pos.x) + PHD_90) >> W2V_SHIFT; if (!Lara.hit_frame) { PlaySoundEffect(31, &laraitem->pos, 0); } @@ -323,23 +322,19 @@ void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll) { --Lara.spaz_effect_count; } -void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { - ITEM_INFO* item; - - item = &Items[itemID]; +void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll) { + ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { - if (CHK_ANY(coll->flags, 0x8) && Lara.water_status != 1) { // NOTE: original checked "(Lara.water_status == 0) != 2" but it's always true ! + if (CHK_ANY(coll->flags, 0x8) && Lara.water_status != LWS_Underwater) { // NOTE: original checked "(Lara.water_status == 0) != 2" but it's always true ! ItemPushLara(item, laraitem, coll, CHK_ANY(coll->flags, 0x10), FALSE); } } } } -void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { - ITEM_INFO* item; - - item = &Items[itemID]; +void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll) { + ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { if CHK_ANY(coll->flags, 0x8) { @@ -349,10 +344,8 @@ void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* col } } -void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { - ITEM_INFO* item; - - item = &Items[itemID]; +void __cdecl DoorCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll) { + ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { if CHK_ANY(coll->flags, 0x8) { @@ -366,10 +359,8 @@ void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) } } -void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) { - ITEM_INFO* item; - - item = &Items[itemID]; +void __cdecl TrapCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll) { + ITEM_INFO *item = &Items[itemID]; if (item->status == ITEM_ACTIVE) { if (TestBoundsCollide(item, laraitem, coll->radius)) { TestCollision(item, laraitem); @@ -379,12 +370,12 @@ void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll) } } -void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush) { +void __cdecl ItemPushLara(ITEM_INFO *item, ITEM_INFO *laraitem, COLL_INFO *coll, BOOL spazon, BOOL bigpush) { int x, z, rx, rz; int l, r, t, b; int bndMin, bndMax; int radius; - __int16* bounds; + __int16 *bounds; __int16 c, s; __int16 minx, maxx, minz, maxz; __int16 oldFacing; @@ -434,7 +425,7 @@ void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, rz -= (bndMax * c - bndMin * s) >> W2V_SHIFT; if (spazon && bounds[3] - bounds[2] > 256) { - Lara.hit_direction = (unsigned __int16)(laraitem->pos.rotY + PHD_180 - phd_atan(rz, rx) + PHD_90) >> W2V_SHIFT; + Lara.hit_direction = (UINT16)(laraitem->pos.rotY + PHD_180 - phd_atan(rz, rx) + PHD_90) >> W2V_SHIFT; if (!Lara.hit_frame) { PlaySoundEffect(31, &laraitem->pos, 0); } @@ -464,7 +455,7 @@ void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, } } -BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius) { +BOOL __cdecl TestBoundsCollide(ITEM_INFO *item, ITEM_INFO *laraitem, int radius) { __int16 *boundItem; __int16 *boundLara; int x, z, s, c; @@ -491,10 +482,10 @@ BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius) return FALSE; } -BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem) { +BOOL __cdecl TestLaraPosition(__int16 *bounds, ITEM_INFO *item, ITEM_INFO *laraitem) { int x, y, z; int xBound, yBound, zBound; - short yRot, xRot, zRot; + __int16 yRot, xRot, zRot; xRot = laraitem->pos.rotX - item->pos.rotX; yRot = laraitem->pos.rotY - item->pos.rotY; @@ -525,8 +516,8 @@ BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* larai && zBound <= bounds[5]; } -void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem) { - FLOOR_INFO* floor; +void __cdecl AlignLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *laraitem) { + FLOOR_INFO *floor; int x, y, z; int height, ceiling; __int16 roomID; @@ -554,9 +545,9 @@ void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* lara } } -BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem) { +BOOL __cdecl MoveLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *laraitem) { PHD_3DPOS newpos; - FLOOR_INFO* floor; + FLOOR_INFO *floor; int height, distance; int xDist, yDist, zDist; __int16 roomID; @@ -591,7 +582,7 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* larai return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); } -BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __int16 angleAdder) { +BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS *src, PHD_3DPOS *dest, int velocity, __int16 angleAdder) { int x, y, z, distance; __int16 xRot, yRot, zRot; diff --git a/game/collide.h b/game/collide.h index 452deec..0bfd553 100644 --- a/game/collide.h +++ b/game/collide.h @@ -32,20 +32,20 @@ int __cdecl FindGridShift(int src, int dest); // 0x00412F90 int __cdecl CollideStaticObjects(COLL_INFO *coll, int x, int y, int z, __int16 roomID, int hite); // 0x00412FC0 void __cdecl GetNearByRooms(int x, int y, int z, int r, int h, __int16 roomID); // 0x004133B0 void __cdecl GetNewRoom(int x, int y, int z, __int16 roomID); // 0x00413480 -void __cdecl ShiftItem(ITEM_INFO* item, COLL_INFO* coll); // 0x004134E0 -void __cdecl UpdateLaraRoom(ITEM_INFO* item, int height); // 0x00413520 -__int16 __cdecl GetTiltType(FLOOR_INFO* floor, int x, int y, int z); // 0x00413580 -void __cdecl LaraBaddieCollision(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413620 -void __cdecl EffectSpaz(ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004137C0 -void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413840 -void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004138C0 -void __cdecl DoorCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x00413920 -void __cdecl TrapCollision(__int16 itemID, ITEM_INFO* laraitem, COLL_INFO* coll); // 0x004139A0 -void __cdecl ItemPushLara(ITEM_INFO* item, ITEM_INFO* laraitem, COLL_INFO* coll, BOOL spazon, BOOL bigpush); // 0x00413A10 -BOOL __cdecl TestBoundsCollide(ITEM_INFO* item, ITEM_INFO* laraitem, int radius); // 0x00413D20 -BOOL __cdecl TestLaraPosition(__int16* bounds, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413DF0 -void __cdecl AlignLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00413F30 -BOOL __cdecl MoveLaraPosition(PHD_VECTOR* pos, ITEM_INFO* item, ITEM_INFO* laraitem); // 0x00414070 -BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS* src, PHD_3DPOS* dest, int velocity, __int16 angleAdder); // 0x00414200 +void __cdecl ShiftItem(ITEM_INFO *item, COLL_INFO *coll); // 0x004134E0 +void __cdecl UpdateLaraRoom(ITEM_INFO *item, int height); // 0x00413520 +__int16 __cdecl GetTiltType(FLOOR_INFO *floor, int x, int y, int z); // 0x00413580 +void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll); // 0x00413620 +void __cdecl EffectSpaz(ITEM_INFO *laraitem, COLL_INFO *coll); // 0x004137C0 +void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll); // 0x00413840 +void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll); // 0x004138C0 +void __cdecl DoorCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll); // 0x00413920 +void __cdecl TrapCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll); // 0x004139A0 +void __cdecl ItemPushLara(ITEM_INFO *item, ITEM_INFO *laraitem, COLL_INFO *coll, BOOL spazon, BOOL bigpush); // 0x00413A10 +BOOL __cdecl TestBoundsCollide(ITEM_INFO *item, ITEM_INFO *laraitem, int radius); // 0x00413D20 +BOOL __cdecl TestLaraPosition(__int16 *bounds, ITEM_INFO *item, ITEM_INFO *laraitem); // 0x00413DF0 +void __cdecl AlignLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *laraitem); // 0x00413F30 +BOOL __cdecl MoveLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *laraitem); // 0x00414070 +BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS *src, PHD_3DPOS *dest, int velocity, __int16 angleAdder); // 0x00414200 #endif // COLLIDE_H_INCLUDED diff --git a/global/types.h b/global/types.h index 20bb191..a42d358 100644 --- a/global/types.h +++ b/global/types.h @@ -1835,9 +1835,9 @@ typedef struct DoorInfos_t { typedef struct FloorInfo_t { __int16 index; __int16 box; - unsigned char pitRoom; + BYTE pitRoom; char floor; - unsigned char skyRoom; + BYTE skyRoom; char ceiling; } FLOOR_INFO; From 899ea57b2f510480da22287f08e4a3546e202847 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Fri, 18 Mar 2022 10:19:22 +0100 Subject: [PATCH 22/66] Maybe fixed a bug about key Link: https://discord.com/channels/218414493355606016/394838132643725314/954130260650229790 --- game/collide.cpp | 27 ++++++++++++++++++++------- 1 file changed, 20 insertions(+), 7 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index 5458aa1..3a56a30 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -491,10 +491,23 @@ BOOL __cdecl TestLaraPosition(__int16 *bounds, ITEM_INFO *item, ITEM_INFO *larai yRot = laraitem->pos.rotY - item->pos.rotY; zRot = laraitem->pos.rotZ - item->pos.rotZ; - if (xRot < bounds[6] || xRot > bounds[7] || - yRot < bounds[8] || yRot > bounds[9] || - zRot < bounds[10] || zRot > bounds[11]) { - return 0; + if (xRot < bounds[6]) { + return FALSE; + } + if (xRot > bounds[7]) { + return FALSE; + } + if (yRot < bounds[8]) { + return FALSE; + } + if (yRot > bounds[9]) { + return FALSE; + } + if (zRot < bounds[10]) { + return FALSE; + } + if (zRot > bounds[11]) { + return FALSE; } x = laraitem->pos.x - item->pos.x; @@ -564,7 +577,7 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *larai phd_PopMatrix(); if (item->objectID != ID_FLARE_ITEM) { - return Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); + return Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 364); } roomID = laraitem->roomNumber; @@ -578,8 +591,8 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *larai zDist = SQR(newpos.z - laraitem->pos.z); yDist = SQR(newpos.y - laraitem->pos.y); xDist = SQR(newpos.x - laraitem->pos.z); - distance = phd_sqrt(xDist + yDist + zDist); - return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 2 * PHD_DEGREE); + distance = phd_sqrt(zDist + yDist + xDist); + return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 364); } BOOL __cdecl Move3DPosTo3DPos(PHD_3DPOS *src, PHD_3DPOS *dest, int velocity, __int16 angleAdder) { From e130a4b8f1e45351706698a2490cafdbae8085a1 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Fri, 18 Mar 2022 16:05:26 +0100 Subject: [PATCH 23/66] Fix MoveLaraPosition() for Flare --- game/collide.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/game/collide.cpp b/game/collide.cpp index 3a56a30..fa1db57 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -590,7 +590,7 @@ BOOL __cdecl MoveLaraPosition(PHD_VECTOR *pos, ITEM_INFO *item, ITEM_INFO *larai zDist = SQR(newpos.z - laraitem->pos.z); yDist = SQR(newpos.y - laraitem->pos.y); - xDist = SQR(newpos.x - laraitem->pos.z); + xDist = SQR(newpos.x - laraitem->pos.x); distance = phd_sqrt(zDist + yDist + xDist); return distance < 128 || Move3DPosTo3DPos(&laraitem->pos, &newpos, 16, 364); } From 03202076246b9d508fcaa06cfd412ad6d69d7223 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 12:47:44 +0100 Subject: [PATCH 24/66] Decompiled DrawLara() --- game/draw.cpp | 304 +++++++++++++++++++++++++++++++++++++++++++++++++- game/draw.h | 2 +- 2 files changed, 304 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 3c5e307..be05db4 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -655,6 +655,308 @@ void __cdecl DrawAnimatingItem(ITEM_INFO *item) { phd_PopMatrix(); } +void __cdecl DrawLara(ITEM_INFO *laraitem) { + PHD_MATRIX hairMatrix, weaponMatrix; + OBJECT_INFO *obj; + int gunType; + int frac, rate, clip; + int currentState; + int oldBottom, oldTop, oldLeft, oldRight; + int interpolation; + int *bones; + UINT16 *rot1, *rot2, *rot1copy; + __int16 *framesPtr[2]; + __int16 *animFramePtr; + __int16 *frame; + + oldBottom = PhdWinBottom; + oldTop = PhdWinTop; + oldLeft = PhdWinLeft; + oldRight = PhdWinRight; + PhdWinBottom = PhdWinMaxY; + PhdWinTop = 0; + PhdWinLeft = 0; + PhdWinRight = PhdWinMaxX; + + if (Lara.hit_direction < 0) { + frac = GetFrames(laraitem, framesPtr, &rate); + if (frac) { + DrawLaraInt(laraitem, framesPtr[0], framesPtr[1], frac, rate); + PhdWinBottom = oldBottom; + PhdWinTop = oldTop; + PhdWinLeft = oldLeft; + PhdWinRight = oldRight; + return; + } + } + + if (Lara.hit_direction < 0) { + frame = framesPtr[0]; + } else { + switch (Lara.hit_direction) { + case 1: + animFramePtr = Anims[127].framePtr; + interpolation = Anims[127].interpolation; + break; + case 2: + animFramePtr = Anims[126].framePtr; + interpolation = Anims[126].interpolation; + break; + case 3: + animFramePtr = Anims[128].framePtr; + interpolation = Anims[128].interpolation; + break; + default: + animFramePtr = Anims[125].framePtr; + interpolation = Anims[125].interpolation; + break; + } + frame = &animFramePtr[Lara.hit_frame * (interpolation >> 8)]; + } + + obj = &Objects[laraitem->objectID]; + if (Lara.skidoo == -1) { + S_PrintShadow(obj->shadowSize, frame, laraitem); + } + + // save hair matrix position + memcpy(&hairMatrix, PhdMatrixPtr, sizeof(hairMatrix)); + + phd_PushMatrix(); + phd_TranslateAbs(laraitem->pos.x, laraitem->pos.y, laraitem->pos.z); + phd_RotYXZ(laraitem->pos.rotY, laraitem->pos.rotX, laraitem->pos.rotZ); + clip = S_GetObjectBounds(frame); + if (clip) { + bones = &AnimBones[obj->boneIndex]; + rot1 = (UINT16 *)frame + 9; + rot1copy = rot1; + + phd_PushMatrix(); + CalculateObjectLighting(laraitem, frame); + phd_TranslateRel(frame[6], frame[7], frame[8]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[0], clip); + + phd_PushMatrix(); + phd_TranslateRel(bones[1], bones[2], bones[3]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[1], clip); + phd_TranslateRel(bones[5], bones[6], bones[7]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[2], clip); + phd_TranslateRel(bones[9], bones[10], bones[11]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[3], clip); + phd_PopMatrix(); + + phd_PushMatrix(); + phd_TranslateRel(bones[13], bones[14], bones[15]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[4], clip); + phd_TranslateRel(bones[17], bones[18], bones[19]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[5], clip); + phd_TranslateRel(bones[21], bones[22], bones[23]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[6], clip); + phd_PopMatrix(); + + phd_TranslateRel(bones[25], bones[26], bones[27]); + currentState = Items[Lara.weapon_item].currentAnimState; + if (Lara.weapon_item != -1 && Lara.gun_type == LGT_M16 && currentState == 0 && currentState == 2 && currentState == 4) { + rot1copy = (UINT16*)Lara.right_arm.frame_base + Lara.right_arm.frame_number * (Anims[Lara.right_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1copy, 7); + } else { + phd_RotYXZsuperpack(&rot1, 0); + } + phd_RotYXZ(Lara.torso_y_rot, Lara.torso_x_rot, Lara.torso_z_rot); + phd_PutPolygons(Lara.mesh_ptrs[7], clip); + + phd_PushMatrix(); + phd_TranslateRel(bones[53], bones[54], bones[55]); + rot1copy = rot1; + phd_RotYXZsuperpack(&rot1, 6); + rot1 = rot1copy; + phd_RotYXZ(Lara.head_y_rot, Lara.head_x_rot, Lara.head_z_rot); + phd_PutPolygons(Lara.mesh_ptrs[14], clip); + // restore hair matrix position + memcpy(PhdMatrixPtr, &hairMatrix, sizeof(PHD_MATRIX)); + DrawHair(); + phd_PopMatrix(); + + if (Lara.back_gun) { + phd_PushMatrix(); + obj = &Objects[Lara.back_gun]; + phd_TranslateRel(AnimBones[obj->boneIndex + 53], AnimBones[obj->boneIndex + 54], AnimBones[obj->boneIndex + 55]); + rot2 = (UINT16*)Objects[Lara.back_gun].frameBase + 9; + phd_RotYXZsuperpack(&rot2, 14); + phd_PutPolygons(MeshPtr[obj->meshIndex + 14], clip); + phd_PopMatrix(); + } + + if (Lara.gun_status == LGS_Ready || Lara.gun_status == LGS_Special || Lara.gun_status == LGS_Draw || Lara.gun_status == LGS_Undraw) { + gunType = Lara.gun_type; + } else { + gunType = LGT_Unarmed; + } + + switch (gunType) { + case LGT_Unarmed: + case LGT_Flare: + phd_PushMatrix(); + phd_TranslateRel(bones[29], bones[30], bones[31]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[8], clip); + + phd_TranslateRel(bones[33], bones[34], bones[35]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[9], clip); + + phd_TranslateRel(bones[37], bones[38], bones[39]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[10], clip); + phd_PopMatrix(); + + phd_PushMatrix(); + phd_TranslateRel(bones[41], bones[42], bones[43]); + if (Lara.flare_control_left) { + rot1 = (UINT16*)Lara.left_arm.frame_base + (Lara.left_arm.frame_number - Anims[Lara.left_arm.anim_number].frameBase) * (Anims[Lara.left_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1, 11); + } else { + phd_RotYXZsuperpack(&rot1, 0); + } + phd_PutPolygons(Lara.mesh_ptrs[11], clip); + + phd_TranslateRel(bones[45], bones[46], bones[47]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[12], clip); + + phd_TranslateRel(bones[49], bones[50], bones[51]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[13], clip); + if (Lara.gun_type == LGT_Flare && Lara.left_arm.flash_gun) { + DrawGunFlash(LGT_Flare, clip); + } + phd_PopMatrix(); + break; + case LGT_Pistols: + case LGT_Magnums: + case LGT_Uzis: + phd_PushMatrix(); + phd_TranslateRel(bones[29], bones[30], bones[31]); + PhdMatrixPtr->_00 = PhdMatrixPtr[-2]._00; + PhdMatrixPtr->_01 = PhdMatrixPtr[-2]._01; + PhdMatrixPtr->_02 = PhdMatrixPtr[-2]._02; + PhdMatrixPtr->_10 = PhdMatrixPtr[-2]._10; + PhdMatrixPtr->_11 = PhdMatrixPtr[-2]._11; + PhdMatrixPtr->_12 = PhdMatrixPtr[-2]._12; + PhdMatrixPtr->_20 = PhdMatrixPtr[-2]._20; + PhdMatrixPtr->_21 = PhdMatrixPtr[-2]._21; + PhdMatrixPtr->_22 = PhdMatrixPtr[-2]._22; + phd_RotYXZ(Lara.right_arm.y_rot, Lara.right_arm.x_rot, Lara.right_arm.z_rot); + rot1 = (UINT16*)Lara.right_arm.frame_base + (Lara.right_arm.frame_number - Anims[Lara.right_arm.anim_number].frameBase) * (Anims[Lara.right_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1, 8); + phd_PutPolygons(Lara.mesh_ptrs[8], clip); + + phd_TranslateRel(bones[33], bones[34], bones[35]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[9], clip); + + phd_TranslateRel(bones[37], bones[38], bones[39]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[10], clip); + if (Lara.right_arm.flash_gun) { + memcpy(&weaponMatrix, PhdMatrixPtr, sizeof(PHD_MATRIX)); + } + phd_PopMatrix(); + + phd_PushMatrix(); + phd_TranslateRel(bones[41], bones[42], bones[43]); + PhdMatrixPtr->_00 = PhdMatrixPtr[-2]._00; + PhdMatrixPtr->_01 = PhdMatrixPtr[-2]._01; + PhdMatrixPtr->_02 = PhdMatrixPtr[-2]._02; + PhdMatrixPtr->_10 = PhdMatrixPtr[-2]._10; + PhdMatrixPtr->_11 = PhdMatrixPtr[-2]._11; + PhdMatrixPtr->_12 = PhdMatrixPtr[-2]._12; + PhdMatrixPtr->_20 = PhdMatrixPtr[-2]._20; + PhdMatrixPtr->_21 = PhdMatrixPtr[-2]._21; + PhdMatrixPtr->_22 = PhdMatrixPtr[-2]._22; + phd_RotYXZ(Lara.left_arm.y_rot, Lara.left_arm.x_rot, Lara.left_arm.z_rot); + rot1 = (UINT16*)Lara.left_arm.frame_base + (Lara.left_arm.frame_number - Anims[Lara.left_arm.anim_number].frameBase) * (Anims[Lara.left_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1, 11); + phd_PutPolygons(Lara.mesh_ptrs[11], clip); + + phd_TranslateRel(bones[45], bones[46], bones[47]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[12], clip); + + phd_TranslateRel(bones[49], bones[50], bones[51]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[13], clip); + + if (Lara.left_arm.flash_gun) { + DrawGunFlash(gunType, 0); + } + if (Lara.right_arm.flash_gun) { + memcpy(PhdMatrixPtr, &weaponMatrix, sizeof(PHD_MATRIX)); + DrawGunFlash(gunType, clip); + } + phd_PopMatrix(); + break; + case LGT_Shotgun: + case LGT_M16: + case LGT_Grenade: + case LGT_Harpoon: + phd_PushMatrix(); + phd_TranslateRel(bones[29], bones[30], bones[31]); + rot1 = (UINT16*)Lara.right_arm.frame_base + Lara.right_arm.frame_number * (Anims[Lara.right_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1, 8); + phd_PutPolygons(Lara.mesh_ptrs[8], clip); + + phd_TranslateRel(bones[33], bones[34], bones[35]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[9], clip); + + phd_TranslateRel(bones[37], bones[38], bones[39]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[10], clip); + if (Lara.right_arm.flash_gun) { + memcpy(&weaponMatrix, PhdMatrixPtr, sizeof(PHD_MATRIX)); + } + phd_PopMatrix(); + + phd_PushMatrix(); + phd_TranslateRel(bones[41], bones[42], bones[43]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[11], clip); + + phd_TranslateRel(bones[45], bones[46], bones[47]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[12], clip); + + phd_TranslateRel(bones[49], bones[50], bones[51]); + phd_RotYXZsuperpack(&rot1, 0); + phd_PutPolygons(Lara.mesh_ptrs[13], clip); + + if (Lara.right_arm.flash_gun) { + memcpy(PhdMatrixPtr, &weaponMatrix, sizeof(PHD_MATRIX)); + DrawGunFlash(gunType, clip); + } + phd_PopMatrix(); + break; + default: + break; + } + } + + phd_PopMatrix(); + phd_PopMatrix(); + PhdWinBottom = oldBottom; + PhdWinTop = oldTop; + PhdWinLeft = oldLeft; + PhdWinRight = oldRight; +} + void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int frac, int rate) { PHD_MATRIX matrix; UINT16 *rot1, *rot2, *rot1copy, *rot2copy; @@ -1022,7 +1324,7 @@ void Inject_Draw() { // INJECT(----------, DrawDummyItem); INJECT(0x00419A50, DrawAnimatingItem); -// INJECT(0x00419DD0, DrawLara); + INJECT(0x00419DD0, DrawLara); INJECT(0x0041AB00, DrawLaraInt); diff --git a/game/draw.h b/game/draw.h index f007824..54a37f8 100644 --- a/game/draw.h +++ b/game/draw.h @@ -41,7 +41,7 @@ void __cdecl DrawSpriteItem(ITEM_INFO *item); // 0x004199C0 void __cdecl DrawDummyItem(ITEM_INFO *item); void __cdecl DrawAnimatingItem(ITEM_INFO *item); // 0x00419A50 -#define DrawLara ((void(__cdecl*)(ITEM_INFO*)) 0x00419DD0) +void __cdecl DrawLara(ITEM_INFO *laraitem); // 0x00419DD0 void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int frac, int rate); From 2c70a05b5a93d05aed46a629abfc6d846431cd15 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 12:54:25 +0100 Subject: [PATCH 25/66] Decompiled DrawPhaseCinematic() and DrawPhaseGame() --- game/draw.cpp | 23 +++++++++++++++++++++-- game/draw.h | 4 ++-- global/vars.h | 2 +- 3 files changed, 24 insertions(+), 5 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index be05db4..f1ae84c 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -24,6 +24,7 @@ #include "3dsystem/3d_gen.h" #include "3dsystem/scalespr.h" #include "game/hair.h" +#include "game/health.h" #include "specific/game.h" #include "specific/output.h" #include "global/vars.h" @@ -44,6 +45,24 @@ void ResetGoldenLaraAlpha() { } #endif // FEATURE_VIDEOFX_IMPROVED +int __cdecl DrawPhaseCinematic() { + UnderwaterCamera = FALSE; + DrawRooms(Camera.pos.roomNumber); + S_OutputPolyList(); + Camera.numberFrames = S_DumpScreen(); + S_AnimateTextures(Camera.numberFrames); + return Camera.numberFrames; +} + +int __cdecl DrawPhaseGame() { + DrawRooms(Camera.pos.roomNumber); + DrawGameInfo(TRUE); + S_OutputPolyList(); + Camera.numberFrames = S_DumpScreen(); + S_AnimateTextures(Camera.numberFrames); + return Camera.numberFrames; +} + void __cdecl DrawRooms(__int16 currentRoom) { ROOM_INFO *room = &RoomInfo[currentRoom]; @@ -1309,8 +1328,8 @@ void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff) { * Inject function */ void Inject_Draw() { -// INJECT(0x00418920, DrawPhaseCinematic); -// INJECT(0x00418960, DrawPhaseGame); + INJECT(0x00418920, DrawPhaseCinematic); + INJECT(0x00418960, DrawPhaseGame); INJECT(0x004189A0, DrawRooms); INJECT(0x00418C50, GetRoomBounds); diff --git a/game/draw.h b/game/draw.h index 54a37f8..d9403bc 100644 --- a/game/draw.h +++ b/game/draw.h @@ -27,8 +27,8 @@ /* * Function list */ -#define DrawPhaseCinematic ((int(__cdecl*)(void)) 0x00418920) -#define DrawPhaseGame ((int(__cdecl*)(void)) 0x00418960) +int __cdecl DrawPhaseCinematic(); // 0x00418920 +int __cdecl DrawPhaseGame(); // 0x00418960 void __cdecl DrawRooms(__int16 currentRoom); // 0x004189A0 void __cdecl GetRoomBounds(); // 0x00418C50 diff --git a/global/vars.h b/global/vars.h index e575962..fce3ab1 100644 --- a/global/vars.h +++ b/global/vars.h @@ -394,7 +394,7 @@ extern APP_SETTINGS SavedAppSettings; #define AnimChanges VAR_U_(0x0052617C, CHANGE_STRUCT*) #define RoomCount VAR_U_(0x00526180, __int16) #define RoomInfo VAR_U_(0x0052618C, ROOM_INFO*) -#define UnderwaterCamera VAR_U_(0x00526190, int) +#define UnderwaterCamera VAR_U_(0x00526190, BOOL) #define SunsetTimer VAR_U_(0x00526194, DWORD) #define OutsideRight VAR_U_(0x00526198, int) #define OutsideTop VAR_U_(0x005261AC, int) From e9e9414d543c34354f285b28b2b4d6a40c849821 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:08:42 +0100 Subject: [PATCH 26/66] Decompiled InitInterpolate() - Added 4 variable (2 int, 1 ptr, 1 array) --- game/draw.cpp | 9 ++++++++- game/draw.h | 2 +- global/vars.h | 4 ++++ 3 files changed, 13 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index f1ae84c..d6a1364 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1215,6 +1215,13 @@ void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int phd_PopMatrix(); } +void __cdecl InitInterpolate(int frac, int rate) { + IMRate = rate; + IMFrac = frac; + IMPtr = IMStack; + memcpy(IMStack, PhdMatrixPtr, sizeof(PHD_MATRIX)); +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1347,7 +1354,7 @@ void Inject_Draw() { INJECT(0x0041AB00, DrawLaraInt); -// INJECT(0x0041B6F0, InitInterpolate); + INJECT(0x0041B6F0, InitInterpolate); // INJECT(0x0041B730, phd_PopMatrix_I); // INJECT(0x0041B760, phd_PushMatrix_I); // INJECT(0x0041B790, phd_RotY_I); diff --git a/game/draw.h b/game/draw.h index d9403bc..f01a076 100644 --- a/game/draw.h +++ b/game/draw.h @@ -45,7 +45,7 @@ void __cdecl DrawLara(ITEM_INFO *laraitem); // 0x00419DD0 void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int frac, int rate); -#define InitInterpolate ((void(__cdecl*)(int, int)) 0x0041B6F0) +void __cdecl InitInterpolate(int frac, int rate); // 0x0041B6F0 #define phd_PopMatrix_I ((void(__cdecl*)(void)) 0x0041B730) #define phd_PushMatrix_I ((void(__cdecl*)(void)) 0x0041B760) #define phd_RotY_I ((void(__cdecl*)(__int16)) 0x0041B790) diff --git a/global/vars.h b/global/vars.h index fce3ab1..46ab75b 100644 --- a/global/vars.h +++ b/global/vars.h @@ -412,6 +412,10 @@ extern APP_SETTINGS SavedAppSettings; #define Overlaps VAR_U_(0x005263C8, UINT16*) #define Boxes VAR_U_(0x005263CC, BOX_INFO*) #define BoxesCount VAR_U_(0x005263D0, DWORD) +#define IMRate VAR_U_(0x00526184, int) +#define IMFrac VAR_U_(0x005258F0, int) +#define IMPtr VAR_U_(0x00526188, PHD_MATRIX*) +#define IMStack ARRAY_(0x005252C0, PHD_MATRIX, [32]) // Initialized arrays #define TrackIDs ARRAY_(0x004642F0, __int16, [16]) /* = {2, 0}; */ From 2009cc3831cea62d213b60f5fa356c5bff574126 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:12:13 +0100 Subject: [PATCH 27/66] Decompiled phd_PopMatrix_I() Decompiled phd_PushMatrix_I() too. --- game/draw.cpp | 15 +++++++++++++-- game/draw.h | 4 ++-- 2 files changed, 15 insertions(+), 4 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index d6a1364..f3b5602 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1222,6 +1222,17 @@ void __cdecl InitInterpolate(int frac, int rate) { memcpy(IMStack, PhdMatrixPtr, sizeof(PHD_MATRIX)); } +void __cdecl phd_PopMatrix_I() { + phd_PopMatrix(); + --IMPtr; +} + +void __cdecl phd_PushMatrix_I() { + phd_PushMatrix(); + memcpy(&IMPtr[1], &IMPtr[0], sizeof(PHD_MATRIX)); + ++IMPtr; +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1355,8 +1366,8 @@ void Inject_Draw() { INJECT(0x0041AB00, DrawLaraInt); INJECT(0x0041B6F0, InitInterpolate); -// INJECT(0x0041B730, phd_PopMatrix_I); -// INJECT(0x0041B760, phd_PushMatrix_I); + INJECT(0x0041B730, phd_PopMatrix_I); + INJECT(0x0041B760, phd_PushMatrix_I); // INJECT(0x0041B790, phd_RotY_I); // INJECT(0x0041B7D0, phd_RotX_I); // INJECT(0x0041B810, phd_RotZ_I); diff --git a/game/draw.h b/game/draw.h index f01a076..d14eee5 100644 --- a/game/draw.h +++ b/game/draw.h @@ -46,8 +46,8 @@ void __cdecl DrawLara(ITEM_INFO *laraitem); // 0x00419DD0 void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int frac, int rate); void __cdecl InitInterpolate(int frac, int rate); // 0x0041B6F0 -#define phd_PopMatrix_I ((void(__cdecl*)(void)) 0x0041B730) -#define phd_PushMatrix_I ((void(__cdecl*)(void)) 0x0041B760) +void __cdecl phd_PopMatrix_I(); // 0x0041B730 +void __cdecl phd_PushMatrix_I(); // 0x0041B760 #define phd_RotY_I ((void(__cdecl*)(__int16)) 0x0041B790) #define phd_RotX_I ((void(__cdecl*)(__int16)) 0x0041B7D0) #define phd_RotZ_I ((void(__cdecl*)(__int16)) 0x0041B810) From 46564b6eb1b079e7c636954a4a465456521a012a Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:36:15 +0100 Subject: [PATCH 28/66] Decompiled phd_RotY_I() Also decompiled phd_RotX_I() and phd_RotZ_I() --- game/draw.cpp | 33 ++++++++++++++++++++++++++++++--- game/draw.h | 6 +++--- 2 files changed, 33 insertions(+), 6 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index f3b5602..8471f13 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1233,6 +1233,33 @@ void __cdecl phd_PushMatrix_I() { ++IMPtr; } +void __cdecl phd_RotY_I(__int16 angle) { + PHD_MATRIX *oldMatrix; + phd_RotY(angle); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_RotY(angle); + PhdMatrixPtr = oldMatrix; +} + +void __cdecl phd_RotX_I(__int16 angle) { + PHD_MATRIX *oldMatrix; + phd_RotX(angle); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_RotX(angle); + PhdMatrixPtr = oldMatrix; +} + +void __cdecl phd_RotZ_I(__int16 angle) { + PHD_MATRIX *oldMatrix; + phd_RotZ(angle); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_RotZ(angle); + PhdMatrixPtr = oldMatrix; +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1368,9 +1395,9 @@ void Inject_Draw() { INJECT(0x0041B6F0, InitInterpolate); INJECT(0x0041B730, phd_PopMatrix_I); INJECT(0x0041B760, phd_PushMatrix_I); -// INJECT(0x0041B790, phd_RotY_I); -// INJECT(0x0041B7D0, phd_RotX_I); -// INJECT(0x0041B810, phd_RotZ_I); + INJECT(0x0041B790, phd_RotY_I); + INJECT(0x0041B7D0, phd_RotX_I); + INJECT(0x0041B810, phd_RotZ_I); // INJECT(0x0041B850, phd_TranslateRel_I); // INJECT(0x0041B8A0, phd_TranslateRel_ID); // INJECT(0x0041B8F0, phd_RotYXZ_I); diff --git a/game/draw.h b/game/draw.h index d14eee5..d2580d1 100644 --- a/game/draw.h +++ b/game/draw.h @@ -48,9 +48,9 @@ void __cdecl DrawLaraInt(ITEM_INFO *item, __int16 *frame1, __int16 *frame2, int void __cdecl InitInterpolate(int frac, int rate); // 0x0041B6F0 void __cdecl phd_PopMatrix_I(); // 0x0041B730 void __cdecl phd_PushMatrix_I(); // 0x0041B760 -#define phd_RotY_I ((void(__cdecl*)(__int16)) 0x0041B790) -#define phd_RotX_I ((void(__cdecl*)(__int16)) 0x0041B7D0) -#define phd_RotZ_I ((void(__cdecl*)(__int16)) 0x0041B810) +void __cdecl phd_RotY_I(__int16 angle); // 0x0041B790 +void __cdecl phd_RotX_I(__int16 angle); // 0x0041B7D0 +void __cdecl phd_RotZ_I(__int16 angle); // 0x0041B810 #define phd_TranslateRel_I ((void(__cdecl*)(int, int, int)) 0x0041B850) #define phd_TranslateRel_ID ((void(__cdecl*)(int, int, int, int, int, int)) 0x0041B8A0) #define phd_RotYXZ_I ((void(__cdecl*)(int, int, int)) 0x0041B8F0) From 5e70804726a1d283afe2c38dbe7dba4f4e17bca2 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:42:20 +0100 Subject: [PATCH 29/66] Decompiled phd_TranslateRel_I() --- game/draw.cpp | 11 ++++++++++- game/draw.h | 2 +- 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 8471f13..d6128a7 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1260,6 +1260,15 @@ void __cdecl phd_RotZ_I(__int16 angle) { PhdMatrixPtr = oldMatrix; } +void __cdecl phd_TranslateRel_I(int x, int y, int z) { + PHD_MATRIX *oldMatrix; + phd_TranslateRel(x, y, z); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_TranslateRel(x, y, z); + PhdMatrixPtr = oldMatrix; +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1398,7 +1407,7 @@ void Inject_Draw() { INJECT(0x0041B790, phd_RotY_I); INJECT(0x0041B7D0, phd_RotX_I); INJECT(0x0041B810, phd_RotZ_I); -// INJECT(0x0041B850, phd_TranslateRel_I); + INJECT(0x0041B850, phd_TranslateRel_I); // INJECT(0x0041B8A0, phd_TranslateRel_ID); // INJECT(0x0041B8F0, phd_RotYXZ_I); // INJECT(0x0041B940, phd_RotYXZsuperpack_I); diff --git a/game/draw.h b/game/draw.h index d2580d1..523a53a 100644 --- a/game/draw.h +++ b/game/draw.h @@ -51,7 +51,7 @@ void __cdecl phd_PushMatrix_I(); // 0x0041B760 void __cdecl phd_RotY_I(__int16 angle); // 0x0041B790 void __cdecl phd_RotX_I(__int16 angle); // 0x0041B7D0 void __cdecl phd_RotZ_I(__int16 angle); // 0x0041B810 -#define phd_TranslateRel_I ((void(__cdecl*)(int, int, int)) 0x0041B850) +void __cdecl phd_TranslateRel_I(int x, int y, int z); // 0x0041B850 #define phd_TranslateRel_ID ((void(__cdecl*)(int, int, int, int, int, int)) 0x0041B8A0) #define phd_RotYXZ_I ((void(__cdecl*)(int, int, int)) 0x0041B8F0) #define phd_RotYXZsuperpack_I ((void(__cdecl*)(UINT16**, UINT16**, int)) 0x0041B940) From 7fab6433df76b496c8bdd11c37e0e75de506f09b Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:53:05 +0100 Subject: [PATCH 30/66] Decompiled phd_TranslateRel_ID() Also decompiled phd_RotYXZ_I() --- game/draw.cpp | 22 ++++++++++++++++++++-- game/draw.h | 4 ++-- 2 files changed, 22 insertions(+), 4 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index d6128a7..4c95006 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1269,6 +1269,24 @@ void __cdecl phd_TranslateRel_I(int x, int y, int z) { PhdMatrixPtr = oldMatrix; } +void __cdecl phd_TranslateRel_ID(int x1, int y1, int z1, int x2, int y2, int z2) { + PHD_MATRIX *oldMatrix; + phd_TranslateRel(x1, y1, z1); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_TranslateRel(x2, y2, z2); + PhdMatrixPtr = oldMatrix; +} + +void __cdecl phd_RotYXZ_I(__int16 y, __int16 x, __int16 z) { + PHD_MATRIX *oldMatrix; + phd_RotYXZ(y, x, z); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_RotYXZ(y, x, z); + PhdMatrixPtr = oldMatrix; +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1408,8 +1426,8 @@ void Inject_Draw() { INJECT(0x0041B7D0, phd_RotX_I); INJECT(0x0041B810, phd_RotZ_I); INJECT(0x0041B850, phd_TranslateRel_I); -// INJECT(0x0041B8A0, phd_TranslateRel_ID); -// INJECT(0x0041B8F0, phd_RotYXZ_I); + INJECT(0x0041B8A0, phd_TranslateRel_ID); + INJECT(0x0041B8F0, phd_RotYXZ_I); // INJECT(0x0041B940, phd_RotYXZsuperpack_I); INJECT(0x0041B980, phd_RotYXZsuperpack); diff --git a/game/draw.h b/game/draw.h index 523a53a..12f92c5 100644 --- a/game/draw.h +++ b/game/draw.h @@ -52,8 +52,8 @@ void __cdecl phd_RotY_I(__int16 angle); // 0x0041B790 void __cdecl phd_RotX_I(__int16 angle); // 0x0041B7D0 void __cdecl phd_RotZ_I(__int16 angle); // 0x0041B810 void __cdecl phd_TranslateRel_I(int x, int y, int z); // 0x0041B850 -#define phd_TranslateRel_ID ((void(__cdecl*)(int, int, int, int, int, int)) 0x0041B8A0) -#define phd_RotYXZ_I ((void(__cdecl*)(int, int, int)) 0x0041B8F0) +void __cdecl phd_TranslateRel_ID(int x1, int y1, int z1, int x2, int y2, int z2); // 0x0041B8A0 +void __cdecl phd_RotYXZ_I(__int16 y, __int16 x, __int16 z); // 0x0041B8F0 #define phd_RotYXZsuperpack_I ((void(__cdecl*)(UINT16**, UINT16**, int)) 0x0041B940) void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index); // 0x0041B980 From 4b1415f6f1bb9a2059181e2b343412381b646cb1 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 13:57:54 +0100 Subject: [PATCH 31/66] Decompiled phd_RotYXZsuperpack_I() --- game/draw.cpp | 11 ++++++++++- game/draw.h | 3 +-- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 4c95006..33105d9 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1287,6 +1287,15 @@ void __cdecl phd_RotYXZ_I(__int16 y, __int16 x, __int16 z) { PhdMatrixPtr = oldMatrix; } +void __cdecl phd_RotYXZsuperpack_I(UINT16 **pptr1, UINT16 **pptr2, int index) { + PHD_MATRIX *oldMatrix; + phd_RotYXZsuperpack(pptr1, index); + oldMatrix = PhdMatrixPtr; + PhdMatrixPtr = IMPtr; + phd_RotYXZsuperpack(pptr2, index); + PhdMatrixPtr = oldMatrix; +} + void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index) { for( int i = 0; i < index; ++i ) { if( (**pptr >> 14) == 0 ) @@ -1428,7 +1437,7 @@ void Inject_Draw() { INJECT(0x0041B850, phd_TranslateRel_I); INJECT(0x0041B8A0, phd_TranslateRel_ID); INJECT(0x0041B8F0, phd_RotYXZ_I); -// INJECT(0x0041B940, phd_RotYXZsuperpack_I); + INJECT(0x0041B940, phd_RotYXZsuperpack_I); INJECT(0x0041B980, phd_RotYXZsuperpack); INJECT(0x0041BA30, phd_PutPolygons_I); diff --git a/game/draw.h b/game/draw.h index 12f92c5..4e4c421 100644 --- a/game/draw.h +++ b/game/draw.h @@ -54,8 +54,7 @@ void __cdecl phd_RotZ_I(__int16 angle); // 0x0041B810 void __cdecl phd_TranslateRel_I(int x, int y, int z); // 0x0041B850 void __cdecl phd_TranslateRel_ID(int x1, int y1, int z1, int x2, int y2, int z2); // 0x0041B8A0 void __cdecl phd_RotYXZ_I(__int16 y, __int16 x, __int16 z); // 0x0041B8F0 -#define phd_RotYXZsuperpack_I ((void(__cdecl*)(UINT16**, UINT16**, int)) 0x0041B940) - +void __cdecl phd_RotYXZsuperpack_I(UINT16 **pptr1, UINT16 **pptr2, int index); // 0x0041B940 void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index); // 0x0041B980 void __cdecl phd_PutPolygons_I(__int16 *ptrObj, int clip); // 0x0041BA30 From 2aaa2ee427a6c11be81798cd1c80e2fb062a1b79 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 14:41:08 +0100 Subject: [PATCH 32/66] Fixed DrawLara() - a phd_PopMatrix() caused weird render artifact. --- game/draw.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/game/draw.cpp b/game/draw.cpp index 33105d9..857467d 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -966,9 +966,9 @@ void __cdecl DrawLara(ITEM_INFO *laraitem) { default: break; } + phd_PopMatrix(); } - phd_PopMatrix(); phd_PopMatrix(); PhdWinBottom = oldBottom; PhdWinTop = oldTop; From 120072f44b10c31739b94298d78c08a84b025e81 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 14:48:31 +0100 Subject: [PATCH 33/66] Decompiled InterpolateMatrix() --- game/draw.cpp | 36 +++++++++++++++++++++++++++++++++++- game/draw.h | 2 +- 2 files changed, 36 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 857467d..20ba007 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1331,6 +1331,40 @@ void __cdecl phd_PutPolygons_I(__int16 *ptrObj, int clip) { phd_PopMatrix(); } +void __cdecl InterpolateMatrix() { + if (IMRate == 2) { + PhdMatrixPtr->_00 = (PhdMatrixPtr->_00 + IMPtr->_00) >> 1; + PhdMatrixPtr->_01 = (PhdMatrixPtr->_01 + IMPtr->_01) >> 1; + PhdMatrixPtr->_02 = (PhdMatrixPtr->_02 + IMPtr->_02) >> 1; + PhdMatrixPtr->_03 = (PhdMatrixPtr->_03 + IMPtr->_03) >> 1; + + PhdMatrixPtr->_10 = (PhdMatrixPtr->_10 + IMPtr->_10) >> 1; + PhdMatrixPtr->_11 = (PhdMatrixPtr->_11 + IMPtr->_11) >> 1; + PhdMatrixPtr->_12 = (PhdMatrixPtr->_12 + IMPtr->_12) >> 1; + PhdMatrixPtr->_13 = (PhdMatrixPtr->_13 + IMPtr->_13) >> 1; + + PhdMatrixPtr->_20 = (PhdMatrixPtr->_20 + IMPtr->_20) >> 1; + PhdMatrixPtr->_21 = (PhdMatrixPtr->_21 + IMPtr->_21) >> 1; + PhdMatrixPtr->_22 = (PhdMatrixPtr->_22 + IMPtr->_22) >> 1; + PhdMatrixPtr->_23 = (PhdMatrixPtr->_23 + IMPtr->_23) >> 1; + } else { + PhdMatrixPtr->_00 += IMFrac * (IMPtr->_00 - PhdMatrixPtr->_00) / IMRate; + PhdMatrixPtr->_01 += IMFrac * (IMPtr->_01 - PhdMatrixPtr->_01) / IMRate; + PhdMatrixPtr->_02 += IMFrac * (IMPtr->_02 - PhdMatrixPtr->_02) / IMRate; + PhdMatrixPtr->_03 += IMFrac * (IMPtr->_03 - PhdMatrixPtr->_03) / IMRate; + + PhdMatrixPtr->_10 += IMFrac * (IMPtr->_10 - PhdMatrixPtr->_10) / IMRate; + PhdMatrixPtr->_11 += IMFrac * (IMPtr->_11 - PhdMatrixPtr->_11) / IMRate; + PhdMatrixPtr->_12 += IMFrac * (IMPtr->_12 - PhdMatrixPtr->_12) / IMRate; + PhdMatrixPtr->_13 += IMFrac * (IMPtr->_13 - PhdMatrixPtr->_13) / IMRate; + + PhdMatrixPtr->_20 += IMFrac * (IMPtr->_20 - PhdMatrixPtr->_20) / IMRate; + PhdMatrixPtr->_21 += IMFrac * (IMPtr->_21 - PhdMatrixPtr->_21) / IMRate; + PhdMatrixPtr->_22 += IMFrac * (IMPtr->_22 - PhdMatrixPtr->_22) / IMRate; + PhdMatrixPtr->_23 += IMFrac * (IMPtr->_23 - PhdMatrixPtr->_23) / IMRate; + } +} + void __cdecl DrawGunFlash(int weapon, int clip) { __int16 light; int len; @@ -1442,7 +1476,7 @@ void Inject_Draw() { INJECT(0x0041B980, phd_RotYXZsuperpack); INJECT(0x0041BA30, phd_PutPolygons_I); -// INJECT(0x0041BA60, InterpolateMatrix); + INJECT(0x0041BA60, InterpolateMatrix); // INJECT(0x0041BC10, InterpolateArmMatrix); INJECT(0x0041BD10, DrawGunFlash); diff --git a/game/draw.h b/game/draw.h index 4e4c421..0a0cdea 100644 --- a/game/draw.h +++ b/game/draw.h @@ -58,7 +58,7 @@ void __cdecl phd_RotYXZsuperpack_I(UINT16 **pptr1, UINT16 **pptr2, int index); / void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index); // 0x0041B980 void __cdecl phd_PutPolygons_I(__int16 *ptrObj, int clip); // 0x0041BA30 -#define InterpolateMatrix ((void(__cdecl*)(void)) 0x0041BA60) +void __cdecl InterpolateMatrix(); // 0x0041BA60 #define InterpolateArmMatrix ((void(__cdecl*)(void)) 0x0041BC10) void __cdecl DrawGunFlash(int weapon, int clip); From c2a7ffb8546609fcaeae0d3d56b430658864ec3b Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 19 Mar 2022 15:03:33 +0100 Subject: [PATCH 34/66] Decompiled InterpolateArmMatrix() --- game/draw.cpp | 24 +++++++++++++++++++++++- game/draw.h | 2 +- 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 20ba007..8797cce 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1365,6 +1365,28 @@ void __cdecl InterpolateMatrix() { } } +void __cdecl InterpolateArmMatrix() { + PhdMatrixPtr->_00 = PhdMatrixPtr[-2]._00; + PhdMatrixPtr->_01 = PhdMatrixPtr[-2]._01; + PhdMatrixPtr->_02 = PhdMatrixPtr[-2]._02; + PhdMatrixPtr->_10 = PhdMatrixPtr[-2]._10; + PhdMatrixPtr->_11 = PhdMatrixPtr[-2]._11; + PhdMatrixPtr->_12 = PhdMatrixPtr[-2]._12; + PhdMatrixPtr->_20 = PhdMatrixPtr[-2]._20; + PhdMatrixPtr->_21 = PhdMatrixPtr[-2]._21; + PhdMatrixPtr->_22 = PhdMatrixPtr[-2]._22; + + if (IMRate == 2) { + PhdMatrixPtr->_03 = (IMPtr->_03 + PhdMatrixPtr->_03) / 2; + PhdMatrixPtr->_13 = (IMPtr->_13 + PhdMatrixPtr->_13) / 2; + PhdMatrixPtr->_23 = (IMPtr->_23 + PhdMatrixPtr->_23) / 2; + } else { + PhdMatrixPtr->_03 += IMFrac * (IMPtr->_03 - PhdMatrixPtr->_03) / IMRate; + PhdMatrixPtr->_13 += IMFrac * (IMPtr->_13 - PhdMatrixPtr->_13) / IMRate; + PhdMatrixPtr->_23 += IMFrac * (IMPtr->_23 - PhdMatrixPtr->_23) / IMRate; + } +} + void __cdecl DrawGunFlash(int weapon, int clip) { __int16 light; int len; @@ -1477,7 +1499,7 @@ void Inject_Draw() { INJECT(0x0041BA30, phd_PutPolygons_I); INJECT(0x0041BA60, InterpolateMatrix); -// INJECT(0x0041BC10, InterpolateArmMatrix); + INJECT(0x0041BC10, InterpolateArmMatrix); INJECT(0x0041BD10, DrawGunFlash); diff --git a/game/draw.h b/game/draw.h index 0a0cdea..4c1580f 100644 --- a/game/draw.h +++ b/game/draw.h @@ -59,7 +59,7 @@ void __cdecl phd_RotYXZsuperpack(UINT16 **pptr, int index); // 0x0041B980 void __cdecl phd_PutPolygons_I(__int16 *ptrObj, int clip); // 0x0041BA30 void __cdecl InterpolateMatrix(); // 0x0041BA60 -#define InterpolateArmMatrix ((void(__cdecl*)(void)) 0x0041BC10) +void __cdecl InterpolateArmMatrix(); // 0x0041BC10 void __cdecl DrawGunFlash(int weapon, int clip); From 0313b1f52a9bd87f48b5ae476f18881ef32bc9c6 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 20 Mar 2022 08:29:48 +0100 Subject: [PATCH 35/66] Decompiled GetFrames() --- game/draw.cpp | 25 ++++++++++++++++++++++++- game/draw.h | 2 +- 2 files changed, 25 insertions(+), 2 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 8797cce..f7beec0 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1452,6 +1452,29 @@ void __cdecl DrawGunFlash(int weapon, int clip) { #endif // FEATURE_VIDEOFX_IMPROVED } +int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate) { + ANIM_STRUCT *anim; + int interopLow, interop; + int frameCurrent; + int frameEnd; + + anim = &Anims[item->animNumber]; + frames[0] = frames[1] = anim->framePtr; + interopLow = LOBYTE(anim->interpolation); + *rate = interopLow; + frameCurrent = item->frameNumber - anim->frameBase; + frames[0] += frameCurrent / interopLow * (anim->interpolation >> 8); + frames[1] = &frames[0][anim->interpolation >> 8]; + if (!(frameCurrent % interopLow)) { + return 0; + } + interop = interopLow * (frameCurrent / interopLow + 1); + if (interop > anim->frameEnd) { + *rate = anim->frameEnd + interopLow - interop; + } + return frameCurrent % interopLow; +} + void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff) { int idx = ( DynamicLightCount < ARRAY_SIZE(DynamicLights) ) ? DynamicLightCount++ : 0; DynamicLights[idx].x = x; @@ -1504,7 +1527,7 @@ void Inject_Draw() { INJECT(0x0041BD10, DrawGunFlash); // INJECT(0x0041BE80, CalculateObjectLighting); -// INJECT(0x0041BF70, GetFrames); + INJECT(0x0041BF70, GetFrames); // INJECT(0x0041C010, GetBoundsAccurate); // INJECT(0x0041C090, GetBestFrame); diff --git a/game/draw.h b/game/draw.h index 4c1580f..fc7d6f1 100644 --- a/game/draw.h +++ b/game/draw.h @@ -64,7 +64,7 @@ void __cdecl InterpolateArmMatrix(); // 0x0041BC10 void __cdecl DrawGunFlash(int weapon, int clip); #define CalculateObjectLighting ((void(__cdecl*)(ITEM_INFO*, __int16*)) 0x0041BE80) -#define GetFrames ((int(__cdecl*)(ITEM_INFO*, __int16**, int*)) 0x0041BF70) +int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate); // 0x0041BF70 #define GetBoundsAccurate ((__int16*(__cdecl*)(ITEM_INFO*)) 0x0041C010) #define GetBestFrame ((__int16*(__cdecl*)(ITEM_INFO*)) 0x0041C090) From ea211b27814edc8a4bf852767b0f21d815e01f2d Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 20 Mar 2022 08:44:25 +0100 Subject: [PATCH 36/66] Decompiled GetBoundsAccurate() --- game/draw.cpp | 17 +++++++++++++++-- game/draw.h | 2 +- global/vars.h | 1 + 3 files changed, 17 insertions(+), 3 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index f7beec0..77531ea 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1456,7 +1456,6 @@ int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate) { ANIM_STRUCT *anim; int interopLow, interop; int frameCurrent; - int frameEnd; anim = &Anims[item->animNumber]; frames[0] = frames[1] = anim->framePtr; @@ -1475,6 +1474,20 @@ int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate) { return frameCurrent % interopLow; } +__int16* __cdecl GetBoundsAccurate(ITEM_INFO* item) { + int rate, frac; + __int16* frames[2]; + + frac = GetFrames(item, frames, &rate); + if (!frac) { + return frames[0]; + } + for (int i = 0; i < 6; i++, frames[0]++, frames[1]++) { + InterpolateBounds[i] = *frames[0] + frac * (*frames[1] - *frames[0]) / rate; + } + return InterpolateBounds; +} + void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff) { int idx = ( DynamicLightCount < ARRAY_SIZE(DynamicLights) ) ? DynamicLightCount++ : 0; DynamicLights[idx].x = x; @@ -1528,7 +1541,7 @@ void Inject_Draw() { // INJECT(0x0041BE80, CalculateObjectLighting); INJECT(0x0041BF70, GetFrames); -// INJECT(0x0041C010, GetBoundsAccurate); + INJECT(0x0041C010, GetBoundsAccurate); // INJECT(0x0041C090, GetBestFrame); INJECT(0x0041C0D0, AddDynamicLight); diff --git a/game/draw.h b/game/draw.h index fc7d6f1..656c400 100644 --- a/game/draw.h +++ b/game/draw.h @@ -65,7 +65,7 @@ void __cdecl DrawGunFlash(int weapon, int clip); #define CalculateObjectLighting ((void(__cdecl*)(ITEM_INFO*, __int16*)) 0x0041BE80) int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate); // 0x0041BF70 -#define GetBoundsAccurate ((__int16*(__cdecl*)(ITEM_INFO*)) 0x0041C010) +__int16* __cdecl GetBoundsAccurate(ITEM_INFO* item); // 0x0041C010 #define GetBestFrame ((__int16*(__cdecl*)(ITEM_INFO*)) 0x0041C090) void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff); // 0x0041C0D0 diff --git a/global/vars.h b/global/vars.h index 46ab75b..d9eb049 100644 --- a/global/vars.h +++ b/global/vars.h @@ -416,6 +416,7 @@ extern APP_SETTINGS SavedAppSettings; #define IMFrac VAR_U_(0x005258F0, int) #define IMPtr VAR_U_(0x00526188, PHD_MATRIX*) #define IMStack ARRAY_(0x005252C0, PHD_MATRIX, [32]) +#define InterpolateBounds ARRAY_(0x005261A0, __int16, [6]) // Initialized arrays #define TrackIDs ARRAY_(0x004642F0, __int16, [16]) /* = {2, 0}; */ From 8311f393818c48c11048b9814b195b5556c25e85 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 20 Mar 2022 08:51:55 +0100 Subject: [PATCH 37/66] Decompiled GetBestFrame() - Fixed code style for pointer. --- game/draw.cpp | 18 ++++++++++++++---- game/draw.h | 6 +++--- 2 files changed, 17 insertions(+), 7 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 77531ea..67c8a76 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -1452,7 +1452,7 @@ void __cdecl DrawGunFlash(int weapon, int clip) { #endif // FEATURE_VIDEOFX_IMPROVED } -int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate) { +int __cdecl GetFrames(ITEM_INFO *item, __int16 **frames, int *rate) { ANIM_STRUCT *anim; int interopLow, interop; int frameCurrent; @@ -1474,9 +1474,9 @@ int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate) { return frameCurrent % interopLow; } -__int16* __cdecl GetBoundsAccurate(ITEM_INFO* item) { +__int16 *__cdecl GetBoundsAccurate(ITEM_INFO *item) { int rate, frac; - __int16* frames[2]; + __int16 *frames[2]; frac = GetFrames(item, frames, &rate); if (!frac) { @@ -1488,6 +1488,16 @@ __int16* __cdecl GetBoundsAccurate(ITEM_INFO* item) { return InterpolateBounds; } +__int16 *__cdecl GetBestFrame(ITEM_INFO *item) { + int frac, rate; + __int16 *frames[2]; + frac = GetFrames(item, frames, &rate); + if (frac > rate / 2) { + return frames[1]; + } + return frames[0]; +} + void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff) { int idx = ( DynamicLightCount < ARRAY_SIZE(DynamicLights) ) ? DynamicLightCount++ : 0; DynamicLights[idx].x = x; @@ -1542,7 +1552,7 @@ void Inject_Draw() { // INJECT(0x0041BE80, CalculateObjectLighting); INJECT(0x0041BF70, GetFrames); INJECT(0x0041C010, GetBoundsAccurate); -// INJECT(0x0041C090, GetBestFrame); + INJECT(0x0041C090, GetBestFrame); INJECT(0x0041C0D0, AddDynamicLight); } diff --git a/game/draw.h b/game/draw.h index 656c400..27e37c9 100644 --- a/game/draw.h +++ b/game/draw.h @@ -64,9 +64,9 @@ void __cdecl InterpolateArmMatrix(); // 0x0041BC10 void __cdecl DrawGunFlash(int weapon, int clip); #define CalculateObjectLighting ((void(__cdecl*)(ITEM_INFO*, __int16*)) 0x0041BE80) -int __cdecl GetFrames(ITEM_INFO *item, __int16** frames, int* rate); // 0x0041BF70 -__int16* __cdecl GetBoundsAccurate(ITEM_INFO* item); // 0x0041C010 -#define GetBestFrame ((__int16*(__cdecl*)(ITEM_INFO*)) 0x0041C090) +int __cdecl GetFrames(ITEM_INFO *item, __int16 **frames, int *rate); // 0x0041BF70 +__int16 *__cdecl GetBoundsAccurate(ITEM_INFO *item); // 0x0041C010 +__int16 *__cdecl GetBestFrame(ITEM_INFO *item); // 0x0041C090 void __cdecl AddDynamicLight(int x, int y, int z, int intensity, int falloff); // 0x0041C0D0 From 8e9ad3e013250d909bebbb64c5befdd8629a227a Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 20 Mar 2022 08:55:08 +0100 Subject: [PATCH 38/66] Update TR2_progress.txt --- TR2_progress.txt | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 7b8410a..b29b310 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -261,8 +261,8 @@ x function is unused / included in another function 0x00418670: * DinoControl game/draw.cpp -0x00418920: * DrawPhaseCinematic -0x00418960: * DrawPhaseGame +0x00418920: + DrawPhaseCinematic +0x00418960: + DrawPhaseGame 0x004189A0: + DrawRooms 0x00418C50: + GetRoomBounds 0x00418E20: + SetRoomBounds @@ -273,27 +273,27 @@ x function is unused / included in another function 0x004199C0: + DrawSpriteItem ----------: + DrawDummyItem 0x00419A50: + DrawAnimatingItem -0x00419DD0: * DrawLara +0x00419DD0: + DrawLara 0x0041AB00: + DrawLaraInt -0x0041B6F0: * InitInterpolate -0x0041B730: * phd_PopMatrix_I -0x0041B760: * phd_PushMatrix_I -0x0041B790: * phd_RotY_I -0x0041B7D0: * phd_RotX_I -0x0041B810: * phd_RotZ_I -0x0041B850: * phd_TranslateRel_I -0x0041B8A0: * phd_TranslateRel_ID -0x0041B8F0: * phd_RotYXZ_I -0x0041B940: * phd_RotYXZsuperpack_I +0x0041B6F0: + InitInterpolate +0x0041B730: + phd_PopMatrix_I +0x0041B760: + phd_PushMatrix_I +0x0041B790: + phd_RotY_I +0x0041B7D0: + phd_RotX_I +0x0041B810: + phd_RotZ_I +0x0041B850: + phd_TranslateRel_I +0x0041B8A0: + phd_TranslateRel_ID +0x0041B8F0: + phd_RotYXZ_I +0x0041B940: + phd_RotYXZsuperpack_I 0x0041B980: + phd_RotYXZsuperpack 0x0041BA30: + phd_PutPolygons_I -0x0041BA60: * InterpolateMatrix -0x0041BC10: * InterpolateArmMatrix +0x0041BA60: + InterpolateMatrix +0x0041BC10: + InterpolateArmMatrix 0x0041BD10: + DrawGunFlash 0x0041BE80: * CalculateObjectLighting -0x0041BF70: * GetFrames -0x0041C010: * GetBoundsAccurate -0x0041C090: * GetBestFrame +0x0041BF70: + GetFrames +0x0041C010: + GetBoundsAccurate +0x0041C090: + GetBestFrame 0x0041C0D0: + AddDynamicLight game/eel.cpp From 831e9a906fbcb64be7393032d76ce98afbd6e071 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 10:53:17 +0100 Subject: [PATCH 39/66] Decompiled LaraInitialiseMeshes() --- game/laramisc.cpp | 61 ++++++++++++++++++++++++++++++++++++++++++++++- game/laramisc.h | 2 +- 2 files changed, 61 insertions(+), 2 deletions(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index 67e802b..d0992ef 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -691,6 +691,65 @@ void __cdecl InitialiseLaraInventory(int levelID) { InitialiseNewWeapon(); } +void __cdecl LaraInitialiseMeshes(int levelID) { + START_INFO *start = &SaveGame.start[levelID]; + + for (int i = 0; i < ARRAY_SIZE(Lara.mesh_ptrs); i++) { + Lara.mesh_ptrs[i] = MeshPtr[Objects[ID_LARA].meshIndex + i]; + } + + // fill the weapon holster + switch (start->gunType) { + case LGT_Pistols: + Lara.mesh_ptrs[1] = MeshPtr[Objects[ID_LARA_PISTOLS].meshIndex + 1]; + Lara.mesh_ptrs[4] = MeshPtr[Objects[ID_LARA_PISTOLS].meshIndex + 4]; + break; + case LGT_Uzis: + Lara.mesh_ptrs[1] = MeshPtr[Objects[ID_LARA_UZIS].meshIndex + 1]; + Lara.mesh_ptrs[4] = MeshPtr[Objects[ID_LARA_UZIS].meshIndex + 4]; + break; + case LGT_Magnums: + Lara.mesh_ptrs[1] = MeshPtr[Objects[ID_LARA_MAGNUMS].meshIndex + 1]; + Lara.mesh_ptrs[4] = MeshPtr[Objects[ID_LARA_MAGNUMS].meshIndex + 4]; + break; + case LGT_Unarmed: + default: + break; + } + + // if you start with the flare, assign the mesh in the hand + if (start->gunType == LGT_Flare) { + Lara.mesh_ptrs[13] = MeshPtr[Objects[ID_LARA_FLARE].meshIndex + 13]; + } + + // check for back gun now ! + switch (start->gunType) { + case LGT_M16: + Lara.back_gun = ID_LARA_M16; + return; + case LGT_Shotgun: + Lara.back_gun = ID_LARA_SHOTGUN; + return; + case LGT_Grenade: + Lara.back_gun = ID_LARA_GRENADE; + return; + case LGT_Harpoon: + Lara.back_gun = ID_LARA_HARPOON; + return; + } + + // if there is no back gun on start and if there is one in inventory, assign it ! + if (start->has_shotgun) { + Lara.back_gun = ID_LARA_SHOTGUN; + } else if (start->has_m16) { + Lara.back_gun = ID_LARA_M16; + } else if (start->has_grenade) { + Lara.back_gun = ID_LARA_GRENADE; + } else if (start->has_harpoon) { + Lara.back_gun = ID_LARA_HARPOON; + } +} + /* * Inject function */ @@ -708,5 +767,5 @@ void Inject_LaraMisc() { INJECT(0x004312A0, InitialiseLaraInventory); -// INJECT(0x00431610, LaraInitialiseMeshes); + INJECT(0x00431610, LaraInitialiseMeshes); } diff --git a/game/laramisc.h b/game/laramisc.h index 2e2ea09..49028e2 100644 --- a/game/laramisc.h +++ b/game/laramisc.h @@ -40,6 +40,6 @@ void __cdecl InitialiseLaraLoad(__int16 itemID); // 0x00430FB0 void __cdecl InitialiseLaraInventory(int levelID); // 0x004312A0 -#define LaraInitialiseMeshes ((void(__cdecl*)(int)) 0x00431610) +void __cdecl LaraInitialiseMeshes(int levelID); // 0x00431610 #endif // LARAMISC_H_INCLUDED From 22d1bbed692d744f93d3f7afa4878518bbbfcfd3 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 11:28:23 +0100 Subject: [PATCH 40/66] Decompiled InitialiseLara() - Fixed warning about ARRAY_SIZE() returning UINT32 instead of INT. - Used pointer for Lara instead, just because these two variable have the same text size and height (lara & item) --- game/laramisc.cpp | 91 +++++++++++++++++++++++++++++++++++++++++++++-- game/laramisc.h | 2 +- global/vars.h | 1 + 3 files changed, 91 insertions(+), 3 deletions(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index d0992ef..918698c 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -492,6 +492,93 @@ void __cdecl InitialiseLaraLoad(__int16 itemID) { LaraItem = &Items[itemID]; } +void __cdecl InitialiseLara(GF_LEVEL_TYPE type) { + ITEM_INFO* item = LaraItem; + LARA_INFO* lara = &Lara; + + item->data = lara; + item->collidable = FALSE; + item->hitPoints = 1000; + + lara->hit_direction = -1; + lara->skidoo = -1; + lara->weapon_item = -1; + lara->calc_fallspeed = 0; + lara->climb_status = 0; + lara->pose_count = 0; + lara->hit_frame = 0; + lara->air = 1800; + lara->dive_count = 0; + lara->death_count = 0; + lara->current_active = 0; + lara->spaz_effect_count = 0; + lara->flare_age = 0; + lara->flare_frame = 0; + lara->flare_control_left = FALSE; + lara->flare_control_right = FALSE; + lara->burn = FALSE; + lara->CanMonkeySwing = FALSE; + lara->extra_anim = 0; + lara->keep_ducked = FALSE; + lara->look = TRUE; + lara->back_gun = ID_LARA; + lara->last_pos.x = item->pos.x; + lara->last_pos.y = item->pos.y; + lara->last_pos.z = item->pos.z; + lara->spaz_effect = 0; + lara->mesh_effects = 0; + lara->target = 0; + lara->turn_rate = 0; + lara->move_angle = 0; + lara->head_z_rot = 0; + lara->head_y_rot = 0; + lara->head_x_rot = 0; + lara->torso_z_rot = 0; + lara->torso_y_rot = 0; + lara->torso_x_rot = 0; + lara->right_arm.flash_gun = 0; + lara->left_arm.flash_gun = 0; + lara->right_arm.lock = FALSE; + lara->left_arm.lock = FALSE; + lara->creature = NULL; + + if (type == GFL_NORMAL && GF_LaraStartAnim) { + lara->gun_status = LGS_HandBusy; + lara->water_status = LWS_AboveWater; + item->animNumber = Objects[ID_LARA_EXTRA].animIndex; + item->frameNumber = Anims[item->animNumber].frameBase; + item->goalAnimState = GF_LaraStartAnim; + AnimateLara(item); + Camera.type = CAM_Cinematic; + CineCurrentFrame = 0; + CinematicPos = item->pos; + } else if CHK_ANY(RoomInfo[item->roomNumber].flags, ROOM_UNDERWATER) { + lara->gun_status = LGS_Armless; + item->animNumber = 108; + item->frameNumber = Anims[108].frameBase; + item->goalAnimState = AS_TREAD; + item->currentAnimState = AS_TREAD; + item->fallSpeed = 0; + } else { + lara->gun_status = LGS_Armless; + item->animNumber = 11; + item->frameNumber = Anims[11].frameBase; + item->goalAnimState = AS_STOP; + item->currentAnimState = AS_STOP; + } + + if (type == GFL_CUTSCENE) { + lara->gun_status = LGS_Armless; + for (UINT32 i = 0; i < ARRAY_SIZE(lara->mesh_ptrs); i++) { + lara->mesh_ptrs[i] = MeshPtr[Objects[ID_LARA].meshIndex + i]; + } + lara->mesh_ptrs[1] = MeshPtr[Objects[ID_LARA_PISTOLS].meshIndex + 1]; + lara->mesh_ptrs[4] = MeshPtr[Objects[ID_LARA_PISTOLS].meshIndex + 4]; + } else { + InitialiseLaraInventory(CurrentLevel); + } +} + void __cdecl InitialiseLaraInventory(int levelID) { int i; START_INFO *start = &SaveGame.start[levelID]; @@ -694,7 +781,7 @@ void __cdecl InitialiseLaraInventory(int levelID) { void __cdecl LaraInitialiseMeshes(int levelID) { START_INFO *start = &SaveGame.start[levelID]; - for (int i = 0; i < ARRAY_SIZE(Lara.mesh_ptrs); i++) { + for (UINT32 i = 0; i < ARRAY_SIZE(Lara.mesh_ptrs); i++) { Lara.mesh_ptrs[i] = MeshPtr[Objects[ID_LARA].meshIndex + i]; } @@ -763,7 +850,7 @@ void Inject_LaraMisc() { INJECT(0x00430F90, ControlLaraExtra); INJECT(0x00430FB0, InitialiseLaraLoad); -// INJECT(0x00430FE0, InitialiseLara); + INJECT(0x00430FE0, InitialiseLara); INJECT(0x004312A0, InitialiseLaraInventory); diff --git a/game/laramisc.h b/game/laramisc.h index 49028e2..1be2b5c 100644 --- a/game/laramisc.h +++ b/game/laramisc.h @@ -36,7 +36,7 @@ void __cdecl LaraCheatGetStuff(); // 0x00430ED0 void __cdecl ControlLaraExtra(__int16 itemID); // 0x00430F90 void __cdecl InitialiseLaraLoad(__int16 itemID); // 0x00430FB0 -#define InitialiseLara ((void(__cdecl*)(int)) 0x00430FE0) +void __cdecl InitialiseLara(GF_LEVEL_TYPE type); // 0x00430FE0 void __cdecl InitialiseLaraInventory(int levelID); // 0x004312A0 diff --git a/global/vars.h b/global/vars.h index d9eb049..7ec4e12 100644 --- a/global/vars.h +++ b/global/vars.h @@ -406,6 +406,7 @@ extern APP_SETTINGS SavedAppSettings; #define IsCinematicLoaded VAR_U_(0x005262F4, __int16) #define CineFramesCount VAR_U_(0x005262F6, __int16) #define CineFrames VAR_U_(0x005262F8, CINE_FRAME_INFO*) +#define CinematicPos VAR_U_(0x00526300, PHD_3DPOS) #define CineLevelID VAR_U_(0x00526312, __int16) #define CineFrameIdx VAR_U_(0x00526314, __int16) #define Camera VAR_U_(0x00526320, CAMERA_INFO) From afd27068d55f0363390118d96397314a267ae69b Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 13:17:25 +0100 Subject: [PATCH 41/66] Decompiled AnimateLara() - Fixed pointer wrong pos. - Added EffectFunctions array. - Removed space between INJECT and in the .H too --- game/control.h | 4 +- game/laramisc.cpp | 114 ++++++++++++++++++++++++++++++++++++++++++---- game/laramisc.h | 7 +-- global/vars.h | 1 + 4 files changed, 110 insertions(+), 16 deletions(-) diff --git a/game/control.h b/game/control.h index 8d91dd6..5640981 100644 --- a/game/control.h +++ b/game/control.h @@ -31,8 +31,8 @@ int __cdecl ControlPhase(int nTicks, BOOL demoMode); #define AnimateItem ((void(__cdecl*)(ITEM_INFO*)) 0x004146C0) -// 0x00414A30: GetChange -// 0x00414AE0: TranslateItem +#define GetChange ((int(__cdecl*)(ITEM_INFO*,ANIM_STRUCT*)) 0x00414A30) +#define TranslateItem ((void(__cdecl*)(ITEM_INFO*,int,int,int)) 0x00414AE0) #define GetFloor ((FLOOR_INFO*(__cdecl*)(int, int, int, __int16*)) 0x00414B40) #define GetWaterHeight ((int(__cdecl*)(int, int, int, __int16)) 0x00414CE0) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index 918698c..0cb5862 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -320,6 +320,109 @@ void __cdecl LaraControl(__int16 itemID) { Lara.last_pos.z = item->pos.z; } +void __cdecl AnimateLara(ITEM_INFO* item) { + ANIM_STRUCT *anim; + int waterSurfDist; + int velocity; + short *command, soundType; + bool notLand, notWater; + + ++item->frameNumber; + anim = &Anims[item->animNumber]; + if (anim->numberChanges > 0 && GetChange(item, anim)) { + anim = &Anims[item->animNumber]; + item->currentAnimState = anim->currentAnimState; + } + + if (item->frameNumber > anim->frameEnd) { + command = &AnimCommands[anim->commandIndex]; + for (short i = anim->numberCommands; i > 0; i--) { + switch (*command++) { + case 1: + TranslateItem(item, command[0], command[1], command[2]); + command += 3; + break; + case 2: + item->fallSpeed = command[0]; + item->speed = command[1]; + item->gravity = TRUE; + if (Lara.calc_fallspeed) { + item->fallSpeed = Lara.calc_fallspeed; + Lara.calc_fallspeed = 0; + } + command += 2; + break; + case 3: + if (Lara.gun_status != LGS_Special) + Lara.gun_status = LGS_Armless; + break; + case 5: + case 6: + command += 2; + break; + } + } + item->animNumber = anim->jumpAnimNum; + item->frameNumber = anim->jumpFrameNum; + anim = &Anims[item->animNumber]; + item->currentAnimState = anim->currentAnimState; + } + + if (anim->numberCommands > 0) { + command = &AnimCommands[anim->commandIndex]; + for (short i = anim->numberCommands; i > 0; i--) { + switch (*command++) { + case 1: + command += 3; + continue; + case 5: + if (item->frameNumber != command[0]) { + break; + } + waterSurfDist = Lara.water_surface_dist; + soundType = command[1] & 0xC000; // LAND or WATER + notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != 0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); + if (soundType != 0 && notLand && notWater) { + break; + } + PlaySoundEffect(command[1] & 0x3FFF, &item->pos, SFX_ALWAYS); + break; + case 6: + if (item->frameNumber != command[0]) { + break; + } + waterSurfDist = Lara.water_surface_dist; + soundType = command[1] & 0xC000; // LAND or WATER + notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != 0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); + if (soundType != 0 && notLand && notWater) { + break; + } + EffectFunctions[command[1] & 0x3FFF](item); + break; + } + command += 2; + } + } + + if (item->gravity) { + velocity = anim->velocity + anim->acceleration * (item->frameNumber - anim->frameBase - 1); + item->speed -= velocity >> 16; + item->speed += (anim->acceleration + velocity) >> 16; + item->fallSpeed += item->fallSpeed >= 128 ? 1 : 6; + item->pos.y += item->fallSpeed; + } else { + velocity = anim->velocity; + if (anim->acceleration) + velocity += anim->acceleration * (item->frameNumber - anim->frameBase); + item->speed = velocity >> 16; + } + + item->pos.x += (item->speed * phd_sin(Lara.move_angle)) >> W2V_SHIFT; + item->pos.z += (item->speed * phd_cos(Lara.move_angle)) >> W2V_SHIFT; +} + void __cdecl UseItem(__int16 itemID) { if( itemID <= ID_NONE || itemID >= ID_NUMBER_OBJECTS ) return; @@ -493,8 +596,8 @@ void __cdecl InitialiseLaraLoad(__int16 itemID) { } void __cdecl InitialiseLara(GF_LEVEL_TYPE type) { - ITEM_INFO* item = LaraItem; - LARA_INFO* lara = &Lara; + ITEM_INFO *item = LaraItem; + LARA_INFO *lara = &Lara; item->data = lara; item->collidable = FALSE; @@ -842,17 +945,12 @@ void __cdecl LaraInitialiseMeshes(int levelID) { */ void Inject_LaraMisc() { INJECT(0x00430380, LaraControl); - -// INJECT(0x00430A10, AnimateLara); - + INJECT(0x00430A10, AnimateLara); INJECT(0x00430D10, UseItem); INJECT(0x00430ED0, LaraCheatGetStuff); INJECT(0x00430F90, ControlLaraExtra); INJECT(0x00430FB0, InitialiseLaraLoad); - INJECT(0x00430FE0, InitialiseLara); - INJECT(0x004312A0, InitialiseLaraInventory); - INJECT(0x00431610, LaraInitialiseMeshes); } diff --git a/game/laramisc.h b/game/laramisc.h index 1be2b5c..2a06d87 100644 --- a/game/laramisc.h +++ b/game/laramisc.h @@ -28,18 +28,13 @@ * Function list */ void __cdecl LaraControl(__int16 itemID); - -#define AnimateLara ((void(__cdecl*)(ITEM_INFO*)) 0x00430A10) - +void __cdecl AnimateLara(ITEM_INFO* item); // 0x00430A10 void __cdecl UseItem(__int16 itemID); // 0x00430D10 void __cdecl LaraCheatGetStuff(); // 0x00430ED0 void __cdecl ControlLaraExtra(__int16 itemID); // 0x00430F90 void __cdecl InitialiseLaraLoad(__int16 itemID); // 0x00430FB0 - void __cdecl InitialiseLara(GF_LEVEL_TYPE type); // 0x00430FE0 - void __cdecl InitialiseLaraInventory(int levelID); // 0x004312A0 - void __cdecl LaraInitialiseMeshes(int levelID); // 0x00431610 #endif // LARAMISC_H_INCLUDED diff --git a/global/vars.h b/global/vars.h index 7ec4e12..e373fe5 100644 --- a/global/vars.h +++ b/global/vars.h @@ -58,6 +58,7 @@ #define ins_objectG3 (*(__int16*(__cdecl **)(__int16*,int,SORTTYPE)) 0x004BCB40) #define SfxFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define EffectFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) // Initialized variables #define PerspectiveDistance VAR_I_(0x00464060, DWORD, 0x3000000) From d1433ef1842c8a294e628e8fc7c4ef3fc316f507 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 15:42:22 +0100 Subject: [PATCH 42/66] Decompiled LaraUnderWater() - Added the door cheat from Tomb1Main. Also: - Decompiled ShutThatDoor() OpenThatDoor() DoorControl() - Added 2 new structure. - Added lara function array ! --- game/lara.h | 6 +-- game/laraswim.cpp | 135 +++++++++++++++++++++++++++++++++++++++++++++- game/laraswim.h | 4 +- game/objects.cpp | 54 +++++++++++++++++-- game/objects.h | 8 +-- global/types.h | 13 +++++ global/vars.h | 7 ++- 7 files changed, 212 insertions(+), 15 deletions(-) diff --git a/game/lara.h b/game/lara.h index c3bdb97..ca31e99 100644 --- a/game/lara.h +++ b/game/lara.h @@ -29,9 +29,9 @@ */ #define LaraAboveWater ((void(__cdecl*)(ITEM_INFO*, COLL_INFO*)) 0x00427560) -// 0x00427700: LookUpDown -// 0x00427770: LookLeftRight -// 0x004277F0: ResetLook +#define LookUpDown ((void(__cdecl*)(void)) 0x00427700) +#define LookLeftRight ((void(__cdecl*)(void)) 0x00427770) +#define ResetLook ((void(__cdecl*)(void)) 0x004277F0) // 0x00427880: lara_as_walk // 0x00427910: lara_as_run // 0x00427A60: lara_as_stop diff --git a/game/laraswim.cpp b/game/laraswim.cpp index d9bfeca..9a0c330 100644 --- a/game/laraswim.cpp +++ b/game/laraswim.cpp @@ -21,8 +21,141 @@ #include "global/precompiled.h" #include "game/laraswim.h" +#include "3dsystem/phd_math.h" +#include "game/control.h" +#include "game/collide.h" +#include "game/items.h" +#include "game/lara.h" +#include "game/larafire.h" +#include "game/laramisc.h" +#include "game/objects.h" #include "global/vars.h" +#ifdef FEATURE_CHEAT +static int OpenDoorsCheatCooldown = 0; +// NOTE: this come from Tomb1Main (Door Cheat) +void DoorOpenNearest(ITEM_INFO *lara_item) { + int max_dist = SQR((1024 * 2) >> 8); + for (int itemID = 0; itemID < LevelItemCount; itemID++) { + ITEM_INFO *item = &Items[itemID]; + int dx = (item->pos.x - lara_item->pos.x) >> 8; + int dy = (item->pos.y - lara_item->pos.y) >> 8; + int dz = (item->pos.z - lara_item->pos.z) >> 8; + int dist = SQR(dx) + SQR(dy) + SQR(dz); + if (dist > max_dist) { + continue; + } + + if ((item->objectID < ID_DOOR_TYPE1 + || item->objectID > ID_DOOR_TYPE8) + && item->objectID != ID_TRAPDOOR_TYPE1 + && item->objectID != ID_TRAPDOOR_TYPE2 + && item->objectID != ID_TRAPDOOR_TYPE3) { + continue; + } + + if (!item->active) { + AddActiveItem(itemID); + item->flags |= IFL_CODEBITS; + } else if CHK_ANY(item->flags, IFL_CODEBITS) { + item->flags &= ~IFL_CODEBITS; + } else { + item->flags |= IFL_CODEBITS; + } + item->timer = 0; + item->touchBits = 0; + } +} +#endif + +void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { + int s, s2, c; + + coll->badPos = -NO_HEIGHT; + coll->badNeg = -400; + coll->badCeiling = 400; + coll->old.x = item->pos.x; + coll->old.y = item->pos.y; + coll->old.z = item->pos.z; + coll->radius = 300; + coll->trigger = 0; + coll->flags &= ~0x17; + coll->flags |= 0x18; + + if (CHK_ANY(InputStatus, IN_LOOK) && Lara.look) { + LookLeftRight(); + } else { + ResetLook(); + } + + Lara.look = TRUE; + if (Lara.extra_anim) { + ExtraFunctions[item->currentAnimState](item); + } else { + LaraControlFunctions[item->currentAnimState](item); + } + + if (item->pos.rotZ < -364 || item->pos.rotZ > 364) { + if (item->pos.rotZ >= 0) { + item->pos.rotZ -= 364; + } else { + item->pos.rotZ += 364; + } + } else { + item->pos.rotZ = 0; + } + + CLAMP(item->pos.rotX, -15470, 15470) + CLAMP(item->pos.rotZ, -4004, 4004) + + if (Lara.turn_rate < -364 || Lara.turn_rate > 364) { + if (Lara.turn_rate >= 0) { + Lara.turn_rate -= 364; + } else { + Lara.turn_rate += 364; + } + } else { + Lara.turn_rate = 0; + } + + item->pos.rotY += Lara.turn_rate; + if (Lara.current_active && Lara.water_status != LWS_Cheat) { + LaraWaterCurrent(coll); + } + AnimateLara(item); + + s = (item->fallSpeed * phd_sin(item->pos.rotY)) >> 16; + s2 = (item->fallSpeed * phd_sin(item->pos.rotX)) >> 16; + c = (item->fallSpeed * phd_cos(item->pos.rotY)) >> 16; + item->pos.x += (phd_cos(item->pos.rotX) * s) >> W2V_SHIFT; + item->pos.y -= s2; + item->pos.z += (phd_cos(item->pos.rotX) * c) >> W2V_SHIFT; + + if (Lara.extra_anim == 0) { + if (Lara.water_status != LWS_Cheat) { + LaraBaddieCollision(item, coll); + } + LaraCollisionFunctions[item->currentAnimState](item, coll); + } + +#ifdef FEATURE_CHEAT + // NOTE: this come from Tomb1Main (Door Cheat) + // Press Draw key to open any near door ! + if (Lara.water_status == LWS_Cheat) { + if (OpenDoorsCheatCooldown) { + OpenDoorsCheatCooldown--; + } else if CHK_ANY(InputStatus, IN_DRAW) { + OpenDoorsCheatCooldown = FRAMES_PER_SECOND; + DoorOpenNearest(LaraItem); + } + } +#endif // FEATURE_CHEAT + + UpdateLaraRoom(item, 0); + LaraGun(); + TestTriggers(coll->trigger, FALSE); +} + void __cdecl SwimTurn(ITEM_INFO *item) { if( CHK_ANY(InputStatus, IN_FORWARD) ) { item->pos.rotX -= 2*PHD_DEGREE; @@ -73,7 +206,7 @@ void __cdecl lara_as_swim(ITEM_INFO *item, COLL_INFO *coll) { * Inject function */ void Inject_LaraSwim() { -// INJECT(0x00432000, LaraUnderWater); + INJECT(0x00432000, LaraUnderWater); INJECT(0x00432230, SwimTurn); INJECT(0x004322C0, lara_as_swim); diff --git a/game/laraswim.h b/game/laraswim.h index 5a04c43..0ff1664 100644 --- a/game/laraswim.h +++ b/game/laraswim.h @@ -27,7 +27,7 @@ /* * Function list */ -#define LaraUnderWater ((void(__cdecl*)(ITEM_INFO*, COLL_INFO*)) 0x00432000) +void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll); // 0x00432000 void __cdecl SwimTurn(ITEM_INFO *item); // 0x00432230 void __cdecl lara_as_swim(ITEM_INFO *item, COLL_INFO *coll); // 0x004322C0 @@ -48,6 +48,6 @@ void __cdecl lara_as_swim(ITEM_INFO *item, COLL_INFO *coll); // 0x004322C0 // 0x004326F0: LaraTestWaterDepth // 0x004327C0: LaraSwimCollision -// 0x00432920: LaraWaterCurrent +#define LaraWaterCurrent ((void(__cdecl*)(COLL_INFO*)) 0x00432920) #endif // LARA_SWIM_H_INCLUDED diff --git a/game/objects.cpp b/game/objects.cpp index 46577a9..dd45582 100644 --- a/game/objects.cpp +++ b/game/objects.cpp @@ -21,9 +21,57 @@ #include "global/precompiled.h" #include "game/objects.h" +#include "game/control.h" #include "global/vars.h" +void __cdecl ShutThatDoor(DOORPOS_DATA *door) { + FLOOR_INFO* floor = door->floor; + if (floor != NULL) { + floor->index = 0; + floor->ceiling = -127; + floor->floor = -127; + floor->box = -1; + floor->skyRoom = -1; + floor->pitRoom = -1; + if (door->box != -1) { + Boxes[door->box].overlapIndex |= 0x40; // BLOCKED + } + } +} + +void __cdecl OpenThatDoor(DOORPOS_DATA *door) { + if (door->floor) { + *door->floor = door->data; + if (door->box != -1) { + Boxes[door->box].overlapIndex &= ~0x40; // UNBLOCKED + } + } +} +void __cdecl DoorControl(__int16 itemID) { + ITEM_INFO *item = &Items[itemID]; + DOOR_DATA *data = (DOOR_DATA*)item->data; + + if (TriggerActive(item)) { + if (item->currentAnimState) { + OpenThatDoor(&data->d1); + OpenThatDoor(&data->d2); + OpenThatDoor(&data->d1flip); + OpenThatDoor(&data->d2flip); + } else { + item->goalAnimState = 1; + } + } + else if (item->currentAnimState == 1) { + item->goalAnimState = 0; + } else { + ShutThatDoor(&data->d1); + ShutThatDoor(&data->d2); + ShutThatDoor(&data->d1flip); + ShutThatDoor(&data->d2flip); + } + AnimateItem(item); +} /* * Inject function @@ -45,10 +93,10 @@ void Inject_Objects() { // INJECT(0x00434EB0, SmashWindow); // INJECT(0x00434F80, WindowControl); // INJECT(0x00435020, SmashIceControl); -// INJECT(0x00435100, ShutThatDoor); -// INJECT(0x00435150, OpenThatDoor); + INJECT(0x00435100, ShutThatDoor); + INJECT(0x00435150, OpenThatDoor); // INJECT(0x00435190, InitialiseDoor); -// INJECT(0x00435570, DoorControl); + INJECT(0x00435570, DoorControl); // INJECT(0x00435640, OnDrawBridge); // INJECT(0x00435700, DrawBridgeFloor); // INJECT(0x00435740, DrawBridgeCeiling); diff --git a/game/objects.h b/game/objects.h index 096b944..a7a0ff9 100644 --- a/game/objects.h +++ b/game/objects.h @@ -45,10 +45,10 @@ // 0x00434F80: WindowControl // 0x00435020: SmashIceControl -// 0x00435100: ShutThatDoor -// 0x00435150: OpenThatDoor -// 0x00435190: InitialiseDoor -// 0x00435570: DoorControl +void __cdecl ShutThatDoor(DOORPOS_DATA* door); // 0x00435100 +void __cdecl OpenThatDoor(DOORPOS_DATA* door); // 0x00435150 +#define InitialiseDoor ((void(__cdecl*)(__int16 itemID)) 0x00435190) +void __cdecl DoorControl(__int16 itemID); // 0x00435570 // 0x00435640: OnDrawBridge // 0x00435700: DrawBridgeFloor // 0x00435740: DrawBridgeCeiling diff --git a/global/types.h b/global/types.h index a42d358..ab64f15 100644 --- a/global/types.h +++ b/global/types.h @@ -1861,6 +1861,19 @@ typedef struct MeshInfo_t { __int16 staticNumber; } MESH_INFO; +typedef struct DoorPosData_t { + FLOOR_INFO* floor; + FLOOR_INFO data; + __int16 box; +} DOORPOS_DATA; + +typedef struct DoorData_t { + DOORPOS_DATA d1; + DOORPOS_DATA d1flip; + DOORPOS_DATA d2; + DOORPOS_DATA d2flip; +} DOOR_DATA; + typedef struct RoomInfo_t { __int16 *data; DOOR_INFOS *doors; diff --git a/global/vars.h b/global/vars.h index e373fe5..1fb1db1 100644 --- a/global/vars.h +++ b/global/vars.h @@ -57,8 +57,11 @@ #define ins_objectG4 (*(__int16*(__cdecl **)(__int16*,int,SORTTYPE)) 0x004BCAF8) #define ins_objectG3 (*(__int16*(__cdecl **)(__int16*,int,SORTTYPE)) 0x004BCB40) -#define SfxFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) -#define EffectFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define SfxFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define EffectFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define ExtraFunctions (*(void(__cdecl *(*)[11])(ITEM_INFO*)) 0x00465DF0) +#define LaraControlFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*)) 0x00465CD0) +#define LaraCollisionFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*,COLL_INFO*)) 0x00465E20) // Initialized variables #define PerspectiveDistance VAR_I_(0x00464060, DWORD, 0x3000000) From bb4daf5e6d2b253971c562589c73589a1050f1ef Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 15:52:57 +0100 Subject: [PATCH 43/66] Fix space to tab --- game/laraswim.cpp | 60 +++++++++++++++++++++++------------------------ 1 file changed, 29 insertions(+), 31 deletions(-) diff --git a/game/laraswim.cpp b/game/laraswim.cpp index 9a0c330..443e516 100644 --- a/game/laraswim.cpp +++ b/game/laraswim.cpp @@ -35,36 +35,34 @@ static int OpenDoorsCheatCooldown = 0; // NOTE: this come from Tomb1Main (Door Cheat) void DoorOpenNearest(ITEM_INFO *lara_item) { - int max_dist = SQR((1024 * 2) >> 8); - for (int itemID = 0; itemID < LevelItemCount; itemID++) { - ITEM_INFO *item = &Items[itemID]; - int dx = (item->pos.x - lara_item->pos.x) >> 8; - int dy = (item->pos.y - lara_item->pos.y) >> 8; - int dz = (item->pos.z - lara_item->pos.z) >> 8; - int dist = SQR(dx) + SQR(dy) + SQR(dz); - if (dist > max_dist) { - continue; - } - - if ((item->objectID < ID_DOOR_TYPE1 + int max_dist = SQR((1024 * 2) >> 8); + for (int itemID = 0; itemID < LevelItemCount; itemID++) { + ITEM_INFO *item = &Items[itemID]; + if ((item->objectID < ID_DOOR_TYPE1 || item->objectID > ID_DOOR_TYPE8) && item->objectID != ID_TRAPDOOR_TYPE1 && item->objectID != ID_TRAPDOOR_TYPE2 && item->objectID != ID_TRAPDOOR_TYPE3) { - continue; - } - - if (!item->active) { - AddActiveItem(itemID); - item->flags |= IFL_CODEBITS; - } else if CHK_ANY(item->flags, IFL_CODEBITS) { - item->flags &= ~IFL_CODEBITS; - } else { - item->flags |= IFL_CODEBITS; - } - item->timer = 0; - item->touchBits = 0; - } + continue; + } + int dx = (item->pos.x - lara_item->pos.x) >> 8; + int dy = (item->pos.y - lara_item->pos.y) >> 8; + int dz = (item->pos.z - lara_item->pos.z) >> 8; + int dist = SQR(dx) + SQR(dy) + SQR(dz); + if (dist > max_dist) { + continue; + } + if (!item->active) { + AddActiveItem(itemID); + item->flags |= IFL_CODEBITS; + } else if CHK_ANY(item->flags, IFL_CODEBITS) { + item->flags &= ~IFL_CODEBITS; + } else { + item->flags |= IFL_CODEBITS; + } + item->timer = 0; + item->touchBits = 0; + } } #endif @@ -143,11 +141,11 @@ void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { // Press Draw key to open any near door ! if (Lara.water_status == LWS_Cheat) { if (OpenDoorsCheatCooldown) { - OpenDoorsCheatCooldown--; - } else if CHK_ANY(InputStatus, IN_DRAW) { - OpenDoorsCheatCooldown = FRAMES_PER_SECOND; - DoorOpenNearest(LaraItem); - } + OpenDoorsCheatCooldown--; + } else if CHK_ANY(InputStatus, IN_DRAW) { + OpenDoorsCheatCooldown = FRAMES_PER_SECOND; + DoorOpenNearest(LaraItem); + } } #endif // FEATURE_CHEAT From d07e99af88eefd546963af528bc903e0928c5b40 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 16:23:24 +0100 Subject: [PATCH 44/66] Changed short to __int16 Also fixed a warning about a bool always true because of this: soundType != 0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT) --- game/laramisc.cpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index 0cb5862..817c466 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -324,7 +324,7 @@ void __cdecl AnimateLara(ITEM_INFO* item) { ANIM_STRUCT *anim; int waterSurfDist; int velocity; - short *command, soundType; + __int16 *command, soundType; bool notLand, notWater; ++item->frameNumber; @@ -336,7 +336,7 @@ void __cdecl AnimateLara(ITEM_INFO* item) { if (item->frameNumber > anim->frameEnd) { command = &AnimCommands[anim->commandIndex]; - for (short i = anim->numberCommands; i > 0; i--) { + for (__int16 i = anim->numberCommands; i > 0; i--) { switch (*command++) { case 1: TranslateItem(item, command[0], command[1], command[2]); @@ -370,7 +370,7 @@ void __cdecl AnimateLara(ITEM_INFO* item) { if (anim->numberCommands > 0) { command = &AnimCommands[anim->commandIndex]; - for (short i = anim->numberCommands; i > 0; i--) { + for (__int16 i = anim->numberCommands; i > 0; i--) { switch (*command++) { case 1: command += 3; @@ -381,8 +381,8 @@ void __cdecl AnimateLara(ITEM_INFO* item) { } waterSurfDist = Lara.water_surface_dist; soundType = command[1] & 0xC000; // LAND or WATER - notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); - notWater = soundType != 0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); + notLand = soundType != (__int16)0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != (__int16)0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); if (soundType != 0 && notLand && notWater) { break; } @@ -394,8 +394,8 @@ void __cdecl AnimateLara(ITEM_INFO* item) { } waterSurfDist = Lara.water_surface_dist; soundType = command[1] & 0xC000; // LAND or WATER - notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); - notWater = soundType != 0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); + notLand = soundType != (__int16)0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != (__int16)0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); if (soundType != 0 && notLand && notWater) { break; } From 0d2916f69bb08cfef2811447e3708e30f90eecb5 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 21 Mar 2022 19:02:22 +0100 Subject: [PATCH 45/66] Fix lara death in offshore rig Lara die directly because there is missing variable in InitialiseLara() caused by me :x --- game/laramisc.cpp | 7 +++++-- game/laraswim.cpp | 20 ++++++++++---------- 2 files changed, 15 insertions(+), 12 deletions(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index 817c466..aad6a3d 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -624,7 +624,8 @@ void __cdecl InitialiseLara(GF_LEVEL_TYPE type) { lara->extra_anim = 0; lara->keep_ducked = FALSE; lara->look = TRUE; - lara->back_gun = ID_LARA; + lara->back_gun = 0; + lara->water_surface_dist = 100; lara->last_pos.x = item->pos.x; lara->last_pos.y = item->pos.y; lara->last_pos.z = item->pos.z; @@ -648,12 +649,14 @@ void __cdecl InitialiseLara(GF_LEVEL_TYPE type) { if (type == GFL_NORMAL && GF_LaraStartAnim) { lara->gun_status = LGS_HandBusy; lara->water_status = LWS_AboveWater; + lara->extra_anim = TRUE; item->animNumber = Objects[ID_LARA_EXTRA].animIndex; item->frameNumber = Anims[item->animNumber].frameBase; + item->currentAnimState = EXTRA_BREATH; item->goalAnimState = GF_LaraStartAnim; AnimateLara(item); Camera.type = CAM_Cinematic; - CineCurrentFrame = 0; + CineFrameIdx = 0; CinematicPos = item->pos; } else if CHK_ANY(RoomInfo[item->roomNumber].flags, ROOM_UNDERWATER) { lara->gun_status = LGS_Armless; diff --git a/game/laraswim.cpp b/game/laraswim.cpp index 443e516..0319d9a 100644 --- a/game/laraswim.cpp +++ b/game/laraswim.cpp @@ -34,10 +34,17 @@ #ifdef FEATURE_CHEAT static int OpenDoorsCheatCooldown = 0; // NOTE: this come from Tomb1Main (Door Cheat) -void DoorOpenNearest(ITEM_INFO *lara_item) { - int max_dist = SQR((1024 * 2) >> 8); +void DoorOpenNearest(int rangeClick) { + int max_dist = SQR((1024 * rangeClick) >> 8); for (int itemID = 0; itemID < LevelItemCount; itemID++) { ITEM_INFO *item = &Items[itemID]; + int dx = (item->pos.x - LaraItem->pos.x) >> 8; + int dy = (item->pos.y - LaraItem->pos.y) >> 8; + int dz = (item->pos.z - LaraItem->pos.z) >> 8; + int dist = SQR(dx) + SQR(dy) + SQR(dz); + if (dist > max_dist) { + continue; + } if ((item->objectID < ID_DOOR_TYPE1 || item->objectID > ID_DOOR_TYPE8) && item->objectID != ID_TRAPDOOR_TYPE1 @@ -45,13 +52,6 @@ void DoorOpenNearest(ITEM_INFO *lara_item) { && item->objectID != ID_TRAPDOOR_TYPE3) { continue; } - int dx = (item->pos.x - lara_item->pos.x) >> 8; - int dy = (item->pos.y - lara_item->pos.y) >> 8; - int dz = (item->pos.z - lara_item->pos.z) >> 8; - int dist = SQR(dx) + SQR(dy) + SQR(dz); - if (dist > max_dist) { - continue; - } if (!item->active) { AddActiveItem(itemID); item->flags |= IFL_CODEBITS; @@ -144,7 +144,7 @@ void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { OpenDoorsCheatCooldown--; } else if CHK_ANY(InputStatus, IN_DRAW) { OpenDoorsCheatCooldown = FRAMES_PER_SECOND; - DoorOpenNearest(LaraItem); + DoorOpenNearest(5); } } #endif // FEATURE_CHEAT From bbf73c236579060ba165a2075255acded8d2265e Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 22 Mar 2022 10:10:13 +0100 Subject: [PATCH 46/66] Fixed LaraBaddieCollision() --- game/collide.cpp | 69 ++++++++++++++++++++++++------------------------ 1 file changed, 34 insertions(+), 35 deletions(-) diff --git a/game/collide.cpp b/game/collide.cpp index fa1db57..de8fb67 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -256,7 +256,6 @@ __int16 __cdecl GetTiltType(FLOOR_INFO *floor, int x, int y, int z) { void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll) { DOOR_INFOS *doors; - DOOR_INFO *door; ITEM_INFO *item; OBJECT_INFO *obj; int x, y, z; @@ -267,48 +266,48 @@ void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll) { laraitem->hit_status = 0; Lara.hit_direction = -1; + if (laraitem->hitPoints <= 0) { + return; + } - // NOTE: added some nullptr check just in case something want wrong. - if (laraitem->hitPoints > 0) { - roomArray[0] = laraitem->roomNumber; - roomCount = 1; - doors = RoomInfo[roomArray[0]].doors; - if (doors) { - for (i = doors->wCount; i > 0; i--) { - door = doors[i].door; - if (door) { // NOTE: this check was not there in the original game - roomArray[roomCount++] = door->room; - } - } + roomArray[0] = laraitem->roomNumber; + roomCount = 1; + doors = RoomInfo[laraitem->roomNumber].doors; + if (doors) { + for (i = 0; i < doors->wCount; i++) { + roomArray[roomCount++] = doors->door[i].room; } - if (roomCount > 0) { - itemID = RoomInfo[roomArray[0]].itemNumber; - if (itemID != -1) { - for (i = roomCount; i > 0; i--) { - item = &Items[itemID]; - if (item && item->collidable && item->status != ITEM_INVISIBLE) { // NOTE: "item" was not there in the original game - obj = &Objects[item->objectID]; - if (obj && obj->collision) { // NOTE: "obj" was not there in the original game - x = laraitem->pos.x - item->pos.x; - y = laraitem->pos.y - item->pos.y; - z = laraitem->pos.z - item->pos.z; - if (x > -4096 && x < 4096 && z > -4096 && z < 4096 && y > -4096 && y < 4096) { - obj->collision(itemID, laraitem, coll); - } + } + + if (roomCount > 0) { + for (i = 0; i < roomCount; i++) { + itemID = RoomInfo[roomArray[i]].itemNumber; + while (itemID != -1) + { + item = &Items[itemID]; + if (item->collidable && item->status != ITEM_INVISIBLE) { + obj = &Objects[item->objectID]; + if (obj->collision) { + x = laraitem->pos.x - item->pos.x; + y = laraitem->pos.y - item->pos.y; + z = laraitem->pos.z - item->pos.z; + if (x > -4096 && x < 4096 + && y > -4096 && y < 4096 + && z > -4096 && z < 4096) { + obj->collision(itemID, laraitem, coll); } } - itemID = item->nextItem; } + itemID = item->nextItem; } } - if (Lara.spaz_effect_count != 0) { - EffectSpaz(laraitem, coll); // NOTE: coll is not used ! - } - if (Lara.hit_direction == -1) { - Lara.hit_frame = 0; - } - InventoryChosen = -1; } + + if (Lara.spaz_effect_count != 0) + EffectSpaz(laraitem, coll); // NOTE: coll is not used ! + if (Lara.hit_direction == -1) + Lara.hit_frame = 0; + InventoryChosen = -1; } void __cdecl EffectSpaz(ITEM_INFO *laraitem, COLL_INFO *coll) { From 6eea370a562e473a1b8b1e736ad91875ba02d6d0 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 22 Mar 2022 10:23:14 +0100 Subject: [PATCH 47/66] Add array size check In LaraBaddieCollision() --- game/collide.cpp | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/game/collide.cpp b/game/collide.cpp index de8fb67..93ac6e9 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -255,11 +255,12 @@ __int16 __cdecl GetTiltType(FLOOR_INFO *floor, int x, int y, int z) { } void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll) { +#define ROOM_ARRAY_COUNT 20 DOOR_INFOS *doors; ITEM_INFO *item; OBJECT_INFO *obj; int x, y, z; - __int16 roomArray[20]; + __int16 roomArray[ROOM_ARRAY_COUNT]; __int16 roomCount; __int16 itemID; __int16 i; @@ -275,6 +276,9 @@ void __cdecl LaraBaddieCollision(ITEM_INFO *laraitem, COLL_INFO *coll) { doors = RoomInfo[laraitem->roomNumber].doors; if (doors) { for (i = 0; i < doors->wCount; i++) { + if (i > (ROOM_ARRAY_COUNT - 1)) { // check if i > roomArray size, to avoid overflow ! + break; + } roomArray[roomCount++] = doors->door[i].room; } } From c6296d50b8a01b202a953a1b2e721da44d6147d6 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 24 Mar 2022 11:38:20 +0100 Subject: [PATCH 48/66] Fixed lara not playing some sound caused by AnimateLara() command pointer being advanced when it's not ! --- game/laramisc.cpp | 69 ++++++++++++++++++++++++----------------------- 1 file changed, 36 insertions(+), 33 deletions(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index aad6a3d..555f16f 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -364,46 +364,49 @@ void __cdecl AnimateLara(ITEM_INFO* item) { } item->animNumber = anim->jumpAnimNum; item->frameNumber = anim->jumpFrameNum; - anim = &Anims[item->animNumber]; + anim = &Anims[anim->jumpAnimNum]; item->currentAnimState = anim->currentAnimState; } - if (anim->numberCommands > 0) { - command = &AnimCommands[anim->commandIndex]; - for (__int16 i = anim->numberCommands; i > 0; i--) { - switch (*command++) { - case 1: - command += 3; - continue; - case 5: - if (item->frameNumber != command[0]) { - break; - } - waterSurfDist = Lara.water_surface_dist; - soundType = command[1] & 0xC000; // LAND or WATER - notLand = soundType != (__int16)0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); - notWater = soundType != (__int16)0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); - if (soundType != 0 && notLand && notWater) { - break; - } - PlaySoundEffect(command[1] & 0x3FFF, &item->pos, SFX_ALWAYS); + command = &AnimCommands[anim->commandIndex]; + for (__int16 i = anim->numberCommands; i > 0; i--) { + switch (*command++) { + case 1: + command += 3; + continue; + case 2: + command += 2; + break; + case 5: + if (item->frameNumber != command[0]) { break; - case 6: - if (item->frameNumber != command[0]) { - break; - } - waterSurfDist = Lara.water_surface_dist; - soundType = command[1] & 0xC000; // LAND or WATER - notLand = soundType != (__int16)0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); - notWater = soundType != (__int16)0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); - if (soundType != 0 && notLand && notWater) { - break; - } - EffectFunctions[command[1] & 0x3FFF](item); + } + waterSurfDist = Lara.water_surface_dist; + soundType = command[1] & 0xC000; // LAND or WATER + notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != (__int16)0x8000 || waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT; + if (soundType && notLand && notWater) { break; } - command += 2; + PlaySoundEffect(command[1] & 0x3FFF, &item->pos, SFX_ALWAYS); + break; + case 6: + if (item->frameNumber != command[0]) { + break; + } + waterSurfDist = Lara.water_surface_dist; + soundType = command[1] & 0xC000; // LAND or WATER + notLand = soundType != 0x4000 || (waterSurfDist < 0 && waterSurfDist != NO_HEIGHT); + notWater = soundType != (__int16)0x8000 || (waterSurfDist >= 0 || waterSurfDist == NO_HEIGHT); + if (soundType != 0 && notLand && notWater) { + break; + } + EffectFunctions[command[1] & 0x3FFF](item); + break; + default: + continue; } + command += 2; } if (item->gravity) { From a5579a17933e25ca831f74b9b7c3d0e930afd681 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 24 Mar 2022 11:51:41 +0100 Subject: [PATCH 49/66] Fixed a mistake about lara command --- game/laramisc.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/game/laramisc.cpp b/game/laramisc.cpp index 555f16f..952be23 100644 --- a/game/laramisc.cpp +++ b/game/laramisc.cpp @@ -375,7 +375,6 @@ void __cdecl AnimateLara(ITEM_INFO* item) { command += 3; continue; case 2: - command += 2; break; case 5: if (item->frameNumber != command[0]) { From 93e95c10dc342cc98985e105264693e39c5185b5 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 19 Apr 2022 08:48:20 +0200 Subject: [PATCH 50/66] Fixed M16 torso rotation. --- game/draw.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/game/draw.cpp b/game/draw.cpp index 67c8a76..1f5f135 100644 --- a/game/draw.cpp +++ b/game/draw.cpp @@ -782,9 +782,9 @@ void __cdecl DrawLara(ITEM_INFO *laraitem) { phd_TranslateRel(bones[25], bones[26], bones[27]); currentState = Items[Lara.weapon_item].currentAnimState; - if (Lara.weapon_item != -1 && Lara.gun_type == LGT_M16 && currentState == 0 && currentState == 2 && currentState == 4) { - rot1copy = (UINT16*)Lara.right_arm.frame_base + Lara.right_arm.frame_number * (Anims[Lara.right_arm.anim_number].interpolation >> 8) + 9; - phd_RotYXZsuperpack(&rot1copy, 7); + if (Lara.weapon_item != -1 && Lara.gun_type == LGT_M16 && (currentState == 0 || currentState == 2 || currentState == 4)) { + rot1 = (UINT16*)Lara.right_arm.frame_base + Lara.right_arm.frame_number * (Anims[Lara.right_arm.anim_number].interpolation >> 8) + 9; + phd_RotYXZsuperpack(&rot1, 7); } else { phd_RotYXZsuperpack(&rot1, 0); } From 676c7d44018f52c81ec963b47a7da88deebb97fc Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 21 Apr 2022 10:50:11 +0200 Subject: [PATCH 51/66] Decompiled GeneralControl() - Add the bridgelightfix in TR2Main.json to fix the dynamic light created by drawbridge when triggered. --- configs/TR2Main.json | 5 +++++ game/objects.cpp | 43 ++++++++++++++++++++++++++++++++++++++++++- game/objects.h | 2 +- modding/mod_utils.cpp | 9 +++++++++ modding/mod_utils.h | 1 + 5 files changed, 58 insertions(+), 2 deletions(-) diff --git a/configs/TR2Main.json b/configs/TR2Main.json index 3b15fd9..43e5fa0 100644 --- a/configs/TR2Main.json +++ b/configs/TR2Main.json @@ -31,6 +31,10 @@ " boots. It is used for alternative sound effects of Lara's steps. ", " The parameter can be true or false. Default value is false. ", " ", + " - 'bridgelightfix' is used to fix the drawbridge that create a ", + " dynamic light when triggered. (minisub is not affected) ", + " Default is true. ", + " ", " - 'semitransparent' is used for semitransparency parameters. ", " It can contain: 'animtex', 'objects', 'statics', 'rooms' ", " ", @@ -91,6 +95,7 @@ "default": { "comment": "Default settings for all levels", "watercolor": "80FFFF", + "bridgelightfix": true, "semitransparent": { "animtex": "auto", "objects": [{ diff --git a/game/objects.cpp b/game/objects.cpp index dd45582..0c91bbf 100644 --- a/game/objects.cpp +++ b/game/objects.cpp @@ -22,8 +22,15 @@ #include "global/precompiled.h" #include "game/objects.h" #include "game/control.h" +#include "game/draw.h" +#include "game/items.h" +#include "game/sphere.h" #include "global/vars.h" +#if defined(FEATURE_MOD_CONFIG) +#include "modding/mod_utils.h" +#endif // !FEATURE_MOD_CONFIG + void __cdecl ShutThatDoor(DOORPOS_DATA *door) { FLOOR_INFO* floor = door->floor; if (floor != NULL) { @@ -73,6 +80,40 @@ void __cdecl DoorControl(__int16 itemID) { AnimateItem(item); } +void __cdecl GeneralControl(__int16 itemID) { + ITEM_INFO *item; + PHD_VECTOR pos; + __int16 roomID; + + item = &Items[itemID]; + if (TriggerActive(item)) { + item->goalAnimState = 1; // NOTE: open + } else { + item->goalAnimState = 0; // NOTE: close + } + + AnimateItem(item); + + roomID = item->roomNumber; + GetFloor(item->pos.x, item->pos.y, item->pos.z, &roomID); + if (roomID != item->roomNumber) { + ItemNewRoom(item->roomNumber, roomID); + } + + if (item->status == ITEM_DISABLED) { + RemoveActiveItem(itemID); + item->flags |= IFL_INVISIBLE; + } +#if defined(FEATURE_MOD_CONFIG) + if (IsModBridgeLightFix() && item->objectID != ID_GENERAL) return; +#endif // !FEATURE_MOD_CONFIG + pos.x = 3000; + pos.y = 720; + pos.z = 0; + GetJointAbsPosition(item, &pos, 0); + AddDynamicLight(pos.x, pos.y, pos.z, 14, 11); +} + /* * Inject function */ @@ -114,6 +155,6 @@ void Inject_Objects() { // INJECT(0x00435BC0, BridgeTilt2Floor); // INJECT(0x00435BF0, BridgeTilt2Ceiling); // INJECT(0x00435C30, CopterControl); -// INJECT(0x00435D40, GeneralControl); + INJECT(0x00435D40, GeneralControl); // INJECT(0x00435E20, DetonatorControl); } diff --git a/game/objects.h b/game/objects.h index a7a0ff9..58e7317 100644 --- a/game/objects.h +++ b/game/objects.h @@ -66,7 +66,7 @@ void __cdecl DoorControl(__int16 itemID); // 0x00435570 // 0x00435BC0: BridgeTilt2Floor // 0x00435BF0: BridgeTilt2Ceiling // 0x00435C30: CopterControl -// 0x00435D40: GeneralControl +void __cdecl GeneralControl(__int16 itemID); // 0x00435D40 // 0x00435E20: DetonatorControl #endif // OBJECTS_H_INCLUDED diff --git a/modding/mod_utils.cpp b/modding/mod_utils.cpp index a90370e..ef57a30 100644 --- a/modding/mod_utils.cpp +++ b/modding/mod_utils.cpp @@ -44,6 +44,7 @@ typedef struct { typedef struct { bool isLoaded; bool isBarefoot; + bool isBridgeLightFix; char loadingPix[256]; DWORD waterColor; SEMITRANS_CONFIG semitrans; @@ -168,6 +169,10 @@ bool IsModBarefoot() { return ModConfig.isBarefoot; } +bool IsModBridgeLightFix() { + return ModConfig.isBridgeLightFix; +} + const char *GetModLoadingPix() { return *ModConfig.loadingPix ? ModConfig.loadingPix : NULL; } @@ -414,6 +419,10 @@ static bool ParseLevelConfiguration(json_value *root) { if( field ) { ModConfig.isBarefoot = field->u.boolean; } + field = GetJsonField(root, json_boolean, "bridgelightfix", NULL); + if( field ) { + ModConfig.isBridgeLightFix = field->u.boolean; + } ParseSemitransConfiguration(GetJsonField(root, json_object, "semitransparent", NULL)); ParseReflectConfiguration(GetJsonField(root, json_object, "reflective", NULL)); return true; diff --git a/modding/mod_utils.h b/modding/mod_utils.h index 920f37d..4ed717b 100644 --- a/modding/mod_utils.h +++ b/modding/mod_utils.h @@ -56,6 +56,7 @@ bool EnumeratePolys(__int16 *ptrObj, bool isRoomMesh, ENUM_POLYS_CB callback, PO #ifdef FEATURE_MOD_CONFIG bool IsModConfigLoaded(); bool IsModBarefoot(); +bool IsModBridgeLightFix(); const char *GetModLoadingPix(); DWORD GetModWaterColor(); bool IsModSemitransConfigLoaded(); From f47ec07bf9af5a8969ec22775ffa28b94e7a170a Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 21 Apr 2022 20:16:54 +0200 Subject: [PATCH 52/66] Bonus level experimental feature - Crash when trying to load the bonus level. --- configs/TR2Main.json | 12 ++++++++++++ game/gameflow.cpp | 7 ++----- modding/mod_utils.cpp | 18 ++++++++++++++++++ modding/mod_utils.h | 2 ++ specific/game.cpp | 37 +++++++++++++++++++++++++++++++++++-- 5 files changed, 69 insertions(+), 7 deletions(-) diff --git a/configs/TR2Main.json b/configs/TR2Main.json index 43e5fa0..680f89e 100644 --- a/configs/TR2Main.json +++ b/configs/TR2Main.json @@ -35,6 +35,16 @@ " dynamic light when triggered. (minisub is not affected) ", " Default is true. ", " ", + " - 'bonuslevel' is used to enable the bonus level when all secrets ", + " in the game, the count for each level is stored in the ", + " 'secretperlevel' you need to specify the level id in the ", + " 'bonuslevelid' ", + " ", + " - 'bonuslevelid' is used when 'bonuslevel' is true, ", + " when all the secrets is found (use gameflow secret command), ", + " this level will be unlocked. (there is only 23 level available ", + " and it start at: 0:title, 1:gym) ", + " ", " - 'semitransparent' is used for semitransparency parameters. ", " It can contain: 'animtex', 'objects', 'statics', 'rooms' ", " ", @@ -96,6 +106,8 @@ "comment": "Default settings for all levels", "watercolor": "80FFFF", "bridgelightfix": true, + "bonuslevel": true, + "bonuslevelid": 19, "semitransparent": { "animtex": "auto", "objects": [{ diff --git a/game/gameflow.cpp b/game/gameflow.cpp index 1f587d5..7107a03 100644 --- a/game/gameflow.cpp +++ b/game/gameflow.cpp @@ -179,10 +179,7 @@ BOOL __cdecl GF_DoFrontEndSequence() { int __cdecl GF_DoLevelSequence(DWORD levelID, GF_LEVEL_TYPE levelType) { for( DWORD i = levelID; i < GF_GameFlow.num_Levels; ++i ) { int direction = GF_InterpretSequence(GF_ScriptTable[i], levelType, 0); - - if( GF_GameFlow.singleLevel >= 0 || - (direction & ~0xFFu) != GF_LEVEL_COMPLETE ) - { + if( GF_GameFlow.singleLevel >= 0 || (direction & ~0xFFu) != GF_LEVEL_COMPLETE ) { return direction; } } @@ -294,7 +291,7 @@ int __cdecl GF_InterpretSequence(__int16 *seq, GF_LEVEL_TYPE levelType, int seqT break; case GFE_GAMECOMPLETE : - DisplayCredits(); + //DisplayCredits(); if( GameStats(CurrentLevel) ) { return GF_EXIT_TO_TITLE; } diff --git a/modding/mod_utils.cpp b/modding/mod_utils.cpp index ef57a30..e637eec 100644 --- a/modding/mod_utils.cpp +++ b/modding/mod_utils.cpp @@ -45,7 +45,9 @@ typedef struct { bool isLoaded; bool isBarefoot; bool isBridgeLightFix; + bool isBonusLevel; char loadingPix[256]; + DWORD bonusLevelID; DWORD waterColor; SEMITRANS_CONFIG semitrans; REFLECT_CONFIG reflect; @@ -173,6 +175,14 @@ bool IsModBridgeLightFix() { return ModConfig.isBridgeLightFix; } +bool IsModBonusLevel() { + return ModConfig.isBonusLevel; +} + +DWORD GetModBonusLevelID() { + return ModConfig.bonusLevelID; +} + const char *GetModLoadingPix() { return *ModConfig.loadingPix ? ModConfig.loadingPix : NULL; } @@ -419,6 +429,14 @@ static bool ParseLevelConfiguration(json_value *root) { if( field ) { ModConfig.isBarefoot = field->u.boolean; } + field = GetJsonField(root, json_boolean, "bonuslevel", NULL); + if( field ) { + ModConfig.isBonusLevel = field->u.boolean; + } + field = GetJsonField(root, json_integer, "bonuslevelid", NULL); + if( field ) { + ModConfig.bonusLevelID = field->u.integer; + } field = GetJsonField(root, json_boolean, "bridgelightfix", NULL); if( field ) { ModConfig.isBridgeLightFix = field->u.boolean; diff --git a/modding/mod_utils.h b/modding/mod_utils.h index 4ed717b..bd16e39 100644 --- a/modding/mod_utils.h +++ b/modding/mod_utils.h @@ -57,6 +57,8 @@ bool EnumeratePolys(__int16 *ptrObj, bool isRoomMesh, ENUM_POLYS_CB callback, PO bool IsModConfigLoaded(); bool IsModBarefoot(); bool IsModBridgeLightFix(); +bool IsModBonusLevel(); +DWORD GetModBonusLevelID(); const char *GetModLoadingPix(); DWORD GetModWaterColor(); bool IsModSemitransConfigLoaded(); diff --git a/specific/game.cpp b/specific/game.cpp index 1581c12..9d7d6b3 100644 --- a/specific/game.cpp +++ b/specific/game.cpp @@ -24,6 +24,7 @@ #include "game/camera.h" #include "game/control.h" #include "game/draw.h" +#include "game/gameflow.h" #include "game/inventory.h" #include "game/invtext.h" #include "game/savegame.h" @@ -46,6 +47,12 @@ extern DWORD StatsBackgroundMode; #endif // FEATURE_BACKGROUND_IMPROVED +#ifdef FEATURE_MOD_CONFIG +#include "modding/mod_utils.h" +extern int GF_GetNumSecrets(DWORD levelID); +GF_LEVEL_TYPE CurrentLevelType = GFL_NOLEVEL; +#endif // FEATURE_MOD_CONFIG + #ifdef FEATURE_INPUT_IMPROVED #include "modding/joy_output.h" #endif // FEATURE_INPUT_IMPROVED @@ -85,10 +92,10 @@ DWORD SavegameSlots = 16; __int16 __cdecl StartGame(int levelID, GF_LEVEL_TYPE levelType) { if( levelType == GFL_NORMAL || levelType == GFL_SAVED || levelType == GFL_DEMO ) CurrentLevel = levelID; - if( levelType != GFL_SAVED ) ModifyStartInfo(levelID); + CurrentLevelType = levelType; // NOTE: need it for the GameStats() IsTitleLoaded = FALSE; if( levelType != GFL_SAVED ) @@ -318,12 +325,38 @@ int __cdecl GameStats(int levelID) { RemoveJoystickHintText(false, true, false); #endif // FEATURE_HUD_IMPROVED + int totalLevels = (GF_GameFlow.num_Levels - GF_GameFlow.num_Demos) - 1; // NOTE: in the original game, there is slightly different bonusFlag activation. // Here removed bonuses initialization, and added the check that the level is final - if( CurrentLevel == GF_GameFlow.num_Levels-GF_GameFlow.num_Demos-1 ) { + if( CurrentLevel == totalLevels ) { SaveGame.bonusFlag = true; } +#ifdef FEATURE_MOD_CONFIG + if (!IsResetFlag && CurrentLevelType != GFL_STORY) { + if (IsModBonusLevel()) { + int bonusLevelID = GetModBonusLevelID(); + if (levelID < bonusLevelID) { + int numSecretTotal = 0, numSecretGame = 0; + for ( int i = 0; i < totalLevels; i++ ) { + BYTE flags = SaveGame.start[i].statistics.secrets; + // check for secret 1, 2 or 3 + numSecretTotal += CHK_ANY(flags, 0x1) + CHK_ANY(flags, 0x2) + CHK_ANY(flags, 0x4); + numSecretGame += GF_GetNumSecrets(i); + } + if (numSecretTotal >= numSecretGame) { + if (bonusLevelID != -1 && bonusLevelID <= totalLevels) { + SaveGame.start[bonusLevelID].available = 1; + SaveGame.currentLevel = bonusLevelID; + S_SaveGame(&SaveGame, sizeof(SAVEGAME_INFO), 0); + return 1; + } + } + } + } + } +#endif + #ifdef FEATURE_BACKGROUND_IMPROVED BGND2_ShowPicture(0, 0, 10, 2, FALSE); #endif // FEATURE_BACKGROUND_IMPROVED From f2aed5e1d322152e28e3043fef91ca24cac97f00 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 30 Apr 2022 16:53:50 +0200 Subject: [PATCH 53/66] Revert "Bonus level experimental feature" This reverts commit f47ec07bf9af5a8969ec22775ffa28b94e7a170a. --- configs/TR2Main.json | 12 ------------ game/gameflow.cpp | 7 +++++-- modding/mod_utils.cpp | 18 ------------------ modding/mod_utils.h | 2 -- specific/game.cpp | 37 ++----------------------------------- 5 files changed, 7 insertions(+), 69 deletions(-) diff --git a/configs/TR2Main.json b/configs/TR2Main.json index 680f89e..43e5fa0 100644 --- a/configs/TR2Main.json +++ b/configs/TR2Main.json @@ -35,16 +35,6 @@ " dynamic light when triggered. (minisub is not affected) ", " Default is true. ", " ", - " - 'bonuslevel' is used to enable the bonus level when all secrets ", - " in the game, the count for each level is stored in the ", - " 'secretperlevel' you need to specify the level id in the ", - " 'bonuslevelid' ", - " ", - " - 'bonuslevelid' is used when 'bonuslevel' is true, ", - " when all the secrets is found (use gameflow secret command), ", - " this level will be unlocked. (there is only 23 level available ", - " and it start at: 0:title, 1:gym) ", - " ", " - 'semitransparent' is used for semitransparency parameters. ", " It can contain: 'animtex', 'objects', 'statics', 'rooms' ", " ", @@ -106,8 +96,6 @@ "comment": "Default settings for all levels", "watercolor": "80FFFF", "bridgelightfix": true, - "bonuslevel": true, - "bonuslevelid": 19, "semitransparent": { "animtex": "auto", "objects": [{ diff --git a/game/gameflow.cpp b/game/gameflow.cpp index 7107a03..1f587d5 100644 --- a/game/gameflow.cpp +++ b/game/gameflow.cpp @@ -179,7 +179,10 @@ BOOL __cdecl GF_DoFrontEndSequence() { int __cdecl GF_DoLevelSequence(DWORD levelID, GF_LEVEL_TYPE levelType) { for( DWORD i = levelID; i < GF_GameFlow.num_Levels; ++i ) { int direction = GF_InterpretSequence(GF_ScriptTable[i], levelType, 0); - if( GF_GameFlow.singleLevel >= 0 || (direction & ~0xFFu) != GF_LEVEL_COMPLETE ) { + + if( GF_GameFlow.singleLevel >= 0 || + (direction & ~0xFFu) != GF_LEVEL_COMPLETE ) + { return direction; } } @@ -291,7 +294,7 @@ int __cdecl GF_InterpretSequence(__int16 *seq, GF_LEVEL_TYPE levelType, int seqT break; case GFE_GAMECOMPLETE : - //DisplayCredits(); + DisplayCredits(); if( GameStats(CurrentLevel) ) { return GF_EXIT_TO_TITLE; } diff --git a/modding/mod_utils.cpp b/modding/mod_utils.cpp index e637eec..ef57a30 100644 --- a/modding/mod_utils.cpp +++ b/modding/mod_utils.cpp @@ -45,9 +45,7 @@ typedef struct { bool isLoaded; bool isBarefoot; bool isBridgeLightFix; - bool isBonusLevel; char loadingPix[256]; - DWORD bonusLevelID; DWORD waterColor; SEMITRANS_CONFIG semitrans; REFLECT_CONFIG reflect; @@ -175,14 +173,6 @@ bool IsModBridgeLightFix() { return ModConfig.isBridgeLightFix; } -bool IsModBonusLevel() { - return ModConfig.isBonusLevel; -} - -DWORD GetModBonusLevelID() { - return ModConfig.bonusLevelID; -} - const char *GetModLoadingPix() { return *ModConfig.loadingPix ? ModConfig.loadingPix : NULL; } @@ -429,14 +419,6 @@ static bool ParseLevelConfiguration(json_value *root) { if( field ) { ModConfig.isBarefoot = field->u.boolean; } - field = GetJsonField(root, json_boolean, "bonuslevel", NULL); - if( field ) { - ModConfig.isBonusLevel = field->u.boolean; - } - field = GetJsonField(root, json_integer, "bonuslevelid", NULL); - if( field ) { - ModConfig.bonusLevelID = field->u.integer; - } field = GetJsonField(root, json_boolean, "bridgelightfix", NULL); if( field ) { ModConfig.isBridgeLightFix = field->u.boolean; diff --git a/modding/mod_utils.h b/modding/mod_utils.h index bd16e39..4ed717b 100644 --- a/modding/mod_utils.h +++ b/modding/mod_utils.h @@ -57,8 +57,6 @@ bool EnumeratePolys(__int16 *ptrObj, bool isRoomMesh, ENUM_POLYS_CB callback, PO bool IsModConfigLoaded(); bool IsModBarefoot(); bool IsModBridgeLightFix(); -bool IsModBonusLevel(); -DWORD GetModBonusLevelID(); const char *GetModLoadingPix(); DWORD GetModWaterColor(); bool IsModSemitransConfigLoaded(); diff --git a/specific/game.cpp b/specific/game.cpp index 9d7d6b3..1581c12 100644 --- a/specific/game.cpp +++ b/specific/game.cpp @@ -24,7 +24,6 @@ #include "game/camera.h" #include "game/control.h" #include "game/draw.h" -#include "game/gameflow.h" #include "game/inventory.h" #include "game/invtext.h" #include "game/savegame.h" @@ -47,12 +46,6 @@ extern DWORD StatsBackgroundMode; #endif // FEATURE_BACKGROUND_IMPROVED -#ifdef FEATURE_MOD_CONFIG -#include "modding/mod_utils.h" -extern int GF_GetNumSecrets(DWORD levelID); -GF_LEVEL_TYPE CurrentLevelType = GFL_NOLEVEL; -#endif // FEATURE_MOD_CONFIG - #ifdef FEATURE_INPUT_IMPROVED #include "modding/joy_output.h" #endif // FEATURE_INPUT_IMPROVED @@ -92,10 +85,10 @@ DWORD SavegameSlots = 16; __int16 __cdecl StartGame(int levelID, GF_LEVEL_TYPE levelType) { if( levelType == GFL_NORMAL || levelType == GFL_SAVED || levelType == GFL_DEMO ) CurrentLevel = levelID; + if( levelType != GFL_SAVED ) ModifyStartInfo(levelID); - CurrentLevelType = levelType; // NOTE: need it for the GameStats() IsTitleLoaded = FALSE; if( levelType != GFL_SAVED ) @@ -325,38 +318,12 @@ int __cdecl GameStats(int levelID) { RemoveJoystickHintText(false, true, false); #endif // FEATURE_HUD_IMPROVED - int totalLevels = (GF_GameFlow.num_Levels - GF_GameFlow.num_Demos) - 1; // NOTE: in the original game, there is slightly different bonusFlag activation. // Here removed bonuses initialization, and added the check that the level is final - if( CurrentLevel == totalLevels ) { + if( CurrentLevel == GF_GameFlow.num_Levels-GF_GameFlow.num_Demos-1 ) { SaveGame.bonusFlag = true; } -#ifdef FEATURE_MOD_CONFIG - if (!IsResetFlag && CurrentLevelType != GFL_STORY) { - if (IsModBonusLevel()) { - int bonusLevelID = GetModBonusLevelID(); - if (levelID < bonusLevelID) { - int numSecretTotal = 0, numSecretGame = 0; - for ( int i = 0; i < totalLevels; i++ ) { - BYTE flags = SaveGame.start[i].statistics.secrets; - // check for secret 1, 2 or 3 - numSecretTotal += CHK_ANY(flags, 0x1) + CHK_ANY(flags, 0x2) + CHK_ANY(flags, 0x4); - numSecretGame += GF_GetNumSecrets(i); - } - if (numSecretTotal >= numSecretGame) { - if (bonusLevelID != -1 && bonusLevelID <= totalLevels) { - SaveGame.start[bonusLevelID].available = 1; - SaveGame.currentLevel = bonusLevelID; - S_SaveGame(&SaveGame, sizeof(SAVEGAME_INFO), 0); - return 1; - } - } - } - } - } -#endif - #ifdef FEATURE_BACKGROUND_IMPROVED BGND2_ShowPicture(0, 0, 10, 2, FALSE); #endif // FEATURE_BACKGROUND_IMPROVED From c4bdc7c83ff768438141b3d29f2abdc073492799 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 1 May 2022 11:23:53 +0200 Subject: [PATCH 54/66] Fixed a crash - Decompiled GetJointAbsPosition() and BaddieBiteEffect(). - Changed COLL_INFO flags. - Fixed lara picking item when underwater, it crashed the game. - Updated TR2_progress.txt --- TR2_progress.txt | 12 ++++----- game/collide.cpp | 10 +++---- game/laraswim.cpp | 25 ++++++++++-------- game/sphere.cpp | 67 +++++++++++++++++++++++++++++++++++++++++++++-- game/sphere.h | 5 ++-- global/types.h | 7 ++++- global/vars.h | 10 +++---- 7 files changed, 103 insertions(+), 33 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 7b0522e..e5480a7 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -778,10 +778,10 @@ x function is unused / included in another function 0x00434EB0: * SmashWindow 0x00434F80: WindowControl 0x00435020: SmashIceControl -0x00435100: ShutThatDoor -0x00435150: OpenThatDoor +0x00435100: + ShutThatDoor +0x00435150: + OpenThatDoor 0x00435190: InitialiseDoor -0x00435570: DoorControl +0x00435570: + DoorControl 0x00435640: OnDrawBridge 0x00435700: DrawBridgeFloor 0x00435740: DrawBridgeCeiling @@ -799,7 +799,7 @@ x function is unused / included in another function 0x00435BC0: BridgeTilt2Floor 0x00435BF0: BridgeTilt2Ceiling 0x00435C30: CopterControl -0x00435D40: GeneralControl +0x00435D40: + GeneralControl 0x00435E20: DetonatorControl game/people.cpp @@ -896,8 +896,8 @@ x function is unused / included in another function game/sphere.cpp 0x0043FA60: * TestCollision 0x0043FB90: GetSpheres -0x0043FE70: * GetJointAbsPosition -0x00440010: * BaddieBiteEffect +0x0043FE70: + GetJointAbsPosition +0x00440010: + BaddieBiteEffect game/spider.cpp 0x00440070: SpiderLeap diff --git a/game/collide.cpp b/game/collide.cpp index 93ac6e9..53b7a5e 100644 --- a/game/collide.cpp +++ b/game/collide.cpp @@ -329,8 +329,8 @@ void __cdecl CreatureCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *c ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { - if (CHK_ANY(coll->flags, 0x8) && Lara.water_status != LWS_Underwater) { // NOTE: original checked "(Lara.water_status == 0) != 2" but it's always true ! - ItemPushLara(item, laraitem, coll, CHK_ANY(coll->flags, 0x10), FALSE); + if (coll->enableBaddiePush && Lara.water_status != LWS_Underwater) { // NOTE: original checked "(Lara.water_status == 0) != 2" but it's always true ! + ItemPushLara(item, laraitem, coll, coll->enableSpaz, FALSE); } } } @@ -340,7 +340,7 @@ void __cdecl ObjectCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *col ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { - if CHK_ANY(coll->flags, 0x8) { + if (coll->enableBaddiePush) { ItemPushLara(item, laraitem, coll, FALSE, TRUE); } } @@ -351,11 +351,11 @@ void __cdecl DoorCollision(__int16 itemID, ITEM_INFO *laraitem, COLL_INFO *coll) ITEM_INFO *item = &Items[itemID]; if (TestBoundsCollide(item, laraitem, coll->radius)) { if (TestCollision(item, laraitem)) { - if CHK_ANY(coll->flags, 0x8) { + if (coll->enableBaddiePush) { if (item->currentAnimState == item->goalAnimState) { ItemPushLara(item, laraitem, coll, FALSE, TRUE); } else { - ItemPushLara(item, laraitem, coll, CHK_ANY(coll->flags, 0x10), TRUE); + ItemPushLara(item, laraitem, coll, coll->enableSpaz, TRUE); } } } diff --git a/game/laraswim.cpp b/game/laraswim.cpp index 0319d9a..b6e3eae 100644 --- a/game/laraswim.cpp +++ b/game/laraswim.cpp @@ -67,7 +67,7 @@ void DoorOpenNearest(int rangeClick) { #endif void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { - int s, s2, c; + int s, c; coll->badPos = -NO_HEIGHT; coll->badNeg = -400; @@ -77,8 +77,11 @@ void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { coll->old.z = item->pos.z; coll->radius = 300; coll->trigger = 0; - coll->flags &= ~0x17; - coll->flags |= 0x18; + coll->slopesAreWalls = 0; + coll->slopesArePits = 0; + coll->lavaIsPit = 0; + coll->enableSpaz = 0; + coll->enableBaddiePush = 1; if (CHK_ANY(InputStatus, IN_LOOK) && Lara.look) { LookLeftRight(); @@ -88,9 +91,9 @@ void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { Lara.look = TRUE; if (Lara.extra_anim) { - ExtraFunctions[item->currentAnimState](item); + ExtraFunctions[item->currentAnimState](item, coll); } else { - LaraControlFunctions[item->currentAnimState](item); + LaraControlFunctions[item->currentAnimState](item, coll); } if (item->pos.rotZ < -364 || item->pos.rotZ > 364) { @@ -122,17 +125,17 @@ void __cdecl LaraUnderWater(ITEM_INFO *item, COLL_INFO *coll) { } AnimateLara(item); - s = (item->fallSpeed * phd_sin(item->pos.rotY)) >> 16; - s2 = (item->fallSpeed * phd_sin(item->pos.rotX)) >> 16; c = (item->fallSpeed * phd_cos(item->pos.rotY)) >> 16; + s = (item->fallSpeed * phd_sin(item->pos.rotY)) >> 16; + item->pos.y -= (item->fallSpeed * phd_sin(item->pos.rotX)) >> 16; item->pos.x += (phd_cos(item->pos.rotX) * s) >> W2V_SHIFT; - item->pos.y -= s2; item->pos.z += (phd_cos(item->pos.rotX) * c) >> W2V_SHIFT; + if (Lara.water_status != LWS_Cheat && Lara.extra_anim == 0) { + LaraBaddieCollision(item, coll); + } + if (Lara.extra_anim == 0) { - if (Lara.water_status != LWS_Cheat) { - LaraBaddieCollision(item, coll); - } LaraCollisionFunctions[item->currentAnimState](item, coll); } diff --git a/game/sphere.cpp b/game/sphere.cpp index d5b0b4a..5fb0419 100644 --- a/game/sphere.cpp +++ b/game/sphere.cpp @@ -21,9 +21,72 @@ #include "global/precompiled.h" #include "game/sphere.h" +#include "3dsystem/3d_gen.h" +#include "game/draw.h" +#include "game/effects.h" #include "global/vars.h" +void __cdecl GetJointAbsPosition(ITEM_INFO *item, PHD_VECTOR *pos, int joint) { + OBJECT_INFO *obj; + int *bones, flags; + UINT16 *rotation; + __int16 *frame, *rot; + + obj = &Objects[item->objectID]; + bones = &AnimBones[obj->boneIndex]; + frame = GetBestFrame(item); + rot = (__int16*)item->data; + + phd_PushUnitMatrix(); + PhdMatrixPtr->_03 = 0; + PhdMatrixPtr->_13 = 0; + PhdMatrixPtr->_23 = 0; + phd_RotYXZ(item->pos.rotY, item->pos.rotX, item->pos.rotZ); + phd_TranslateRel(frame[6], frame[7], frame[8]); + rotation = (UINT16*)frame + 9; + phd_RotYXZsuperpack(&rotation, 0); + + for (int i = 0; i < joint; i++, bones += 4) { + flags = bones[0]; + if (flags & 1) { + phd_PopMatrix(); + } + if (flags & 2) { + phd_PushMatrix(); + } + + phd_TranslateRel(bones[1], bones[2], bones[3]); + phd_RotYXZsuperpack(&rotation, 0); + + if (flags & 0x1C) { + if (flags & 8) { + phd_RotY(*(rot++)); + } + if (flags & 4) { + phd_RotX(*(rot++)); + } + if (flags & 0x10) { + phd_RotZ(*(rot++)); + } + } + } + + phd_TranslateRel(pos->x, pos->y, pos->z); + pos->x = (PhdMatrixPtr->_03 >> W2V_SHIFT) + item->pos.x; + pos->y = (PhdMatrixPtr->_13 >> W2V_SHIFT) + item->pos.y; + pos->z = (PhdMatrixPtr->_23 >> W2V_SHIFT) + item->pos.z; + phd_PopMatrix(); +} + +void __cdecl BaddieBiteEffect(ITEM_INFO *item, BITE_INFO *bite) { + PHD_VECTOR pos; + pos.x = bite->x; + pos.y = bite->y; + pos.z = bite->z; + GetJointAbsPosition(item, &pos, bite->meshIndex); + DoBloodSplat(pos.x, pos.y, pos.z, item->speed, item->pos.rotY, item->roomNumber); +} /* * Inject function @@ -31,6 +94,6 @@ void Inject_Sphere() { // INJECT(0x0043FA60, TestCollision); // INJECT(0x0043FB90, GetSpheres); -// INJECT(0x0043FE70, GetJointAbsPosition); -// INJECT(0x00440010, BaddieBiteEffect); + INJECT(0x0043FE70, GetJointAbsPosition); + INJECT(0x00440010, BaddieBiteEffect); } diff --git a/game/sphere.h b/game/sphere.h index 975c102..9ff7a46 100644 --- a/game/sphere.h +++ b/game/sphere.h @@ -29,8 +29,7 @@ */ #define TestCollision ((BOOL(__cdecl*)(ITEM_INFO*, ITEM_INFO*)) 0x0043FA60) // 0x0043FB90: GetSpheres - -#define GetJointAbsPosition ((void(__cdecl*)(ITEM_INFO*, PHD_VECTOR*, int)) 0x0043FE70) -#define BaddieBiteEffect ((void(__cdecl*)(ITEM_INFO*,BITE_INFO*)) 0x00440010) +void __cdecl GetJointAbsPosition(ITEM_INFO *item, PHD_VECTOR *pos, int joint); // 0x0043FE70 +void __cdecl BaddieBiteEffect(ITEM_INFO *item, BITE_INFO *bite); // 0x00440010 #endif // SPHERE_H_INCLUDED diff --git a/global/types.h b/global/types.h index ab64f15..193e27e 100644 --- a/global/types.h +++ b/global/types.h @@ -1783,7 +1783,12 @@ typedef struct CollInfo_t { char zTilt; char hitByBaddie; char hitStatic; - UINT16 flags; + UINT16 slopesAreWalls : 2; + UINT16 slopesArePits : 1; + UINT16 lavaIsPit : 1; + UINT16 enableBaddiePush : 1; + UINT16 enableSpaz : 1; + UINT16 hitCeiling : 1; } COLL_INFO; typedef struct ObjectInfo_t { diff --git a/global/vars.h b/global/vars.h index 1fb1db1..d8f4cf1 100644 --- a/global/vars.h +++ b/global/vars.h @@ -57,11 +57,11 @@ #define ins_objectG4 (*(__int16*(__cdecl **)(__int16*,int,SORTTYPE)) 0x004BCAF8) #define ins_objectG3 (*(__int16*(__cdecl **)(__int16*,int,SORTTYPE)) 0x004BCB40) -#define SfxFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) -#define EffectFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) -#define ExtraFunctions (*(void(__cdecl *(*)[11])(ITEM_INFO*)) 0x00465DF0) -#define LaraControlFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*)) 0x00465CD0) -#define LaraCollisionFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*,COLL_INFO*)) 0x00465E20) +#define SfxFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define EffectFunctions (*(void(__cdecl *(*)[32])(ITEM_INFO*)) 0x004641F8) +#define ExtraFunctions (*(void(__cdecl *(*)[11])(ITEM_INFO*,COLL_INFO*)) 0x00465DF0) +#define LaraControlFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*,COLL_INFO*)) 0x00465CD0) +#define LaraCollisionFunctions (*(void(__cdecl *(*)[71])(ITEM_INFO*,COLL_INFO*)) 0x00465E20) // Initialized variables #define PerspectiveDistance VAR_I_(0x00464060, DWORD, 0x3000000) From a2243d879fdbb08be98512b83a3705455d2d1f87 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Tue, 3 May 2022 14:15:54 +0200 Subject: [PATCH 55/66] Started decompiling setup.cpp --- TR2_progress.txt | 12 ++-- game/lot.h | 3 +- game/objects.h | 70 +++++++++--------- game/setup.cpp | 175 +++++++++++++++++++++++++++++++++++++++++++-- game/setup.h | 13 ++-- game/traps.h | 37 ++++------ specific/game.cpp | 2 +- specific/smain.cpp | 2 +- 8 files changed, 230 insertions(+), 84 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index e5480a7..6201c01 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -691,14 +691,14 @@ x function is unused / included in another function game/laramisc.cpp 0x00430380: + LaraControl -0x00430A10: * AnimateLara +0x00430A10: + AnimateLara 0x00430D10: + UseItem 0x00430ED0: + LaraCheatGetStuff 0x00430F90: + ControlLaraExtra 0x00430FB0: + InitialiseLaraLoad -0x00430FE0: * InitialiseLara +0x00430FE0: + InitialiseLara 0x004312A0: + InitialiseLaraInventory -0x00431610: * LaraInitialiseMeshes +0x00431610: + LaraInitialiseMeshes game/larasurf.cpp 0x00431710: * LaraSurface @@ -847,14 +847,14 @@ x function is unused / included in another function 0x0043A2F0: + ReadSG game/setup.cpp -0x0043A330: * InitialiseLevel -0x0043A490: InitialiseGameFlags +0x0043A330: + InitialiseLevel +0x0043A490: * InitialiseGameFlags 0x0043A500: + InitialiseLevelFlags 0x0043A530: + BaddyObjects 0x0043B570: * TrapObjects 0x0043BB70: * ObjectObjects 0x0043C7C0: + InitialiseObjects -0x0043C830: GetCarriedItems +0x0043C830: * GetCarriedItems game/shark.cpp 0x0043C900: * JellyControl diff --git a/game/lot.h b/game/lot.h index 01f17d9..9ac03bb 100644 --- a/game/lot.h +++ b/game/lot.h @@ -27,8 +27,7 @@ /* * Function list */ -// 0x00432B10: InitialiseLOTarray - +#define InitialiseLOTarray ((void(__cdecl*)(void)) 0x00432B10) #define DisableBaddieAI ((void(__cdecl*)(__int16)) 0x00432B70) #define EnableBaddieAI ((int(__cdecl*)(__int16, BOOL)) 0x00432BC0) diff --git a/game/objects.h b/game/objects.h index 58e7317..e1981cc 100644 --- a/game/objects.h +++ b/game/objects.h @@ -27,46 +27,44 @@ /* * Function list */ -// 0x004342C0: EarthQuake -// 0x004343A0: ControlCutShotgun -// 0x004343E0: InitialiseFinalLevel -// 0x004344B0: FinalLevelCounter -// 0x004346C0: MiniCopterControl -// 0x004347A0: InitialiseDyingMonk -// 0x00434820: DyingMonk -// 0x004348B0: ControlGongBonger -// 0x00434970: DeathSlideCollision -// 0x00434A30: ControlDeathSlide -// 0x00434CC0: BigBowlControl -// 0x00434DB0: BellControl -// 0x00434E30: InitialiseWindow - +#define EarthQuake ((void(__cdecl*)(__int16)) 0x004342C0) +#define ControlCutShotgun ((void(__cdecl*)(__int16)) 0x004343A0) +#define InitialiseFinalLevel ((void(__cdecl*)(__int16)) 0x004343E0) +#define FinalLevelCounter ((void(__cdecl*)(__int16)) 0x004344B0) +#define MiniCopterControl ((void(__cdecl*)(__int16)) 0x004346C0) +#define InitialiseDyingMonk ((void(__cdecl*)(__int16)) 0x004347A0) +#define DyingMonk ((void(__cdecl*)(__int16)) 0x00434820) +#define ControlGongBonger ((void(__cdecl*)(__int16)) 0x004348B0) +#define DeathSlideCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00434970) +#define ControlDeathSlide ((void(__cdecl*)(__int16)) 0x00434A30) +#define BigBowlControl ((void(__cdecl*)(__int16)) 0x00434CC0) +#define BellControl ((void(__cdecl*)(__int16)) 0x00434DB0) +#define InitialiseWindow ((void(__cdecl*)(__int16)) 0x00434E30) #define SmashWindow ((void(__cdecl*)(__int16)) 0x00434EB0) - -// 0x00434F80: WindowControl -// 0x00435020: SmashIceControl +#define WindowControl ((void(__cdecl*)(__int16)) 0x00434F80) +#define SmashIceControl ((void(__cdecl*)(__int16)) 0x00435020) void __cdecl ShutThatDoor(DOORPOS_DATA* door); // 0x00435100 void __cdecl OpenThatDoor(DOORPOS_DATA* door); // 0x00435150 -#define InitialiseDoor ((void(__cdecl*)(__int16 itemID)) 0x00435190) +#define InitialiseDoor ((void(__cdecl*)(__int16)) 0x00435190) void __cdecl DoorControl(__int16 itemID); // 0x00435570 -// 0x00435640: OnDrawBridge -// 0x00435700: DrawBridgeFloor -// 0x00435740: DrawBridgeCeiling -// 0x00435780: DrawBridgeCollision -// 0x004357B0: InitialiseLift -// 0x004357F0: LiftControl -// 0x004358D0: LiftFloorCeiling -// 0x00435A50: LiftFloor -// 0x00435A90: LiftCeiling -// 0x00435AD0: BridgeFlatFloor -// 0x00435AF0: BridgeFlatCeiling -// 0x00435B10: GetOffset -// 0x00435B50: BridgeTilt1Floor -// 0x00435B80: BridgeTilt1Ceiling -// 0x00435BC0: BridgeTilt2Floor -// 0x00435BF0: BridgeTilt2Ceiling -// 0x00435C30: CopterControl +#define OnDrawBridge ((BOOL(__cdecl*)(ITEM_INFO*,int,int)) 0x00435640) +#define DrawBridgeFloor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435700) +#define DrawBridgeCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435740) +#define DrawBridgeCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00435780) +#define InitialiseLift ((void(__cdecl*)(__int16)) 0x004357B0) +#define LiftControl ((void(__cdecl*)(__int16)) 0x004357F0) +#define LiftFloorCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,int*,int*)) 0x004358D0) +#define LiftFloor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435A50) +#define LiftCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435A90) +#define BridgeFlatFloor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435AD0) +#define BridgeFlatCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435AF0) +#define GetOffset ((int(__cdecl*)(ITEM_INFO*,int,int)) 0x00435B10) +#define BridgeTilt1Floor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435B50) +#define BridgeTilt1Ceiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435B80) +#define BridgeTilt2Floor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435BC0) +#define BridgeTilt2Ceiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00435BF0) +#define CopterControl ((void(__cdecl*)(__int16)) 0x00435C30) void __cdecl GeneralControl(__int16 itemID); // 0x00435D40 -// 0x00435E20: DetonatorControl +#define DetonatorControl ((void(__cdecl*)(__int16)) 0x00435E20) #endif // OBJECTS_H_INCLUDED diff --git a/game/setup.cpp b/game/setup.cpp index 7ee1236..a665430 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -23,6 +23,7 @@ #include "game/setup.h" #include "game/bear.h" #include "game/bird.h" +#include "game/boat.h" #include "game/collide.h" #include "game/diver.h" #include "game/dog.h" @@ -30,16 +31,30 @@ #include "game/draw.h" #include "game/eel.h" #include "game/enemies.h" +#include "game/gameflow.h" #include "game/hair.h" +#include "game/health.h" +#include "game/items.h" +#include "game/invfunc.h" #include "game/laramisc.h" +#include "game/lot.h" #include "game/moveblock.h" +#include "game/objects.h" #include "game/people.h" #include "game/rat.h" +#include "game/savegame.h" #include "game/shark.h" #include "game/skidoo.h" #include "game/spider.h" +#include "game/sound.h" +#include "game/traps.h" +#include "game/text.h" #include "game/wolf.h" #include "game/yeti.h" +#include "specific/file.h" +#include "specific/init.h" +#include "specific/output.h" +#include "specific/sndpc.h" #include "specific/winmain.h" #include "global/vars.h" @@ -47,6 +62,82 @@ extern bool IsGold(); #endif +BOOL __cdecl InitialiseLevel(int levelID, GF_LEVEL_TYPE levelType) { + BOOL isLoaded = FALSE; + + if (levelType != GFL_TITLE && levelType != GFL_CUTSCENE) { + CurrentLevel = levelID; + } + IsDemoLevelType = levelType == GFL_DEMO; + Lara.item_number = -1; + IsTitleLoaded = FALSE; + if (levelType != GFL_TITLE) { + if (levelType == GFL_SAVED || levelType != GFL_CUTSCENE) { + isLoaded = S_LoadLevelFile(GF_LevelFilesStringTable[levelID], levelID, levelType); + } else { + isLoaded = S_LoadLevelFile(GF_CutsFilesStringTable[levelID], levelID, GFL_CUTSCENE); + } + } else { + isLoaded = S_LoadLevelFile(GF_TitleFilesStringTable[0], levelID, GFL_TITLE); + } + + if (isLoaded) { + if (Lara.item_number != -1) { + InitialiseLara(levelType); + } + if (levelType == GFL_NORMAL || levelType == GFL_SAVED || levelType == GFL_DEMO) { + GetCarriedItems(); + } + Effects = (FX_INFO*)game_malloc(3600, GBUF_EffectsArray); + InitialiseFXArray(); + InitialiseLOTarray(); + InitColours(); + T_InitPrint(); + InitialisePickUpDisplay(); + S_InitialiseScreen(levelType); + HealthBarTimer = 100; + SOUND_Stop(); + + if (levelType == GFL_SAVED) { + ExtractSaveGameInfo(); + } else if (levelType == GFL_NORMAL) { + GF_ModifyInventory(CurrentLevel, FALSE); + } + + if (Objects[ID_FINAL_LEVEL_COUNTER].loaded) { + InitialiseFinalLevel(); + } + + if (levelType == GFL_NORMAL || levelType == GFL_SAVED || levelType == GFL_DEMO) { + if (TrackIDs[0] != 0) { + S_CDPlay(TrackIDs[0], TRUE); + } + } + + IsAssaultTimerActive = FALSE; + IsAssaultTimerDisplay = FALSE; + Camera.underwater = FALSE; + isLoaded = TRUE; + } + + return isLoaded; +} + +void __cdecl InitialiseGameFlags() { + FlipStatus = 0; + ZeroMemory(FlipMaps, sizeof(FlipMaps)); + ZeroMemory(CD_Flags, sizeof(CD_Flags)); + for (int i = 0; i < ID_NUMBER_OBJECTS; i++) { + Objects[i].loaded = FALSE; + } + SunsetTimer = 0; + AmmoTextInfo = NULL; + IsLevelComplete = FALSE; + FlipEffect = -1; + MinesDetonated = FALSE; + IsMonkAngry = FALSE; +} + void __cdecl InitialiseLevelFlags() { memset(&SaveGame.statistics, 0, sizeof(STATISTICS_INFO)); } @@ -701,20 +792,90 @@ void __cdecl BaddyObjects() { } } +void __cdecl TrapObjects() { + OBJECT_INFO* obj; + obj = &Objects[ID_GONDOLA]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = GondolaControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_CEILING_SPIKES]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = ControlCeilingSpikes; + obj->save_position = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_COPTER]; + if (obj->loaded) { + obj->control = CopterControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_MINI_COPTER]; + if (obj->loaded) { + obj->control = MiniCopterControl; + obj->save_flags = TRUE; + obj->save_position = TRUE; + } + obj = &Objects[ID_HOOK]; + if (obj->loaded) { + obj->collision = CreatureCollision; + obj->control = HookControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_GENERAL]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = GeneralControl; + obj->water_creature = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_DYING_MONK]; + if (obj->loaded) { + obj->initialise = InitialiseDyingMonk; + obj->collision = ObjectCollision; + obj->control = DyingMonk; + obj->save_flags = TRUE; + } + obj = &Objects[ID_MINE]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = MineControl; + obj->save_flags = TRUE; + } + obj = &Objects[ID_DEATH_SLIDE]; + if (obj->loaded) { + obj->initialise = InitialiseRollingBall; + obj->collision = DeathSlideCollision; + obj->control = ControlDeathSlide; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj->save_position = TRUE; + } + obj = &Objects[ID_PROPELLER2]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } +} + /* * Inject function */ void Inject_Setup() { -// INJECT(0x0043A330, InitialiseLevel); -// INJECT(0x0043A490, InitialiseGameFlags); - + INJECT(0x0043A330, InitialiseLevel); + INJECT(0x0043A490, InitialiseGameFlags); INJECT(0x0043A500, InitialiseLevelFlags); INJECT(0x0043A530, BaddyObjects); - -// INJECT(0x0043B570, TrapObjects); + INJECT(0x0043B570, TrapObjects); // INJECT(0x0043BB70, ObjectObjects); - INJECT(0x0043C7C0, InitialiseObjects); - // INJECT(0x0043C830, GetCarriedItems); } diff --git a/game/setup.h b/game/setup.h index 6831604..657c47a 100644 --- a/game/setup.h +++ b/game/setup.h @@ -27,18 +27,13 @@ /* * Function list */ -#define InitialiseLevel ((BOOL(__cdecl*)(int,int)) 0x0043A330) - -// 0x0043A490: InitialiseGameFlags - +BOOL __cdecl InitialiseLevel(int levelID, GF_LEVEL_TYPE levelType); // 0x0043A330 +void __cdecl InitialiseGameFlags(); // 0x0043A490 void __cdecl InitialiseLevelFlags(); // 0x0043A500 void __cdecl BaddyObjects(); // 0x0043A530 - -#define TrapObjects ((void(__cdecl*)(void)) 0x0043B570) +void __cdecl TrapObjects(); // 0x0043B570 #define ObjectObjects ((void(__cdecl*)(void)) 0x0043BB70) - void __cdecl InitialiseObjects(); // 0x0043C7C0 - -// 0x0043C830: GetCarriedItems +#define GetCarriedItems ((void(__cdecl*)(void)) 0x0043C830) #endif // SETUP_H_INCLUDED diff --git a/game/traps.h b/game/traps.h index ce29eba..5308ed9 100644 --- a/game/traps.h +++ b/game/traps.h @@ -32,32 +32,26 @@ void __cdecl MineControl(__int16 mineID); // 0x00440FC0 void __cdecl ControlSpikeWall(__int16 itemID); // 0x004411C0 void __cdecl ControlCeilingSpikes(__int16 itemID); // 0x00441300 void __cdecl HookControl(__int16 itemID); // 0x00441420 - -// 0x004414B0: PropellerControl - +#define PropellerControl ((void(__cdecl*)(__int16)) 0x004414B0) void __cdecl SpinningBlade(__int16 itemID); // 0x00441640 void __cdecl IcicleControl(__int16 itemID); // 0x004417C0 void __cdecl InitialiseBlade(__int16 itemID); // 0x004418C0 void __cdecl BladeControl(__int16 itemID); // 0x00441900 void __cdecl InitialiseKillerStatue(__int16 itemID); // 0x004419A0 void __cdecl KillerStatueControl(__int16 itemID); // 0x004419F0 - -// 0x00441B00: SpringBoardControl -// 0x00441BE0: InitialiseRollingBall -// 0x00441C20: RollingBallControl -// 0x00441F70: RollingBallCollision -// 0x004421C0: SpikeCollision -// 0x00442320: TrapDoorControl -// 0x00442370: TrapDoorFloor -// 0x004423B0: TrapDoorCeiling -// 0x004423F0: OnTrapDoor - +#define SpringBoardControl ((void(__cdecl*)(__int16)) 0x00441B00) +#define InitialiseRollingBall ((void(__cdecl*)(__int16)) 0x00441BE0) +#define RollingBallControl ((void(__cdecl*)(__int16)) 0x00441C20) +#define RollingBallCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00441F70) +#define SpikeCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x004421C0) +#define TrapDoorControl ((void(__cdecl*)(__int16)) 0x00442320) +#define TrapDoorFloor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00442370) +#define TrapDoorCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x004423B0) +#define OnTrapDoor ((int(__cdecl*)(ITEM_INFO*,int,int)) 0x004423F0) void __cdecl Pendulum(__int16 itemID); // 0x004424A0 - -// 0x004425B0: FallingBlock -// 0x004426C0: FallingBlockFloor -// 0x00442700: FallingBlockCeiling - +#define FallingBlock ((void(__cdecl*)(__int16)) 0x004425B0) +#define FallingBlockFloor ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x004426C0) +#define FallingBlockCeiling ((void(__cdecl*)(ITEM_INFO*,int,int,int,__int16*)) 0x00442700) void __cdecl TeethTrap(__int16 itemID); // 0x00442750 void __cdecl FallingCeiling(__int16 itemID); // 0x00442810 void __cdecl DartEmitterControl(__int16 itemID); // 0x004428F0 @@ -67,8 +61,7 @@ void __cdecl FlameEmitterControl(__int16 item_id); // 0x00442BE0 void __cdecl FlameControl(__int16 fx_id); // 0x00442C70 void __cdecl LaraBurn(); // 0x00442DE0 void __cdecl LavaBurn(ITEM_INFO *item); // 0x00442E30 - -// 0x00442F20: LavaSpray -// 0x00442FF0: ControlLavaBlob +#define LavaSpray ((void(__cdecl*)(__int16)) 0x00442F20) +#define ControlLavaBlob ((void(__cdecl*)(__int16)) 0x00442FF0) #endif // TRAPS_H_INCLUDED diff --git a/specific/game.cpp b/specific/game.cpp index 1581c12..b751a41 100644 --- a/specific/game.cpp +++ b/specific/game.cpp @@ -402,7 +402,7 @@ void __cdecl DisplayCredits() { S_UnloadLevelFile(); TempVideoAdjust(HiRes, 1.0); // NOTE: this line was not in the original code - if( !InitialiseLevel(0, 0) ) // init title level + if( !InitialiseLevel(0, GFL_TITLE) ) // init title level return; memcpy(palette, GamePalette8, sizeof(GamePalette8)); diff --git a/specific/smain.cpp b/specific/smain.cpp index aa4cb85..7b36fa1 100644 --- a/specific/smain.cpp +++ b/specific/smain.cpp @@ -288,7 +288,7 @@ __int16 __cdecl TitleSequence() { NoInputCounter = 0; if( !IsTitleLoaded ) { - if( !InitialiseLevel(0, 0) ) + if( !InitialiseLevel(0, GFL_TITLE) ) return GF_EXIT_GAME; IsTitleLoaded = TRUE; } From c9dce7aeda1d31b92143007b00d4a42369654025 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 21 May 2022 11:00:07 +0200 Subject: [PATCH 56/66] Finished TrapObjects() - Fixed my shit about InitialiseFinalLevel() using short argument when there is none. --- TR2_progress.txt | 110 ++++++++++++------------ game/moveblock.h | 15 ++-- game/objects.h | 2 +- game/setup.cpp | 219 +++++++++++++++++++++++++++++++++++++++++++++-- 4 files changed, 272 insertions(+), 74 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 6201c01..af939a4 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -189,7 +189,7 @@ x function is unused / included in another function 0x00412680: * InGameCinematicCamera game/collide.cpp -0x004128D0: GetCollisionInfo +0x004128D0: * GetCollisionInfo 0x00412F90: + FindGridShift 0x00412FC0: + CollideStaticObjects 0x004133B0: + GetNearByRooms @@ -751,56 +751,56 @@ x function is unused / included in another function 0x004337A0: ControlBodyPart game/moveblock.cpp -0x004339A0: InitialiseMovingBlock +0x004339A0: * InitialiseMovingBlock 0x004339D0: * MovableBlock -0x00433B20: MovableBlockCollision +0x00433B20: * MovableBlockCollision 0x00433D80: TestBlockMovable 0x00433DD0: TestBlockPush 0x00433F20: TestBlockPull 0x00434160: * AlterFloorHeight -0x00434220: DrawMovableBlock +0x00434220: * DrawMovableBlock 0x00434250: * DrawUnclippedItem game/objects.cpp -0x004342C0: EarthQuake -0x004343A0: ControlCutShotgun -0x004343E0: InitialiseFinalLevel -0x004344B0: FinalLevelCounter -0x004346C0: MiniCopterControl -0x004347A0: InitialiseDyingMonk -0x00434820: DyingMonk -0x004348B0: ControlGongBonger -0x00434970: DeathSlideCollision -0x00434A30: ControlDeathSlide -0x00434CC0: BigBowlControl -0x00434DB0: BellControl -0x00434E30: InitialiseWindow +0x004342C0: * EarthQuake +0x004343A0: * ControlCutShotgun +0x004343E0: * InitialiseFinalLevel +0x004344B0: * FinalLevelCounter +0x004346C0: * MiniCopterControl +0x004347A0: * InitialiseDyingMonk +0x00434820: * DyingMonk +0x004348B0: * ControlGongBonger +0x00434970: * DeathSlideCollision +0x00434A30: * ControlDeathSlide +0x00434CC0: * BigBowlControl +0x00434DB0: * BellControl +0x00434E30: * InitialiseWindow 0x00434EB0: * SmashWindow -0x00434F80: WindowControl -0x00435020: SmashIceControl +0x00434F80: * WindowControl +0x00435020: * SmashIceControl 0x00435100: + ShutThatDoor 0x00435150: + OpenThatDoor -0x00435190: InitialiseDoor +0x00435190: * InitialiseDoor 0x00435570: + DoorControl -0x00435640: OnDrawBridge -0x00435700: DrawBridgeFloor -0x00435740: DrawBridgeCeiling -0x00435780: DrawBridgeCollision -0x004357B0: InitialiseLift -0x004357F0: LiftControl -0x004358D0: LiftFloorCeiling -0x00435A50: LiftFloor -0x00435A90: LiftCeiling -0x00435AD0: BridgeFlatFloor -0x00435AF0: BridgeFlatCeiling -0x00435B10: GetOffset -0x00435B50: BridgeTilt1Floor -0x00435B80: BridgeTilt1Ceiling -0x00435BC0: BridgeTilt2Floor -0x00435BF0: BridgeTilt2Ceiling -0x00435C30: CopterControl +0x00435640: * OnDrawBridge +0x00435700: * DrawBridgeFloor +0x00435740: * DrawBridgeCeiling +0x00435780: * DrawBridgeCollision +0x004357B0: * InitialiseLift +0x004357F0: * LiftControl +0x004358D0: * LiftFloorCeiling +0x00435A50: * LiftFloor +0x00435A90: * LiftCeiling +0x00435AD0: * BridgeFlatFloor +0x00435AF0: * BridgeFlatCeiling +0x00435B10: * GetOffset +0x00435B50: * BridgeTilt1Floor +0x00435B80: * BridgeTilt1Ceiling +0x00435BC0: * BridgeTilt2Floor +0x00435BF0: * BridgeTilt2Ceiling +0x00435C30: * CopterControl 0x00435D40: + GeneralControl -0x00435E20: DetonatorControl +0x00435E20: * DetonatorControl game/people.cpp 0x00435EB0: Targetable @@ -851,7 +851,7 @@ x function is unused / included in another function 0x0043A490: * InitialiseGameFlags 0x0043A500: + InitialiseLevelFlags 0x0043A530: + BaddyObjects -0x0043B570: * TrapObjects +0x0043B570: + TrapObjects 0x0043BB70: * ObjectObjects 0x0043C7C0: + InitialiseObjects 0x0043C830: * GetCarriedItems @@ -932,26 +932,26 @@ x function is unused / included in another function 0x004411C0: + ControlSpikeWall 0x00441300: + ControlCeilingSpikes 0x00441420: + HookControl -0x004414B0: PropellerControl +0x004414B0: * PropellerControl 0x00441640: + SpinningBlade 0x004417C0: + IcicleControl 0x004418C0: + InitialiseBlade 0x00441900: + BladeControl 0x004419A0: + InitialiseKillerStatue 0x004419F0: + KillerStatueControl -0x00441B00: SpringBoardControl -0x00441BE0: InitialiseRollingBall -0x00441C20: RollingBallControl -0x00441F70: RollingBallCollision -0x004421C0: SpikeCollision -0x00442320: TrapDoorControl -0x00442370: TrapDoorFloor -0x004423B0: TrapDoorCeiling -0x004423F0: OnTrapDoor +0x00441B00: * SpringBoardControl +0x00441BE0: * InitialiseRollingBall +0x00441C20: * RollingBallControl +0x00441F70: * RollingBallCollision +0x004421C0: * SpikeCollision +0x00442320: * TrapDoorControl +0x00442370: * TrapDoorFloor +0x004423B0: * TrapDoorCeiling +0x004423F0: * OnTrapDoor 0x004424A0: + Pendulum -0x004425B0: FallingBlock -0x004426C0: FallingBlockFloor -0x00442700: FallingBlockCeiling +0x004425B0: * FallingBlock +0x004426C0: * FallingBlockFloor +0x00442700: * FallingBlockCeiling 0x00442750: + TeethTrap 0x00442810: + FallingCeiling 0x004428F0: + DartEmitterControl @@ -961,8 +961,8 @@ x function is unused / included in another function 0x00442C70: + FlameControl 0x00442DE0: + LaraBurn 0x00442E30: + LavaBurn -0x00442F20: LavaSpray -0x00442FF0: ControlLavaBlob +0x00442F20: * LavaSpray +0x00442FF0: * ControlLavaBlob game/yeti.cpp 0x00443100: * GiantYetiControl @@ -1406,7 +1406,7 @@ x function is unused / included in another function 0x00456680: + UpdateTicks 0x004566C0: + TIME_Init 0x00456720: + Sync -0x00456780: + LoadResource +0x00456780: + UT_LoadResource // NOTE: Previous name was LoadResource but utils.h have UT_ in front. 0x004567C0: + UT_InitAccurateTimer 0x00456820: + UT_Microseconds 0x00456870: + UT_CenterWindow diff --git a/game/moveblock.h b/game/moveblock.h index 0b8acff..74cbae2 100644 --- a/game/moveblock.h +++ b/game/moveblock.h @@ -27,19 +27,14 @@ /* * Function list */ -// 0x004339A0: InitialiseMovingBlock - +#define InitialiseMovingBlock ((void(__cdecl*)(__int16)) 0x004339A0) #define MovableBlock ((void(__cdecl*)(__int16)) 0x004339D0) - -// 0x00433B20: MovableBlockCollision +#define MovableBlockCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00433B20) // 0x00433D80: TestBlockMovable // 0x00433DD0: TestBlockPush // 0x00433F20: TestBlockPull - -#define AlterFloorHeight ((void(__cdecl*)(ITEM_INFO *, int)) 0x00434160) - -// 0x00434220: DrawMovableBlock - -#define DrawUnclippedItem ((void(__cdecl*)(ITEM_INFO *)) 0x00434250) +#define AlterFloorHeight ((void(__cdecl*)(ITEM_INFO*, int)) 0x00434160) +#define DrawMovableBlock ((void(__cdecl*)(ITEM_INFO*)) 0x00434220) +#define DrawUnclippedItem ((void(__cdecl*)(ITEM_INFO*)) 0x00434250) #endif // MOVE_BLOCK_H_INCLUDED diff --git a/game/objects.h b/game/objects.h index e1981cc..2464e53 100644 --- a/game/objects.h +++ b/game/objects.h @@ -29,7 +29,7 @@ */ #define EarthQuake ((void(__cdecl*)(__int16)) 0x004342C0) #define ControlCutShotgun ((void(__cdecl*)(__int16)) 0x004343A0) -#define InitialiseFinalLevel ((void(__cdecl*)(__int16)) 0x004343E0) +#define InitialiseFinalLevel ((void(__cdecl*)()) 0x004343E0) #define FinalLevelCounter ((void(__cdecl*)(__int16)) 0x004344B0) #define MiniCopterControl ((void(__cdecl*)(__int16)) 0x004346C0) #define InitialiseDyingMonk ((void(__cdecl*)(__int16)) 0x004347A0) diff --git a/game/setup.cpp b/game/setup.cpp index a665430..ea80c0f 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -144,12 +144,12 @@ void __cdecl InitialiseLevelFlags() { void __cdecl InitialiseObjects() { for( int i = 0; i < ID_NUMBER_OBJECTS; ++i ) { - Objects[i].intelligent = 0; - Objects[i].save_position = 0; - Objects[i].save_hitpoints = 0; - Objects[i].save_flags = 0; - Objects[i].save_anim = 0; - Objects[i].water_creature = 0; + Objects[i].intelligent = FALSE; + Objects[i].save_position = FALSE; + Objects[i].save_hitpoints = FALSE; + Objects[i].save_flags = FALSE; + Objects[i].save_anim = FALSE; + Objects[i].water_creature = FALSE; Objects[i].initialise = NULL; Objects[i].collision = NULL; Objects[i].control = NULL; @@ -793,8 +793,7 @@ void __cdecl BaddyObjects() { } void __cdecl TrapObjects() { - OBJECT_INFO* obj; - obj = &Objects[ID_GONDOLA]; + OBJECT_INFO* obj = &Objects[ID_GONDOLA]; if (obj->loaded) { obj->collision = ObjectCollision; obj->control = GondolaControl; @@ -857,6 +856,13 @@ void __cdecl TrapObjects() { obj->save_flags = TRUE; obj->save_position = TRUE; } + obj = &Objects[ID_PROPELLER1]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } obj = &Objects[ID_PROPELLER2]; if (obj->loaded) { obj->collision = ObjectCollision; @@ -864,6 +870,203 @@ void __cdecl TrapObjects() { obj->save_anim = TRUE; obj->save_flags = TRUE; } + obj = &Objects[ID_PROPELLER3]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj->water_creature = TRUE; + } + obj = &Objects[ID_PROPELLER4]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_SPINNING_BLADE]; + if (obj->loaded) { + obj->initialise = InitialiseKillerStatue; + obj->control = SpinningBlade; + obj->collision = ObjectCollision; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_KILLER_STATUE]; + if (obj->loaded) { + obj->initialise = InitialiseKillerStatue; + obj->control = KillerStatueControl; + obj->collision = TrapCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_FALLING_BLOCK1]; + if (obj->loaded) { + obj->control = FallingBlock; + obj->ceiling = FallingBlockCeiling; + obj->floor = FallingBlockFloor; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_FALLING_BLOCK2]; + if (obj->loaded) { + obj->control = FallingBlock; + obj->ceiling = FallingBlockCeiling; + obj->floor = FallingBlockFloor; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_FALLING_BLOCK3]; + if (obj->loaded) { + obj->control = FallingBlock; + obj->ceiling = FallingBlockCeiling; + obj->floor = FallingBlockFloor; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_ICICLE]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = IcicleControl; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_BLADE]; + if (obj->loaded) { + obj->initialise = InitialiseBlade; + obj->control = BladeControl; + obj->collision = TrapCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_SPRING_BOARD]; + if (obj->loaded) { + obj->control = SpringBoardControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_PENDULUM1]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = Pendulum; + obj->shadowSize = 128; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_PENDULUM2]; + if (obj->loaded) { + obj->collision = ObjectCollision; + obj->control = Pendulum; + obj->shadowSize = 128; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_TEETH_TRAP]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = TeethTrap; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_FALLING_CEILING]; + if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = FallingCeiling; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_ROLLING_BALL1]; + if (obj->loaded) { + obj->initialise = InitialiseRollingBall; + obj->collision = RollingBallCollision; + obj->control = RollingBallControl; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_ROLLING_BALL2]; + if (obj->loaded) { + obj->initialise = InitialiseRollingBall; + obj->collision = RollingBallCollision; + obj->control = RollingBallControl; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + obj = &Objects[ID_ROLLING_BALL3]; + if (obj->loaded) { + obj->initialise = InitialiseRollingBall; + obj->collision = RollingBallCollision; + obj->control = RollingBallControl; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + + for (int i = 0; i < 4; i++) { + obj = &Objects[ID_MOVABLE_BLOCK1 + i]; + if (obj->loaded) { + obj->initialise = InitialiseMovingBlock; + obj->collision = MovableBlockCollision; + obj->control = MovableBlock; + obj->drawRoutine = DrawMovableBlock; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + } + + obj = &Objects[ID_SPIKES]; + if (obj->loaded) { + obj->collision = SpikeCollision; + } + obj = &Objects[ID_DARTS]; + if (obj->loaded) { + obj->control = DartsControl; + obj->collision = ObjectCollision; + obj->shadowSize = 128; + } + obj = &Objects[ID_DART_EMITTER]; + if (obj->loaded) { + obj->control = DartEmitterControl; + obj->save_flags = TRUE; + } + obj = &Objects[ID_DART_EFFECT]; + if (obj->loaded) { + obj->control = DartEffectControl; + obj->drawRoutine = DrawSpriteItem; + obj->semi_transparent = TRUE; + } + obj = &Objects[ID_FLAME]; + if (obj->loaded) { + obj->control = FlameControl; + obj->semi_transparent = TRUE; + } + obj = &Objects[ID_FLAME_EMITTER]; + if (obj->loaded) { + obj->control = FlameEmitterControl; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + } + obj = &Objects[ID_LAVA]; + if (obj->loaded) { + obj->control = ControlLavaBlob; + obj->semi_transparent = TRUE; + } + obj = &Objects[ID_LAVA_EMITTER]; + if (obj->loaded) { + obj->control = LavaSpray; + obj->collision = ObjectCollision; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + } } /* From be6076aba95a766ac384737bf61d2e1d42c7a86b Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sat, 21 May 2022 11:38:04 +0200 Subject: [PATCH 57/66] Added missing SPIKE_WALL obj Reworked the TrapObjects() layout, apparently obj->loaded can cause problem if its not a baddy object ! --- game/setup.cpp | 393 +++++++++++++++++++++---------------------------- 1 file changed, 167 insertions(+), 226 deletions(-) diff --git a/game/setup.cpp b/game/setup.cpp index ea80c0f..773ae27 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -793,135 +793,111 @@ void __cdecl BaddyObjects() { } void __cdecl TrapObjects() { - OBJECT_INFO* obj = &Objects[ID_GONDOLA]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = GondolaControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + OBJECT_INFO* obj; + int i; + + obj = &Objects[ID_GONDOLA]; + obj->collision = ObjectCollision; + obj->control = GondolaControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_SPIKE_WALL]; + obj->collision = ObjectCollision; + obj->control = ControlSpikeWall; + obj->save_position = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_CEILING_SPIKES]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = ControlCeilingSpikes; - obj->save_position = TRUE; - obj->save_flags = TRUE; - } + obj->collision = TrapCollision; + obj->control = ControlCeilingSpikes; + obj->save_position = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_COPTER]; - if (obj->loaded) { - obj->control = CopterControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->control = CopterControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_MINI_COPTER]; - if (obj->loaded) { - obj->control = MiniCopterControl; - obj->save_flags = TRUE; - obj->save_position = TRUE; - } + obj->control = MiniCopterControl; + obj->save_flags = TRUE; + obj->save_position = TRUE; + obj = &Objects[ID_HOOK]; - if (obj->loaded) { - obj->collision = CreatureCollision; - obj->control = HookControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = CreatureCollision; + obj->control = HookControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_GENERAL]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = GeneralControl; - obj->water_creature = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = GeneralControl; + obj->water_creature = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_DYING_MONK]; - if (obj->loaded) { - obj->initialise = InitialiseDyingMonk; - obj->collision = ObjectCollision; - obj->control = DyingMonk; - obj->save_flags = TRUE; - } + obj->initialise = InitialiseDyingMonk; + obj->collision = ObjectCollision; + obj->control = DyingMonk; + obj->save_flags = TRUE; + obj = &Objects[ID_MINE]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = MineControl; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = MineControl; + obj->save_flags = TRUE; + obj = &Objects[ID_DEATH_SLIDE]; - if (obj->loaded) { - obj->initialise = InitialiseRollingBall; - obj->collision = DeathSlideCollision; - obj->control = ControlDeathSlide; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - obj->save_position = TRUE; - } + obj->initialise = InitialiseRollingBall; + obj->collision = DeathSlideCollision; + obj->control = ControlDeathSlide; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj->save_position = TRUE; + obj = &Objects[ID_PROPELLER1]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = PropellerControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = TrapCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_PROPELLER2]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = PropellerControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_PROPELLER3]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = PropellerControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - obj->water_creature = TRUE; - } + obj->collision = TrapCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj->water_creature = TRUE; + obj = &Objects[ID_PROPELLER4]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = PropellerControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = PropellerControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_SPINNING_BLADE]; - if (obj->loaded) { - obj->initialise = InitialiseKillerStatue; - obj->control = SpinningBlade; - obj->collision = ObjectCollision; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->initialise = InitialiseKillerStatue; + obj->control = SpinningBlade; + obj->collision = ObjectCollision; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_KILLER_STATUE]; - if (obj->loaded) { - obj->initialise = InitialiseKillerStatue; - obj->control = KillerStatueControl; - obj->collision = TrapCollision; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - obj = &Objects[ID_FALLING_BLOCK1]; - if (obj->loaded) { - obj->control = FallingBlock; - obj->ceiling = FallingBlockCeiling; - obj->floor = FallingBlockFloor; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - obj = &Objects[ID_FALLING_BLOCK2]; - if (obj->loaded) { - obj->control = FallingBlock; - obj->ceiling = FallingBlockCeiling; - obj->floor = FallingBlockFloor; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - obj = &Objects[ID_FALLING_BLOCK3]; - if (obj->loaded) { + obj->initialise = InitialiseKillerStatue; + obj->control = KillerStatueControl; + obj->collision = TrapCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + for (i = 0; i < 3; i++) { + obj = &Objects[ID_FALLING_BLOCK1 + i]; obj->control = FallingBlock; obj->ceiling = FallingBlockCeiling; obj->floor = FallingBlockFloor; @@ -929,70 +905,55 @@ void __cdecl TrapObjects() { obj->save_anim = TRUE; obj->save_flags = TRUE; } + obj = &Objects[ID_ICICLE]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = IcicleControl; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = TrapCollision; + obj->control = IcicleControl; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_BLADE]; - if (obj->loaded) { - obj->initialise = InitialiseBlade; - obj->control = BladeControl; - obj->collision = TrapCollision; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->initialise = InitialiseBlade; + obj->control = BladeControl; + obj->collision = TrapCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_SPRING_BOARD]; - if (obj->loaded) { - obj->control = SpringBoardControl; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->control = SpringBoardControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_PENDULUM1]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = Pendulum; - obj->shadowSize = 128; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = Pendulum; + obj->shadowSize = 128; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_PENDULUM2]; - if (obj->loaded) { - obj->collision = ObjectCollision; - obj->control = Pendulum; - obj->shadowSize = 128; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = ObjectCollision; + obj->control = Pendulum; + obj->shadowSize = 128; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_TEETH_TRAP]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = TeethTrap; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } + obj->collision = TrapCollision; + obj->control = TeethTrap; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + obj = &Objects[ID_FALLING_CEILING]; - if (obj->loaded) { - obj->collision = TrapCollision; - obj->control = FallingCeiling; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - obj = &Objects[ID_ROLLING_BALL1]; - if (obj->loaded) { - obj->initialise = InitialiseRollingBall; - obj->collision = RollingBallCollision; - obj->control = RollingBallControl; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - obj = &Objects[ID_ROLLING_BALL2]; - if (obj->loaded) { + obj->collision = TrapCollision; + obj->control = FallingCeiling; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + for (i = 0; i < 3; i++) { + obj = &Objects[ID_ROLLING_BALL1 + i]; obj->initialise = InitialiseRollingBall; obj->collision = RollingBallCollision; obj->control = RollingBallControl; @@ -1000,73 +961,53 @@ void __cdecl TrapObjects() { obj->save_anim = TRUE; obj->save_flags = TRUE; } - obj = &Objects[ID_ROLLING_BALL3]; - if (obj->loaded) { - obj->initialise = InitialiseRollingBall; - obj->collision = RollingBallCollision; - obj->control = RollingBallControl; + + for (i = 0; i < 4; i++) { + obj = &Objects[ID_MOVABLE_BLOCK1 + i]; + obj->initialise = InitialiseMovingBlock; + obj->collision = MovableBlockCollision; + obj->control = MovableBlock; + obj->drawRoutine = DrawMovableBlock; obj->save_position = TRUE; obj->save_anim = TRUE; obj->save_flags = TRUE; } - for (int i = 0; i < 4; i++) { - obj = &Objects[ID_MOVABLE_BLOCK1 + i]; - if (obj->loaded) { - obj->initialise = InitialiseMovingBlock; - obj->collision = MovableBlockCollision; - obj->control = MovableBlock; - obj->drawRoutine = DrawMovableBlock; - obj->save_position = TRUE; - obj->save_anim = TRUE; - obj->save_flags = TRUE; - } - } - obj = &Objects[ID_SPIKES]; - if (obj->loaded) { - obj->collision = SpikeCollision; - } + obj->collision = SpikeCollision; + obj = &Objects[ID_DARTS]; - if (obj->loaded) { - obj->control = DartsControl; - obj->collision = ObjectCollision; - obj->shadowSize = 128; - } + obj->control = DartsControl; + obj->collision = ObjectCollision; + obj->shadowSize = 128; + obj = &Objects[ID_DART_EMITTER]; - if (obj->loaded) { - obj->control = DartEmitterControl; - obj->save_flags = TRUE; - } + obj->control = DartEmitterControl; + obj->save_flags = TRUE; + obj = &Objects[ID_DART_EFFECT]; - if (obj->loaded) { - obj->control = DartEffectControl; - obj->drawRoutine = DrawSpriteItem; - obj->semi_transparent = TRUE; - } + obj->control = DartEffectControl; + obj->drawRoutine = DrawSpriteItem; + obj->semi_transparent = TRUE; + obj = &Objects[ID_FLAME]; - if (obj->loaded) { - obj->control = FlameControl; - obj->semi_transparent = TRUE; - } + obj->control = FlameControl; + obj->semi_transparent = TRUE; + obj = &Objects[ID_FLAME_EMITTER]; - if (obj->loaded) { - obj->control = FlameEmitterControl; - obj->drawRoutine = DrawDummyItem; - obj->save_flags = TRUE; - } + obj->control = FlameEmitterControl; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + obj = &Objects[ID_LAVA]; - if (obj->loaded) { - obj->control = ControlLavaBlob; - obj->semi_transparent = TRUE; - } + obj->control = ControlLavaBlob; + obj->semi_transparent = TRUE; + obj = &Objects[ID_LAVA_EMITTER]; - if (obj->loaded) { - obj->control = LavaSpray; - obj->collision = ObjectCollision; - obj->drawRoutine = DrawDummyItem; - obj->save_flags = TRUE; - } + obj->control = LavaSpray; + obj->collision = ObjectCollision; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; } /* From 1812a5c78a28016138ba22cc0a9fb5534b0bead2 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Sun, 22 May 2022 12:46:11 +0200 Subject: [PATCH 58/66] Finished decompiling ObjectObjects() - Added SetPickup() to create pickup easily ! - Fixed secret pickup 1 & 3 not having the control behaviour ! --- game/boat.h | 6 +- game/dragon.h | 3 +- game/lara1gun.h | 2 +- game/laraflare.h | 2 +- game/missile.h | 6 +- game/people.h | 4 +- game/pickup.h | 19 +-- game/setup.cpp | 377 +++++++++++++++++++++++++++++++++++++++++++---- game/setup.h | 2 +- game/skidoo.h | 8 +- 10 files changed, 370 insertions(+), 59 deletions(-) diff --git a/game/boat.h b/game/boat.h index 59b7a6c..34eadff 100644 --- a/game/boat.h +++ b/game/boat.h @@ -27,9 +27,9 @@ /* * Function list */ -// 0x0040CB10: InitialiseBoat +#define InitialiseBoat ((void(__cdecl*)(__int16)) 0x0040CB10) // 0x0040CB50: BoatCheckGeton -// 0x0040CCC0: BoatCollision +#define BoatCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x0040CCC0) // 0x0040CE20: TestWaterHeight // 0x0040CF20: DoBoatShift @@ -39,7 +39,7 @@ void __cdecl DoWakeEffect(ITEM_INFO *item); // 0x0040D0F0 // 0x0040D2C0: BoatDynamics // 0x0040D7A0: BoatUserControl // 0x0040D930: BoatAnimation -// 0x0040DAA0: BoatControl +#define BoatControl ((void(__cdecl*)(__int16)) 0x0040DAA0) void __cdecl GondolaControl(__int16 itemID); // 0x0040E0D0 diff --git a/game/dragon.h b/game/dragon.h index 1dcabe4..6f8e7f9 100644 --- a/game/dragon.h +++ b/game/dragon.h @@ -27,10 +27,9 @@ /* * Function list */ -// 0x00417780: ControlTwinkle +#define ControlTwinkle ((void(__cdecl*)(__int16)) 0x00417780) // 0x00417900: CreateBartoliLight // 0x004179E0: DragonFire - #define DragonCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00417A90) #define DragonBones ((void(__cdecl*)(__int16)) 0x00417D80) #define DragonControl ((void(__cdecl*)(__int16)) 0x00417E60) diff --git a/game/lara1gun.h b/game/lara1gun.h index 744a175..dd31e2b 100644 --- a/game/lara1gun.h +++ b/game/lara1gun.h @@ -36,7 +36,7 @@ void __cdecl FireShotgun(); // 0x0042BE70 void __cdecl FireM16(BOOL isRunning); // 0x0042BF70 void __cdecl FireHarpoon(); // 0x0042BFF0 -// 0x0042C180: ControlHarpoonBolt +#define ControlHarpoonBolt ((void(__cdecl*)(__int16)) 0x0042C180) void __cdecl FireRocket(); // 0x0042C4D0 void __cdecl ControlRocket(__int16 itemID); // 0x0042C5C0 diff --git a/game/laraflare.h b/game/laraflare.h index 67011b3..b508bcf 100644 --- a/game/laraflare.h +++ b/game/laraflare.h @@ -39,6 +39,6 @@ void __cdecl DrawFlareInAir(ITEM_INFO *item); // 0x00430090: draw_flare_meshes // 0x004300B0: undraw_flare_meshes // 0x004300D0: ready_flare -// 0x00430110: FlareControl +#define FlareControl ((void(__cdecl*)(__int16)) 0x00430110) #endif // LARA_FLARE_H_INCLUDED diff --git a/game/missile.h b/game/missile.h index b2863b5..7030d58 100644 --- a/game/missile.h +++ b/game/missile.h @@ -27,13 +27,9 @@ /* * Function list */ - void __cdecl ControlMissile(__int16 fxID); // 0x00433090 - // 0x00433360: ShootAtLara - #define ExplodingDeath ((BOOL(__cdecl*)(__int16, DWORD, __int16)) 0x00433410) - -// 0x004337A0: ControlBodyPart +#define ControlBodyPart ((void(__cdecl*)(__int16)) 0x004337A0) #endif // MISSILE_H_INCLUDED diff --git a/game/people.h b/game/people.h index 1d41dad..7bd4961 100644 --- a/game/people.h +++ b/game/people.h @@ -28,8 +28,8 @@ * Function list */ // 0x00435EB0: Targetable -// 0x00435F40: ControlGlow -// 0x00435F80: ControlGunShot +#define ControlGlow ((void(__cdecl*)(__int16)) 0x00435F40) +#define ControlGunShot ((void(__cdecl*)(__int16)) 0x00435F80) __int16 __cdecl GunShot(int x, int y, int z, __int16 speed, __int16 rotY, __int16 roomNumber); // 0x00435FD0 __int16 __cdecl GunHit(int x, int y, int z, __int16 speed, __int16 rotY, __int16 roomNumber); // 0x00436040 diff --git a/game/pickup.h b/game/pickup.h index 1f5aa0d..a5b21a8 100644 --- a/game/pickup.h +++ b/game/pickup.h @@ -28,19 +28,16 @@ * Function list */ -#define PickUpCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00437F20) - -// 0x004383A0: SwitchCollision -// 0x004385B0: SwitchCollision2 -// 0x004386B0: DetonatorCollision -// 0x004388F0: KeyHoleCollision - -#define PuzzleHoleCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x00438B30) - -// 0x00438DF0: SwitchControl +#define PickUpCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00437F20) +#define SwitchCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x004383A0) +#define SwitchCollision2 ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x004385B0) +#define DetonatorCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x004386B0) +#define KeyHoleCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x004388F0) +#define PuzzleHoleCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x00438B30) +#define SwitchControl ((void(__cdecl*)(__int16)) 0x00438DF0) // 0x00438E30: SwitchTrigger // 0x00438EF0: KeyTrigger // 0x00438F30: PickupTrigger -// 0x00438F70: SecretControl +#define SecretControl ((void(__cdecl*)(__int16)) 0x00438F70) #endif // PICKUP_H_INCLUDED diff --git a/game/setup.cpp b/game/setup.cpp index 773ae27..1580b66 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -25,22 +25,28 @@ #include "game/bird.h" #include "game/boat.h" #include "game/collide.h" +#include "game/cinema.h" #include "game/diver.h" #include "game/dog.h" #include "game/dragon.h" #include "game/draw.h" #include "game/eel.h" +#include "game/effects.h" #include "game/enemies.h" #include "game/gameflow.h" #include "game/hair.h" #include "game/health.h" #include "game/items.h" #include "game/invfunc.h" +#include "game/lara1gun.h" +#include "game/laraflare.h" #include "game/laramisc.h" #include "game/lot.h" #include "game/moveblock.h" +#include "game/missile.h" #include "game/objects.h" #include "game/people.h" +#include "game/pickup.h" #include "game/rat.h" #include "game/savegame.h" #include "game/shark.h" @@ -62,9 +68,21 @@ extern bool IsGold(); #endif +// NOTE: Create simple pickup item (2D) +// Set isSecret if it's a secret pickup (Example: Dragon Item) +static void SetPickup(GAME_OBJECT_ID objectID, bool isSecret = false) { + OBJECT_INFO* obj = &Objects[objectID]; + obj->drawRoutine = DrawSpriteItem; + obj->collision = PickUpCollision; + obj->save_position = TRUE; + obj->save_flags = TRUE; + if (isSecret) { + obj->control = SecretControl; + } +} + BOOL __cdecl InitialiseLevel(int levelID, GF_LEVEL_TYPE levelType) { BOOL isLoaded = FALSE; - if (levelType != GFL_TITLE && levelType != GFL_CUTSCENE) { CurrentLevel = levelID; } @@ -88,7 +106,7 @@ BOOL __cdecl InitialiseLevel(int levelID, GF_LEVEL_TYPE levelType) { if (levelType == GFL_NORMAL || levelType == GFL_SAVED || levelType == GFL_DEMO) { GetCarriedItems(); } - Effects = (FX_INFO*)game_malloc(3600, GBUF_EffectsArray); + Effects = (FX_INFO*)game_malloc(sizeof(FX_INFO) * 100, GBUF_EffectsArray); InitialiseFXArray(); InitialiseLOTarray(); InitColours(); @@ -142,31 +160,6 @@ void __cdecl InitialiseLevelFlags() { memset(&SaveGame.statistics, 0, sizeof(STATISTICS_INFO)); } -void __cdecl InitialiseObjects() { - for( int i = 0; i < ID_NUMBER_OBJECTS; ++i ) { - Objects[i].intelligent = FALSE; - Objects[i].save_position = FALSE; - Objects[i].save_hitpoints = FALSE; - Objects[i].save_flags = FALSE; - Objects[i].save_anim = FALSE; - Objects[i].water_creature = FALSE; - Objects[i].initialise = NULL; - Objects[i].collision = NULL; - Objects[i].control = NULL; - Objects[i].drawRoutine = DrawAnimatingItem; - Objects[i].ceiling = NULL; - Objects[i].floor = NULL; - Objects[i].pivotLength = 0; - Objects[i].radius = 10; - Objects[i].shadowSize = 0; - Objects[i].hitPoints = HP_DONT_TARGET; - } - BaddyObjects(); - TrapObjects(); - ObjectObjects(); - InitialiseHair(); -} - void __cdecl BaddyObjects() { OBJECT_INFO *obj; @@ -793,7 +786,7 @@ void __cdecl BaddyObjects() { } void __cdecl TrapObjects() { - OBJECT_INFO* obj; + OBJECT_INFO *obj; int i; obj = &Objects[ID_GONDOLA]; @@ -1010,6 +1003,332 @@ void __cdecl TrapObjects() { obj->save_flags = TRUE; } +void __cdecl ObjectObjects() { + OBJECT_INFO* obj; + int i; + + obj = &Objects[ID_CAMERA_TARGET]; + obj->drawRoutine = DrawDummyItem; + + obj = &Objects[ID_ROCKET]; + obj->control = ControlRocket; + obj->save_position = TRUE; + + obj = &Objects[ID_HARPOON_BOLT]; + obj->control = ControlHarpoonBolt; + obj->save_position = TRUE; + + obj = &Objects[ID_MISSILE_KNIFE]; + obj->control = ControlMissile; + obj->save_position = TRUE; + + obj = &Objects[ID_MISSILE_HARPOON]; + obj->control = ControlMissile; + obj->save_position = TRUE; + + for (i = 0; i < 3; i++) { + obj = &Objects[ID_SPHERE_OF_DOOM1 + i]; + obj->control = SphereOfDoom; + obj->drawRoutine = DrawSphereOfDoom; + obj->collision = SphereOfDoomCollision; + if (i < 2) { + obj->semi_transparent = TRUE; + } + obj->save_flags = TRUE; + obj->save_position = TRUE; + } + + obj = &Objects[ID_BIG_BOWL]; + obj->control = BigBowlControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_BELL]; + obj->control = BellControl; + obj->collision = ObjectCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_SKIDOO_FAST]; + obj->initialise = InitialiseSkidoo; + obj->collision = SkidooCollision; + obj->drawRoutine = DrawSkidoo; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_BOAT]; + obj->initialise = InitialiseBoat; + obj->control = BoatControl; + obj->collision = BoatCollision; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_FLARE_ITEM]; + obj->control = FlareControl; + obj->collision = PickUpCollision; + obj->drawRoutine = DrawFlareInAir; + obj->save_position = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_WINDOW1]; + obj->initialise = InitialiseWindow; + obj->control = WindowControl; + obj->collision = ObjectCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_WINDOW2]; + obj->initialise = InitialiseWindow; + obj->control = SmashIceControl; + obj->collision = ObjectCollision; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_LIFT]; + obj->initialise = InitialiseLift; + obj->control = LiftControl; + obj->floor = LiftFloor; + obj->ceiling = LiftCeiling; + obj->save_position = TRUE; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_BRIDGE_FLAT]; + obj->floor = BridgeFlatFloor; + obj->ceiling = BridgeFlatCeiling; + + obj = &Objects[ID_BRIDGE_TILT1]; + obj->floor = BridgeTilt1Floor; + obj->ceiling = BridgeTilt1Ceiling; + + obj = &Objects[ID_BRIDGE_TILT2]; + obj->floor = BridgeTilt2Floor; + obj->ceiling = BridgeTilt2Ceiling; + + obj = &Objects[ID_DRAW_BRIDGE]; + if (obj->loaded) { + obj->control = GeneralControl; + obj->collision = DrawBridgeCollision; + obj->floor = DrawBridgeFloor; + obj->ceiling = DrawBridgeCeiling; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + + for (i = 0; i < 5; i++) { + obj = &Objects[ID_SWITCH_TYPE1 + i]; + obj->control = SwitchControl; + obj->collision = i < 4 ? SwitchCollision : SwitchCollision2; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + + for (i = 0; i < 8; i++) { + obj = &Objects[ID_DOOR_TYPE1 + i]; + obj->initialise = InitialiseDoor; + obj->control = DoorControl; + obj->collision = DoorCollision; + obj->drawRoutine = DrawUnclippedItem; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + + for (i = 0; i < 2; i++) { + obj = &Objects[ID_TRAPDOOR_TYPE1 + i]; + obj->control = TrapDoorControl; + obj->ceiling = TrapDoorCeiling; + obj->floor = TrapDoorFloor; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + } + + SetPickup(ID_PICKUP_ITEM1); + SetPickup(ID_PICKUP_ITEM2); + SetPickup(ID_KEY_ITEM1); + SetPickup(ID_KEY_ITEM2); + SetPickup(ID_KEY_ITEM3); + SetPickup(ID_KEY_ITEM4); + SetPickup(ID_PUZZLE_ITEM1); + SetPickup(ID_PUZZLE_ITEM2); + SetPickup(ID_PUZZLE_ITEM3); + SetPickup(ID_PUZZLE_ITEM4); + SetPickup(ID_SECRET1, true); + SetPickup(ID_SECRET2, true); + SetPickup(ID_SECRET3, true); + SetPickup(ID_PISTOL_ITEM); + SetPickup(ID_SHOTGUN_ITEM); + SetPickup(ID_MAGNUM_ITEM); + SetPickup(ID_UZI_ITEM); + SetPickup(ID_M16_ITEM); + SetPickup(ID_HARPOON_ITEM); + SetPickup(ID_GRENADE_ITEM); + SetPickup(ID_PISTOL_AMMO_ITEM); + SetPickup(ID_SHOTGUN_AMMO_ITEM); + SetPickup(ID_MAGNUM_AMMO_ITEM); + SetPickup(ID_UZI_AMMO_ITEM); + SetPickup(ID_M16_AMMO_ITEM); + SetPickup(ID_HARPOON_AMMO_ITEM); + SetPickup(ID_GRENADE_AMMO_ITEM); + SetPickup(ID_FLARES_ITEM); + SetPickup(ID_SMALL_MEDIPACK_ITEM); + SetPickup(ID_LARGE_MEDIPACK_ITEM); + + obj = &Objects[ID_GONG_BONGER]; + obj->control = ControlGongBonger; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + for (i = 0; i < 4; i++) { + obj = &Objects[ID_KEY_HOLE1 + i]; + obj->collision = KeyHoleCollision; + obj->save_flags = TRUE; + } + + for (i = 0; i < 4; i++) { + obj = &Objects[ID_PUZZLE_HOLE1 + i]; + obj->collision = PuzzleHoleCollision; + obj->save_flags = TRUE; + } + + for (i = 0; i < 4; i++) { + obj = &Objects[ID_PUZZLE_DONE1 + i]; + obj->save_flags = TRUE; + } + + obj = &Objects[ID_DETONATOR1]; + obj->collision = DetonatorCollision; + + obj = &Objects[ID_DETONATOR2]; + obj->collision = DetonatorCollision; + obj->control = DetonatorControl; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_ALARM_SOUND]; + obj->control = ControlAlarmSound; + obj->save_flags = TRUE; + + obj = &Objects[ID_LARA_ALARM]; + obj->control = ControlLaraAlarm; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + + for (i = 0; i < 10; i++) { + obj = &Objects[ID_PLAYER1 + i]; + obj->initialise = InitialiseGenPlayer; + obj->control = ControlCinematicPlayer; + obj->hitPoints = 1; + } + + obj = &Objects[ID_BLOOD]; + obj->control = ControlBlood1; + obj->semi_transparent = TRUE; + + obj = &Objects[ID_BUBBLES]; + obj->control = ControlBubble1; + + obj = &Objects[ID_EXPLOSION]; + obj->control = ControlExplosion1; + obj->semi_transparent = TRUE; + + obj = &Objects[ID_MISSILE_FLAME]; + obj->control = ControlMissile; + obj->semi_transparent = TRUE; + + obj = &Objects[ID_RICOCHET]; + obj->control = ControlRichochet1; + + obj = &Objects[ID_TWINKLE]; + obj->control = ControlTwinkle; + + obj = &Objects[ID_SPLASH]; + obj->control = ControlSplash1; + obj->semi_transparent = TRUE; + + obj = &Objects[ID_SNOW_SPRITE]; + obj->control = ControlSnowSprite; + + obj = &Objects[ID_WATER_SPRITE]; + obj->control = ControlWaterSprite; + obj->semi_transparent = TRUE; + + obj = &Objects[ID_WATERFALL]; + obj->control = WaterFall; + obj->drawRoutine = DrawDummyItem; + + obj = &Objects[ID_BODY_PART]; + obj->nMeshes = 0; + obj->control = ControlBodyPart; + obj->loaded = TRUE; + + obj = &Objects[ID_GUN_FLASH]; + obj->control = ControlGunShot; + + obj = &Objects[ID_GLOW]; + obj->control = ControlGlow; + + obj = &Objects[ID_HOT_LIQUID]; + obj->control = ControlHotLiquid; + obj->semi_transparent = TRUE; + + for (i = 0; i < 2; i++) { + obj = &Objects[ID_BIRD_TWEETER1 + i]; + obj->control = ControlBirdTweeter; + obj->drawRoutine = DrawDummyItem; + } + + obj = &Objects[ID_DING_DONG]; + obj->control = ControlDingDong; + obj->drawRoutine = DrawDummyItem; + + obj = &Objects[ID_CLOCK_CHIMES]; + obj->control = ControlClockChimes; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + + obj = &Objects[ID_FINAL_LEVEL_COUNTER]; + obj->control = FinalLevelCounter; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; + + obj = &Objects[ID_CUT_SHOTGUN]; + obj->control = ControlCutShotgun; + obj->save_anim = TRUE; + obj->save_flags = TRUE; + + obj = &Objects[ID_EARTHQUAKE]; + obj->control = EarthQuake; + obj->drawRoutine = DrawDummyItem; + obj->save_flags = TRUE; +} + +void __cdecl InitialiseObjects() { + for( int i = 0; i < ID_NUMBER_OBJECTS; ++i ) { + Objects[i].intelligent = FALSE; + Objects[i].save_position = FALSE; + Objects[i].save_hitpoints = FALSE; + Objects[i].save_flags = FALSE; + Objects[i].save_anim = FALSE; + Objects[i].water_creature = FALSE; + Objects[i].initialise = NULL; + Objects[i].collision = NULL; + Objects[i].control = NULL; + Objects[i].drawRoutine = DrawAnimatingItem; + Objects[i].ceiling = NULL; + Objects[i].floor = NULL; + Objects[i].pivotLength = 0; + Objects[i].radius = 10; + Objects[i].shadowSize = 0; + Objects[i].hitPoints = HP_DONT_TARGET; + } + BaddyObjects(); + TrapObjects(); + ObjectObjects(); + InitialiseHair(); +} + /* * Inject function */ @@ -1019,7 +1338,7 @@ void Inject_Setup() { INJECT(0x0043A500, InitialiseLevelFlags); INJECT(0x0043A530, BaddyObjects); INJECT(0x0043B570, TrapObjects); -// INJECT(0x0043BB70, ObjectObjects); + INJECT(0x0043BB70, ObjectObjects); INJECT(0x0043C7C0, InitialiseObjects); // INJECT(0x0043C830, GetCarriedItems); } diff --git a/game/setup.h b/game/setup.h index 657c47a..7cbddf0 100644 --- a/game/setup.h +++ b/game/setup.h @@ -32,7 +32,7 @@ void __cdecl InitialiseGameFlags(); // 0x0043A490 void __cdecl InitialiseLevelFlags(); // 0x0043A500 void __cdecl BaddyObjects(); // 0x0043A530 void __cdecl TrapObjects(); // 0x0043B570 -#define ObjectObjects ((void(__cdecl*)(void)) 0x0043BB70) +void __cdecl ObjectObjects(); // 0x0043BB70 void __cdecl InitialiseObjects(); // 0x0043C7C0 #define GetCarriedItems ((void(__cdecl*)(void)) 0x0043C830) diff --git a/game/skidoo.h b/game/skidoo.h index 3a95247..16a23f2 100644 --- a/game/skidoo.h +++ b/game/skidoo.h @@ -29,8 +29,8 @@ */ #define InitialiseSkidoo ((void(__cdecl*)(__int16)) 0x0043CEE0) -// 0x0043CF20: SkidooCheckGeton -// 0x0043D010: SkidooCollision +// 0x0043CF20: SkidooCheckGetOn +#define SkidooCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x0043D010) // 0x0043D110: SkidooBaddieCollision // 0x0043D310: TestHeight // 0x0043D3D0: DoShift @@ -50,7 +50,7 @@ void __cdecl SkidooExplode(ITEM_INFO *item); // 0x0043E2D0 void __cdecl SkidooGuns(); // 0x0043E590 -// 0x0043E6B0: SkidooControl +#define SkidooControl ((void(__cdcel*)(__int16)) 0x0043E6B0) void __cdecl DrawSkidoo(ITEM_INFO *item); @@ -59,6 +59,6 @@ void __cdecl DrawSkidoo(ITEM_INFO *item); // 0x0043F280: SkidmanPush -#define SkidmanCollision ((void(__cdecl*)(__int16, ITEM_INFO *, COLL_INFO *)) 0x0043F3A0) +#define SkidmanCollision ((void(__cdecl*)(__int16,ITEM_INFO*,COLL_INFO*)) 0x0043F3A0) #endif // SKIDOO_H_INCLUDED From 7a32ec2b1ff26bc6a379d4be086268b1f88d9d27 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 26 May 2022 10:41:16 +0200 Subject: [PATCH 59/66] Fixed cinematic crash for level 1 - it was caused by InitialiseGameFlags() not being called anymore since it was missing, it cause crash if a cutscene was played after a level finish. - Also fixed the hair flotting in air if the cheat was activated when triggering a cutscene ! --- game/cinema.cpp | 10 ++++++++++ game/setup.cpp | 1 + 2 files changed, 11 insertions(+) diff --git a/game/cinema.cpp b/game/cinema.cpp index 69e46c0..d171f5f 100644 --- a/game/cinema.cpp +++ b/game/cinema.cpp @@ -51,6 +51,16 @@ int __cdecl StartCinematic(int levelID) { return 2; } + // NOTE: fix lara hair waving in air, + // Caused by the cheat fly mode being not reset when cutscene is played ! + if (Lara.water_status == LWS_Cheat) { + Lara.water_status = LWS_AboveWater; + LaraItem->currentAnimState = AS_STOP; + LaraItem->goalAnimState = AS_STOP; + LaraItem->animNumber = 11; + LaraItem->frameNumber = Anims[LaraItem->animNumber].frameBase; + } + InitCinematicRooms(); InitialisePlayer1(Lara.item_number); Camera.targetAngle = CineTargetAngle; diff --git a/game/setup.cpp b/game/setup.cpp index 1580b66..135c947 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -87,6 +87,7 @@ BOOL __cdecl InitialiseLevel(int levelID, GF_LEVEL_TYPE levelType) { CurrentLevel = levelID; } IsDemoLevelType = levelType == GFL_DEMO; + InitialiseGameFlags(); Lara.item_number = -1; IsTitleLoaded = FALSE; if (levelType != GFL_TITLE) { From bfe2c759f496d41148f6b939d94709abeb6c3988 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 26 May 2022 10:54:34 +0200 Subject: [PATCH 60/66] Finished setup.cpp - Decompiled GetCarriedItems() --- game/setup.cpp | 28 +++++++++++++++++++++++++++- game/setup.h | 2 +- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/game/setup.cpp b/game/setup.cpp index 135c947..14e7357 100644 --- a/game/setup.cpp +++ b/game/setup.cpp @@ -1330,6 +1330,32 @@ void __cdecl InitialiseObjects() { InitialiseHair(); } +void __cdecl GetCarriedItems() { + ITEM_INFO *item, *pickup; + int i; + + for (i = 0, item = Items; i < LevelItemCount; i++, item++) { + if (Objects[item->objectID].intelligent) { + item->carriedItem = -1; + __int16 pickupID = RoomInfo[item->roomNumber].itemNumber; + while (pickupID != -1) + { + pickup = &Items[pickupID]; + if (pickup->pos.x == item->pos.x + && pickup->pos.y == item->pos.y + && pickup->pos.z == item->pos.z + && Objects[pickup->objectID].collision == PickUpCollision) { + pickup->carriedItem = item->carriedItem; + item->carriedItem = pickupID; + RemoveDrawnItem(pickupID); + pickup->roomNumber = 255; + } + pickupID = pickup->nextItem; + } + } + } +} + /* * Inject function */ @@ -1341,5 +1367,5 @@ void Inject_Setup() { INJECT(0x0043B570, TrapObjects); INJECT(0x0043BB70, ObjectObjects); INJECT(0x0043C7C0, InitialiseObjects); -// INJECT(0x0043C830, GetCarriedItems); + INJECT(0x0043C830, GetCarriedItems); } diff --git a/game/setup.h b/game/setup.h index 7cbddf0..29a8910 100644 --- a/game/setup.h +++ b/game/setup.h @@ -34,6 +34,6 @@ void __cdecl BaddyObjects(); // 0x0043A530 void __cdecl TrapObjects(); // 0x0043B570 void __cdecl ObjectObjects(); // 0x0043BB70 void __cdecl InitialiseObjects(); // 0x0043C7C0 -#define GetCarriedItems ((void(__cdecl*)(void)) 0x0043C830) +void __cdecl GetCarriedItems(); // 0x0043C830 #endif // SETUP_H_INCLUDED From 636187adde564d8adef06a87c41559d84eebf0c8 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 26 May 2022 11:23:49 +0200 Subject: [PATCH 61/66] Fixed Joystick in DirectInput8 - Wrong flag was used when enumerating joystick. - Fixed also the vibrating joystick check, it was using double left check instead of left and right check. - Also fixed using WINBOOL instead of BOOL - Added all missing define in control.h --- game/control.h | 27 ++++++++------------------- game/effects.h | 2 -- game/items.h | 7 ------- game/sound.h | 2 -- modding/xinput_ex.cpp | 2 +- specific/init_input.cpp | 6 +++++- 6 files changed, 14 insertions(+), 32 deletions(-) diff --git a/game/control.h b/game/control.h index 5640981..5f93622 100644 --- a/game/control.h +++ b/game/control.h @@ -28,36 +28,25 @@ * Function list */ int __cdecl ControlPhase(int nTicks, BOOL demoMode); - #define AnimateItem ((void(__cdecl*)(ITEM_INFO*)) 0x004146C0) - #define GetChange ((int(__cdecl*)(ITEM_INFO*,ANIM_STRUCT*)) 0x00414A30) #define TranslateItem ((void(__cdecl*)(ITEM_INFO*,int,int,int)) 0x00414AE0) - #define GetFloor ((FLOOR_INFO*(__cdecl*)(int, int, int, __int16*)) 0x00414B40) #define GetWaterHeight ((int(__cdecl*)(int, int, int, __int16)) 0x00414CE0) #define GetHeight ((int(__cdecl*)(FLOOR_INFO*, int, int, int)) 0x00414E50) - -// 0x004150D0: RefreshCamera - +#define RefreshCamera ((void(__cdecl*)(int,__int16*)) 0x004150D0) #define TestTriggers ((void(__cdecl*)(__int16*, BOOL)) 0x004151C0) #define TriggerActive ((int(__cdecl*)(ITEM_INFO*)) 0x004158A0) #define GetCeiling ((int(__cdecl*)(FLOOR_INFO*, int, int, int)) 0x00415900) - -// 0x00415B60: GetDoor - +#define GetDoor ((__int16(__cdecl*)(FLOOR_INFO*)) 0x00415B60) #define LOS ((int(__cdecl*)(GAME_VECTOR*, GAME_VECTOR*)) 0x00415BB0) - -// 0x00415C50: zLOS -// 0x00415F40: xLOS -// 0x00416230: ClipTarget -// 0x00416310: ObjectOnLOS - +#define zLOS ((int(__cdecl*)(GAME_VECTOR*, GAME_VECTOR*)) 0x00415C50) +#define xLOS ((int(__cdecl*)(GAME_VECTOR*, GAME_VECTOR*)) 0x00415F40) +#define ClipTarget ((int(__cdecl*)(GAME_VECTOR*, GAME_VECTOR*, FLOOR_INFO*)) 0x00416230) +#define ObjectOnLOS ((int(__cdecl*)(GAME_VECTOR*, GAME_VECTOR*)) 0x00416310) #define FlipMap ((void(__cdecl*)(void)) 0x00416610) - -// 0x004166D0: RemoveRoomFlipItems -// 0x00416770: AddRoomFlipItems - +#define RemoveRoomFlipItems ((void(__cdecl*)(ROOM_INFO*)) 0x004166D0) +#define AddRoomFlipItems ((void(__cdecl*)(ROOM_INFO*)) 0x00416770) void __cdecl TriggerCDTrack(__int16 value, UINT16 flags, __int16 type); // 0x004167D0 void __cdecl TriggerNormalCDTrack(__int16 value, UINT16 flags, __int16 type); // 0x00416800; diff --git a/game/effects.h b/game/effects.h index 72e1ee8..c78856b 100644 --- a/game/effects.h +++ b/game/effects.h @@ -71,10 +71,8 @@ void __cdecl lara_hands_free(ITEM_INFO *item); // 0x0041D760 void __cdecl flip_map_effect(ITEM_INFO *item); // 0x0041D770 void __cdecl draw_right_gun(ITEM_INFO *item); // 0x0041D780 void __cdecl draw_left_gun(ITEM_INFO *item); // 0x0041D7D0 - // ----------: shoot_right_gun // ----------: shoot_left_gun - void __cdecl swap_meshes_with_meshswap1(ITEM_INFO *item); // 0x0041D820 void __cdecl swap_meshes_with_meshswap2(ITEM_INFO *item); // 0x0041D890 void __cdecl swap_meshes_with_meshswap3(ITEM_INFO *item); // 0x0041D900 diff --git a/game/items.h b/game/items.h index ddc757b..87439b5 100644 --- a/game/items.h +++ b/game/items.h @@ -28,21 +28,14 @@ * Function list */ void __cdecl InitialiseItemArray(int itemCount); // 0x00426CD0 - #define KillItem ((void(__cdecl*)(__int16)) 0x00426D30) #define CreateItem ((__int16(__cdecl*)(void)) 0x00426E50) - void __cdecl InitialiseItem(__int16 itemIndex); // 0x00426E90 - #define RemoveActiveItem ((void(__cdecl*)(__int16)) 0x00427050) #define RemoveDrawnItem ((void(__cdecl*)(__int16)) 0x004270E0) - void __cdecl AddActiveItem(__int16 itemIndex); // 0x00427150 - #define ItemNewRoom ((void(__cdecl*)(__int16, __int16)) 0x004271B0) - int __cdecl GlobalItemReplace(int oldItemID, int newItemID); // 0x00427250 - #define InitialiseFXArray ((void(__cdecl*)(void)) 0x004272D0) #define CreateEffect ((__int16(__cdecl*)(__int16)) 0x00427300) #define KillEffect ((void(__cdecl*)(__int16)) 0x00427370) diff --git a/game/sound.h b/game/sound.h index c409403..130946c 100644 --- a/game/sound.h +++ b/game/sound.h @@ -28,12 +28,10 @@ * Function list */ int __cdecl GetRealTrack(int trackID); // 0x0043F430 - #define PlaySoundEffect ((void(__cdecl*)(DWORD, PHD_3DPOS *, DWORD)) 0x0043F470) #define StopSoundEffect ((void(__cdecl*)(int)) 0x0043F910) #define SOUND_EndScene ((void(__cdecl*)(void)) 0x0043F970) #define SOUND_Stop ((void(__cdecl*)(void)) 0x0043FA00) - void __cdecl SOUND_Init(); // 0x0043FA30 #endif // SOUND_H_INCLUDED diff --git a/modding/xinput_ex.cpp b/modding/xinput_ex.cpp index 0949e6e..8a51016 100644 --- a/modding/xinput_ex.cpp +++ b/modding/xinput_ex.cpp @@ -27,7 +27,7 @@ // Imports from xinput*.dll static HMODULE hXInput = NULL; -static void (WINAPI *_XInputEnable)(WINBOOL) = NULL; +static void (WINAPI *_XInputEnable)(BOOL) = NULL; static DWORD (WINAPI *_XInputGetCapabilities)(DWORD, DWORD, XINPUT_CAPABILITIES*) = NULL; static DWORD (WINAPI *_XInputSetState)(DWORD, XINPUT_VIBRATION*) = NULL; static DWORD (WINAPI *_XInputGetState)(DWORD, XINPUT_STATE*) = NULL; diff --git a/specific/init_input.cpp b/specific/init_input.cpp index a9d5f2e..e0d0e04 100644 --- a/specific/init_input.cpp +++ b/specific/init_input.cpp @@ -164,7 +164,7 @@ bool IsJoyVibrationSupported() { return true; } if( XInputIndex >= 0 ) { - return( XInputCaps.Vibration.wLeftMotorSpeed || XInputCaps.Vibration.wLeftMotorSpeed ); + return( XInputCaps.Vibration.wLeftMotorSpeed || XInputCaps.Vibration.wRightMotorSpeed ); } return false; } @@ -459,7 +459,11 @@ bool __cdecl DInputEnumDevices(JOYSTICK_LIST *joystickList) { } RawInputEnumerate(RawInputCallBack, (LPVOID)joystickList); #endif // FEATURE_INPUT_IMPROVED +#if DIRECTINPUT_VERSION >= 0x800 + return SUCCEEDED(DInput->EnumDevices(DI8DEVTYPE_JOYSTICK, DInputEnumDevicesCallback, (LPVOID)joystickList, DIEDFL_ATTACHEDONLY)); +#else return SUCCEEDED(DInput->EnumDevices(DIDEVTYPE_JOYSTICK, DInputEnumDevicesCallback, (LPVOID)joystickList, DIEDFL_ATTACHEDONLY)); +#endif } BOOL CALLBACK DInputEnumDevicesCallback(LPCDIDEVICEINSTANCE lpddi, LPVOID pvRef) { From 3161503ec975481e74ef0fc0eeceec4104d9ee31 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Thu, 26 May 2022 11:31:54 +0200 Subject: [PATCH 62/66] Update TR2_progress.txt --- TR2_progress.txt | 52 ++++++++++++++++++++++++------------------------ 1 file changed, 26 insertions(+), 26 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index af939a4..6accc85 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -121,7 +121,7 @@ x function is unused / included in another function 0x0040C8F0: * EagleControl game/boat.cpp -0x0040CB10: InitialiseBoat +0x0040CB10: * InitialiseBoat 0x0040CB50: BoatCheckGeton 0x0040CCC0: BoatCollision 0x0040CE20: TestWaterHeight @@ -131,7 +131,7 @@ x function is unused / included in another function 0x0040D2C0: BoatDynamics 0x0040D7A0: BoatUserControl 0x0040D930: BoatAnimation -0x0040DAA0: BoatControl +0x0040DAA0: * BoatControl 0x0040E0D0: + GondolaControl game/box.cpp @@ -213,24 +213,24 @@ x function is unused / included in another function game/control.cpp 0x00414370: + ControlPhase 0x004146C0: * AnimateItem -0x00414A30: GetChange -0x00414AE0: TranslateItem +0x00414A30: * GetChange +0x00414AE0: * TranslateItem 0x00414B40: * GetFloor 0x00414CE0: * GetWaterHeight 0x00414E50: * GetHeight -0x004150D0: RefreshCamera +0x004150D0: * RefreshCamera 0x004151C0: * TestTriggers 0x004158A0: * TriggerActive 0x00415900: * GetCeiling -0x00415B60: GetDoor +0x00415B60: * GetDoor 0x00415BB0: * LOS -0x00415C50: zLOS -0x00415F40: xLOS -0x00416230: ClipTarget -0x00416310: ObjectOnLOS +0x00415C50: * zLOS +0x00415F40: * xLOS +0x00416230: * ClipTarget +0x00416310: * ObjectOnLOS 0x00416610: * FlipMap -0x004166D0: RemoveRoomFlipItems -0x00416770: AddRoomFlipItems +0x004166D0: * RemoveRoomFlipItems +0x00416770: * AddRoomFlipItems 0x004167D0: + TriggerCDTrack 0x00416800: + TriggerNormalCDTrack @@ -250,7 +250,7 @@ x function is unused / included in another function 0x004174E0: * TigerControl game/dragon.cpp -0x00417780: ControlTwinkle +0x00417780: * ControlTwinkle 0x00417900: CreateBartoliLight 0x004179E0: DragonFire 0x00417A90: * DragonCollision @@ -737,7 +737,7 @@ x function is unused / included in another function 0x00432920: LaraWaterCurrent game/lot.cpp -0x00432B10: InitialiseLOTarray +0x00432B10: * InitialiseLOTarray 0x00432B70: * DisableBaddieAI 0x00432BC0: * EnableBaddieAI 0x00432D70: InitialiseSlot @@ -748,7 +748,7 @@ x function is unused / included in another function 0x00433090: + ControlMissile 0x00433360: ShootAtLara 0x00433410: * ExplodingDeath -0x004337A0: ControlBodyPart +0x004337A0: * ControlBodyPart game/moveblock.cpp 0x004339A0: * InitialiseMovingBlock @@ -804,8 +804,8 @@ x function is unused / included in another function game/people.cpp 0x00435EB0: Targetable -0x00435F40: ControlGlow -0x00435F80: ControlGunShot +0x00435F40: * ControlGlow +0x00435F80: * ControlGunShot 0x00435FD0: + GunShot 0x00436040: + GunHit 0x00436100: GunMiss @@ -822,16 +822,16 @@ x function is unused / included in another function game/pickup.cpp 0x00437F20: * PickUpCollision -0x004383A0: SwitchCollision -0x004385B0: SwitchCollision2 -0x004386B0: DetonatorCollision -0x004388F0: KeyHoleCollision +0x004383A0: * SwitchCollision +0x004385B0: * SwitchCollision2 +0x004386B0: * DetonatorCollision +0x004388F0: * KeyHoleCollision 0x00438B30: * PuzzleHoleCollision -0x00438DF0: SwitchControl +0x00438DF0: * SwitchControl 0x00438E30: SwitchTrigger 0x00438EF0: KeyTrigger 0x00438F30: PickupTrigger -0x00438F70: SecretControl +0x00438F70: * SecretControl game/rat.cpp 0x00438FA0: * MouseControl @@ -864,7 +864,7 @@ x function is unused / included in another function game/skidoo.cpp 0x0043CEE0: * InitialiseSkidoo 0x0043CF20: SkidooCheckGeton -0x0043D010: SkidooCollision +0x0043D010: * SkidooCollision 0x0043D110: SkidooBaddieCollision 0x0043D310: TestHeight 0x0043D3D0: DoShift @@ -878,7 +878,7 @@ x function is unused / included in another function 0x0043E2D0: + SkidooExplode 0x0043E350: SkidooCheckGetOff 0x0043E590: + SkidooGuns -0x0043E6B0: SkidooControl +0x0043E6B0: * SkidooControl 0x0043EB10: + DrawSkidoo 0x0043EDF0: * InitialiseSkidman 0x0043EE80: * SkidManControl @@ -895,7 +895,7 @@ x function is unused / included in another function game/sphere.cpp 0x0043FA60: * TestCollision -0x0043FB90: GetSpheres +0x0043FB90: * GetSpheres 0x0043FE70: + GetJointAbsPosition 0x00440010: + BaddieBiteEffect From 86556db94cb8d8980071e1f1f3956d77bfb3ef31 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Wed, 7 Dec 2022 13:05:46 +0100 Subject: [PATCH 63/66] Decompiled InitialiseCreature() - if cheat is enabled, when loading a level, you will get all weapons (only for debug dll !) also added mediapack (small&large) to the bonus game. --- game/box.cpp | 9 ++++++++- game/box.h | 2 +- game/savegame.cpp | 8 +++++++- 3 files changed, 16 insertions(+), 3 deletions(-) diff --git a/game/box.cpp b/game/box.cpp index 69d3580..e6c3205 100644 --- a/game/box.cpp +++ b/game/box.cpp @@ -27,6 +27,13 @@ #include "game/missile.h" #include "global/vars.h" +void __cdecl InitialiseCreature(__int16 itemID) { + ITEM_INFO *item = &Items[itemID]; + item->pos.rotY += (GetRandomControl() - 16384) >> 1; + item->collidable = 1; + item->data = NULL; +} + void __cdecl CreatureDie(__int16 itemID, BOOL explode) { ITEM_INFO *item = &Items[itemID]; item->collidable = 0; @@ -98,7 +105,7 @@ void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int lara * Inject function */ void Inject_Box() { -// INJECT(0x0040E190, InitialiseCreature); + INJECT(0x0040E190, InitialiseCreature); // INJECT(0x0040E1C0, CreatureActive); // INJECT(0x0040E210, CreatureAIInfo); // INJECT(0x0040E470, SearchLOT); diff --git a/game/box.h b/game/box.h index 5baf9fa..06f7898 100644 --- a/game/box.h +++ b/game/box.h @@ -27,7 +27,7 @@ /* * Function list */ -#define InitialiseCreature ((void(__cdecl*)(__int16)) 0x0040E190) +void __cdecl InitialiseCreature(__int16 itemID); // 0x0040E190 // 0x0040E1C0: CreatureActive diff --git a/game/savegame.cpp b/game/savegame.cpp index 056bd39..397b54d 100644 --- a/game/savegame.cpp +++ b/game/savegame.cpp @@ -137,8 +137,12 @@ void __cdecl ModifyStartInfo(int levelIdx) { break; } - // Bonus game activated and level is not Assault + // Bonus game activated and level is not Assault give all weapons or else if cheat enabled, give it by default. +#ifdef _DEBUG + if( (SaveGame.bonusFlag && levelIdx != 0) || CHK_ANY(GF_GameFlow.flags, GFF_DozyCheatEnabled) ) { +#else if( SaveGame.bonusFlag && levelIdx != 0 ) { +#endif // !_DEBUG start->available = 1; // make level available start->has_pistols = 1; // Lara has all weapons start->has_magnums = 1; @@ -156,6 +160,8 @@ void __cdecl ModifyStartInfo(int levelIdx) { start->grenadeAmmo = 10001; start->harpoonAmmo = 10001; + start->smallMedipacks = 255; + start->largeMedipacks = 255; start->flares = 255; } } From c743ae51b90b0cbc2085153e29780cb7bd6eccde Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Wed, 7 Dec 2022 13:38:28 +0100 Subject: [PATCH 64/66] Decompiled CreatureActive() --- game/box.cpp | 17 ++++++++++++++++- game/box.h | 2 +- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/game/box.cpp b/game/box.cpp index e6c3205..1af3ddc 100644 --- a/game/box.cpp +++ b/game/box.cpp @@ -25,6 +25,7 @@ #include "game/items.h" #include "game/lot.h" #include "game/missile.h" +#include "specific/game.h" #include "global/vars.h" void __cdecl InitialiseCreature(__int16 itemID) { @@ -34,6 +35,20 @@ void __cdecl InitialiseCreature(__int16 itemID) { item->data = NULL; } +BOOL __cdecl CreatureActive(__int16 itemID) { + ITEM_INFO *item = &Items[itemID]; + + if (CHK_ANY(item->status, ITEM_INVISIBLE)) { + BOOL isActive = EnableBaddieAI(itemID, FALSE); + if (isActive) { + item->status = ITEM_ACTIVE; + return TRUE; + } + } + + return CHK_ANY(item->status, ITEM_ACTIVE); +} + void __cdecl CreatureDie(__int16 itemID, BOOL explode) { ITEM_INFO *item = &Items[itemID]; item->collidable = 0; @@ -106,7 +121,7 @@ void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int lara */ void Inject_Box() { INJECT(0x0040E190, InitialiseCreature); -// INJECT(0x0040E1C0, CreatureActive); + INJECT(0x0040E1C0, CreatureActive); // INJECT(0x0040E210, CreatureAIInfo); // INJECT(0x0040E470, SearchLOT); // INJECT(0x0040E670, UpdateLOT); diff --git a/game/box.h b/game/box.h index 06f7898..b5d71e6 100644 --- a/game/box.h +++ b/game/box.h @@ -29,7 +29,7 @@ */ void __cdecl InitialiseCreature(__int16 itemID); // 0x0040E190 -// 0x0040E1C0: CreatureActive +BOOL __cdecl CreatureActive(__int16 itemID); // 0x0040E1C0 #define CreatureAIInfo ((void(__cdecl*)(ITEM_INFO *, AI_INFO *)) 0x0040E210) From 868063e0a34f0a3e2f436e30d36e84e626cf4ce7 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Wed, 7 Dec 2022 17:33:25 +0100 Subject: [PATCH 65/66] Decompiled CreatureAIInfo() --- game/box.cpp | 70 ++++++++++++++++++++++++++++++++++++++++++++++++++-- game/box.h | 4 +-- 2 files changed, 70 insertions(+), 4 deletions(-) diff --git a/game/box.cpp b/game/box.cpp index 1af3ddc..d5188a0 100644 --- a/game/box.cpp +++ b/game/box.cpp @@ -21,6 +21,7 @@ #include "global/precompiled.h" #include "game/box.h" +#include "3dsystem/phd_math.h" #include "game/control.h" #include "game/items.h" #include "game/lot.h" @@ -30,7 +31,7 @@ void __cdecl InitialiseCreature(__int16 itemID) { ITEM_INFO *item = &Items[itemID]; - item->pos.rotY += (GetRandomControl() - 16384) >> 1; + item->pos.rotY += (GetRandomControl() - PHD_90) >> 1; item->collidable = 1; item->data = NULL; } @@ -49,6 +50,71 @@ BOOL __cdecl CreatureActive(__int16 itemID) { return CHK_ANY(item->status, ITEM_ACTIVE); } +void __cdecl CreatureAIInfo(ITEM_INFO *item, AI_INFO *ai) { + CREATURE_INFO *creature = (CREATURE_INFO*)item->data; + if (creature == NULL) { + return; + } + + ITEM_INFO *enemy = NULL; + __int16 *zone = NULL; + + switch (item->objectID) { + case ID_BANDIT1: + case ID_BANDIT2: + GetBaddieTarget(creature->item_num, 0); + break; + case ID_MONK1: + case ID_MONK2: + GetBaddieTarget(creature->item_num, 1); + break; + default: + creature->enemy = LaraItem; + break; + } + + enemy = creature->enemy; + if (enemy == NULL) { + enemy = LaraItem; + } + + if (creature->LOT.fly != 0) { + zone = FlyZones[FlipStatus]; + } else { + zone = GroundZones[2 * (creature->LOT.step >> 8) + FlipStatus]; + } + + ROOM_INFO *roomSource = &RoomInfo[item->roomNumber]; + item->boxNumber = roomSource->floor[((item->pos.z - roomSource->z) >> WALL_SHIFT) + roomSource->xSize * ((item->pos.x - roomSource->x) >> WALL_SHIFT)].box; + ai->zone_number = zone[item->boxNumber]; + + ROOM_INFO *roomTarget = &RoomInfo[enemy->roomNumber]; + enemy->boxNumber = roomTarget->floor[((enemy->pos.z - roomTarget->z) >> WALL_SHIFT) + roomTarget->xSize * ((enemy->pos.x - roomTarget->x) >> WALL_SHIFT)].box; + ai->enemy_zone = zone[enemy->boxNumber]; + + if ( CHK_ANY(Boxes[enemy->boxNumber].overlapIndex, creature->LOT.block_mask) || creature->LOT.node[item->boxNumber].search_number == (creature->LOT.search_number | 0x8000) ) { + ai->enemy_zone |= 0x4000; + } + + OBJECT_INFO *obj = &Objects[item->objectID]; + int x = enemy->pos.x - ((obj->pivotLength * phd_cos(item->pos.rotY)) >> W2V_SHIFT) - item->pos.x; + int z = enemy->pos.z - ((obj->pivotLength * phd_sin(item->pos.rotY)) >> W2V_SHIFT) - item->pos.z; + int angle = phd_atan(z, x); + if (creature->enemy != NULL) { + ai->distance = SQR(x) + SQR(z); + } else { + ai->distance = 0x7FFFFFFF; + } + ai->angle = angle - item->pos.rotY; + ai->enemy_facing = angle - enemy->pos.rotY + PHD_180; + ai->ahead = angle > -PHD_90 && angle < PHD_90; + if (ai->ahead && enemy->hitPoints >= 0 && ABS(item->pos.y - enemy->pos.y) < 384) { + ai->bite = 1; + } else { + ai->bite = 0; + } +} + void __cdecl CreatureDie(__int16 itemID, BOOL explode) { ITEM_INFO *item = &Items[itemID]; item->collidable = 0; @@ -122,7 +188,7 @@ void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int lara void Inject_Box() { INJECT(0x0040E190, InitialiseCreature); INJECT(0x0040E1C0, CreatureActive); -// INJECT(0x0040E210, CreatureAIInfo); + INJECT(0x0040E210, CreatureAIInfo); // INJECT(0x0040E470, SearchLOT); // INJECT(0x0040E670, UpdateLOT); // INJECT(0x0040E6E0, TargetBox); diff --git a/game/box.h b/game/box.h index b5d71e6..21643b1 100644 --- a/game/box.h +++ b/game/box.h @@ -31,7 +31,7 @@ void __cdecl InitialiseCreature(__int16 itemID); // 0x0040E190 BOOL __cdecl CreatureActive(__int16 itemID); // 0x0040E1C0 -#define CreatureAIInfo ((void(__cdecl*)(ITEM_INFO *, AI_INFO *)) 0x0040E210) +void __cdecl CreatureAIInfo(ITEM_INFO *item, AI_INFO *ai); // 0x0040E210 // 0x0040E470: SearchLOT // 0x0040E670: UpdateLOT @@ -63,6 +63,6 @@ void __cdecl CreatureDie(__int16 itemID, BOOL explode); // 0x0040F440 void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int laraKillState); // 0x00410230 -// 0x004103A0: GetBaddieTarget +#define GetBaddieTarget ((void(__cdecl*)(__int16, int)) 0x004103A0) #endif // BOX_H_INCLUDED From 97dc4c9755b98ecb0b6b5809a8da1036ddb33c83 Mon Sep 17 00:00:00 2001 From: TokyoSU <77746747+TokyoSU@users.noreply.github.com> Date: Mon, 23 Jan 2023 21:19:50 +0100 Subject: [PATCH 66/66] Increased the count of creature to 16 - Removed InitialiseCreature(), CreatureActive(), CreatureAIInfo(). - Decompiled InitialiseLOTarray(), DisableBaddieAI(), EnableBaddieAI(), InitialiseSlot(), LaraGetNewTarget(). - Now you can have 16 creatures simultaneously in the level. - Wolf in TR2_GOLD could probably be stuck on wall (trying to climb) or fall 4 click (1 block), it's fixed now. --- TR2_progress.txt | 18 ++--- game/box.cpp | 80 ++++++++++++++++++++-- game/box.h | 13 ++-- game/larafire.cpp | 63 ++++++++++++++++- game/larafire.h | 2 +- game/lot.cpp | 167 ++++++++++++++++++++++++++++++++++++++++++++-- game/lot.h | 14 ++-- global/vars.h | 3 + 8 files changed, 324 insertions(+), 36 deletions(-) diff --git a/TR2_progress.txt b/TR2_progress.txt index 6accc85..5f05083 100644 --- a/TR2_progress.txt +++ b/TR2_progress.txt @@ -136,7 +136,7 @@ x function is unused / included in another function game/box.cpp 0x0040E190: * InitialiseCreature -0x0040E1C0: CreatureActive +0x0040E1C0: * CreatureActive 0x0040E210: * CreatureAIInfo 0x0040E470: SearchLOT 0x0040E670: UpdateLOT @@ -159,7 +159,7 @@ x function is unused / included in another function 0x00410090: * CreatureEffect 0x004100F0: CreatureVault 0x00410230: + CreatureKill -0x004103A0: GetBaddieTarget +0x004103A0: + GetBaddieTarget game/camera.cpp 0x00410580: + InitialiseCamera @@ -668,7 +668,7 @@ x function is unused / included in another function 0x0042ECB0: * CheckForHoldingState 0x0042ECF0: * InitialiseNewWeapon 0x0042EE30: * LaraTargetInfo -0x0042EFD0: * LaraGetNewTarget +0x0042EFD0: + LaraGetNewTarget 0x0042F1F0: * find_target_point 0x0042F2A0: * AimWeapon 0x0042F370: * FireWeapon @@ -737,12 +737,12 @@ x function is unused / included in another function 0x00432920: LaraWaterCurrent game/lot.cpp -0x00432B10: * InitialiseLOTarray -0x00432B70: * DisableBaddieAI -0x00432BC0: * EnableBaddieAI -0x00432D70: InitialiseSlot -0x00432F80: CreateZone -0x00433040: ClearLOT +0x00432B10: + InitialiseLOTarray +0x00432B70: + DisableBaddieAI +0x00432BC0: + EnableBaddieAI +0x00432D70: + InitialiseSlot +0x00432F80: * CreateZone +0x00433040: * ClearLOT game/missile.cpp 0x00433090: + ControlMissile diff --git a/game/box.cpp b/game/box.cpp index d5188a0..548fc10 100644 --- a/game/box.cpp +++ b/game/box.cpp @@ -29,7 +29,7 @@ #include "specific/game.h" #include "global/vars.h" -void __cdecl InitialiseCreature(__int16 itemID) { +/*void __cdecl InitialiseCreature(__int16 itemID) { ITEM_INFO *item = &Items[itemID]; item->pos.rotY += (GetRandomControl() - PHD_90) >> 1; item->collidable = 1; @@ -113,7 +113,7 @@ void __cdecl CreatureAIInfo(ITEM_INFO *item, AI_INFO *ai) { } else { ai->bite = 0; } -} +}*/ void __cdecl CreatureDie(__int16 itemID, BOOL explode) { ITEM_INFO *item = &Items[itemID]; @@ -182,13 +182,80 @@ void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int lara Camera.pos.roomNumber = LaraItem->roomNumber; } +void __cdecl GetBaddieTarget(__int16 itemNum, int flags) { + ITEM_INFO *item = &Items[itemNum], *target = NULL, *bestItem = NULL; + CREATURE_INFO *creature = (CREATURE_INFO*)item->data, *creatureFound = NULL; + int bestDistance = 0x7FFFFFFF, distance = 0; + int x, y, z; + + for (int i = 0; i < MAXIMUM_CREATURE_SLOTS; i++) { + creatureFound = &ActiveCreatures[i]; + if (creatureFound->item_num == -1 || creatureFound->item_num == itemNum) + continue; + target = &Items[creatureFound->item_num]; + switch (flags) { + case 1: // MONK + if (target->objectID != ID_BANDIT1 && target->objectID != ID_BANDIT2) + continue; + break; + case 0: // BANDIT (Mercenary) + if (target->objectID != ID_MONK1 && target->objectID != ID_MONK2) + continue; + break; + default: + continue; + } + x = (target->pos.x - item->pos.x) >> 6; + y = (target->pos.y - item->pos.y) >> 6; + z = (target->pos.z - item->pos.z) >> 6; + distance = SQR(z) + SQR(y) + SQR(x); + if (distance < bestDistance) { + bestItem = target; + bestDistance = distance; + } + } + + if (bestItem == NULL) { + if (flags == 0 || MonksAttackLara) { + creature->enemy = LaraItem; + } else { + creature->enemy = NULL; + } + return; + } + + if (flags == 0 || MonksAttackLara) { + x = (LaraItem->pos.x - item->pos.x) >> 6; + y = (LaraItem->pos.y - item->pos.y) >> 6; + z = (LaraItem->pos.z - item->pos.z) >> 6; + distance = SQR(z) + SQR(y) + SQR(x); + if (distance < bestDistance) { + bestItem = LaraItem; + bestDistance = distance; + } + } + + target = creature->enemy; + if (target != NULL && target->status == ITEM_ACTIVE) { + x = (target->pos.x - item->pos.x) >> 6; + y = (target->pos.y - item->pos.y) >> 6; + z = (target->pos.z - item->pos.z) >> 6; + distance = SQR(z) + SQR(y) + SQR(x); + if (distance < (bestDistance + 0x400000)) { + creature->enemy = bestItem; + } + } else { + creature->enemy = bestItem; + } +} + /* * Inject function */ void Inject_Box() { - INJECT(0x0040E190, InitialiseCreature); - INJECT(0x0040E1C0, CreatureActive); - INJECT(0x0040E210, CreatureAIInfo); +// INJECT(0x0040E190, InitialiseCreature); +// INJECT(0x0040E1C0, CreatureActive); +// INJECT(0x0040E210, CreatureAIInfo); // INJECT(0x0040E470, SearchLOT); // INJECT(0x0040E670, UpdateLOT); // INJECT(0x0040E6E0, TargetBox); @@ -213,6 +280,5 @@ void Inject_Box() { // INJECT(0x004100F0, CreatureVault); INJECT(0x00410230, CreatureKill); - -// INJECT(0x004103A0, GetBaddieTarget); + INJECT(0x004103A0, GetBaddieTarget); } diff --git a/game/box.h b/game/box.h index 21643b1..6128c4a 100644 --- a/game/box.h +++ b/game/box.h @@ -27,11 +27,10 @@ /* * Function list */ -void __cdecl InitialiseCreature(__int16 itemID); // 0x0040E190 -BOOL __cdecl CreatureActive(__int16 itemID); // 0x0040E1C0 - -void __cdecl CreatureAIInfo(ITEM_INFO *item, AI_INFO *ai); // 0x0040E210 +#define InitialiseCreature ((void(__cdecl*)(__int16)) 0x0040E190) +#define CreatureActive ((BOOL(__cdecl*)(__int16)) 0x0040E1C0) +#define CreatureAIInfo ((void(__cdecl*)(ITEM_INFO*,AI_INFO*)) 0x0040E210) // 0x0040E470: SearchLOT // 0x0040E670: UpdateLOT @@ -40,7 +39,7 @@ void __cdecl CreatureAIInfo(ITEM_INFO *item, AI_INFO *ai); // 0x0040E210 // 0x0040E880: EscapeBox // 0x0040E930: ValidBox -#define CreatureMood ((void(__cdecl*)(ITEM_INFO *, AI_INFO *, BOOL)) 0x0040E9E0) +#define CreatureMood ((void(__cdecl*)(ITEM_INFO*, AI_INFO*, BOOL)) 0x0040E9E0) // 0x0040EE50: CalculateTarget // 0x0040F2B0: CreatureCreature @@ -62,7 +61,7 @@ void __cdecl CreatureDie(__int16 itemID, BOOL explode); // 0x0040F440 // 0x004100F0: CreatureVault void __cdecl CreatureKill(ITEM_INFO *item, int killAnim, int killState, int laraKillState); // 0x00410230 - -#define GetBaddieTarget ((void(__cdecl*)(__int16, int)) 0x004103A0) +// NOTE: 1 = Monk, 0 = Bandit +void __cdecl GetBaddieTarget(__int16 itemNum, int flags); // 0x004103A0 #endif // BOX_H_INCLUDED diff --git a/game/larafire.cpp b/game/larafire.cpp index 3a8b884..deed1d0 100644 --- a/game/larafire.cpp +++ b/game/larafire.cpp @@ -21,9 +21,68 @@ #include "global/precompiled.h" #include "game/larafire.h" +#include "3dsystem/3d_gen.h" +#include "game/control.h" +#include "game/lot.h" #include "global/vars.h" +void __cdecl LaraGetNewTarget(WEAPON_INFO* weapon) { + GAME_VECTOR start, target; + CREATURE_INFO *creature = NULL; + ITEM_INFO *bestItem = NULL, *item = NULL; + int distance; + int bestDistance = 0x7FFFFFFF; + int maxDistance = weapon->targetDist; + int sqrMaxDistance = SQR(maxDistance); + int x, y, z; + VECTOR_ANGLES angles; + __int16 bestYRot = 0x7FFF, yRot; + start.x = LaraItem->pos.x; + start.y = LaraItem->pos.y - 650; + start.z = LaraItem->pos.z; + start.roomNumber = LaraItem->roomNumber; + + for (int i = 0; i < MAXIMUM_CREATURE_SLOTS; i++) { + creature = &ActiveCreatures[i]; + if (creature->item_num != -1 && creature->item_num != Lara.item_number) { + item = &Items[creature->item_num]; + if (item->hitPoints <= 0) + continue; + x = item->pos.x - start.x; + y = item->pos.y - start.y; + z = item->pos.z - start.z; + if ((ABS(x) > maxDistance) || + (ABS(y) > maxDistance) || + (ABS(z) > maxDistance)) + continue; + distance = SQR(z) + SQR(y) + SQR(x); + if (distance < sqrMaxDistance) { + find_target_point(item, &target); + + if (LOS(&start, &target)) { + phd_GetVectorAngles(target.x - start.x, target.y - start.y, target.z - start.z, &angles); + angles.yaw -= LaraItem->pos.rotY + Lara.torso_y_rot; + angles.pitch -= LaraItem->pos.rotX + Lara.torso_x_rot; + if (angles.yaw >= weapon->lockAngles[0] && + angles.yaw <= weapon->lockAngles[1] && + angles.pitch >= weapon->lockAngles[2] && + angles.pitch <= weapon->lockAngles[3]) { + yRot = ABS(angles.yaw); + if (yRot < (bestYRot + 2730) && distance < bestDistance) { + bestDistance = distance; + bestYRot = yRot; + bestItem = item; + } + } + } + } + } + } + + Lara.target = bestItem; + LaraTargetInfo(weapon); +} /* * Inject function @@ -33,11 +92,11 @@ void Inject_LaraFire() { // INJECT(0x0042ECB0, CheckForHoldingState); // INJECT(0x0042ECF0, InitialiseNewWeapon); // INJECT(0x0042EE30, LaraTargetInfo); -// INJECT(0x0042EFD0, LaraGetNewTarget); + INJECT(0x0042EFD0, LaraGetNewTarget); // INJECT(0x0042F1F0, find_target_point); // INJECT(0x0042F2A0, AimWeapon); // INJECT(0x0042F370, FireWeapon); // INJECT(0x0042F6E0, HitTarget); // INJECT(0x0042F780, SmashItem); // INJECT(0x0042F7E0, WeaponObject); -} \ No newline at end of file +} diff --git a/game/larafire.h b/game/larafire.h index 9d5cce3..32de751 100644 --- a/game/larafire.h +++ b/game/larafire.h @@ -31,7 +31,7 @@ #define CheckForHoldingState ((int(__cdecl*)(int)) 0x0042ECB0) #define InitialiseNewWeapon ((void(__cdecl*)(void)) 0x0042ECF0) #define LaraTargetInfo ((void(__cdecl*)(WEAPON_INFO*)) 0x0042EE30) -#define LaraGetNewTarget ((void(__cdecl*)(WEAPON_INFO*)) 0x0042EFD0) +void __cdecl LaraGetNewTarget(WEAPON_INFO* weapon); // 0x0042EFD0 #define find_target_point ((void(__cdecl*)(ITEM_INFO*,GAME_VECTOR*)) 0x0042F1F0) #define AimWeapon ((void(__cdecl*)(WEAPON_INFO*,LARA_ARM*)) 0x0042F2A0) #define FireWeapon ((int(__cdecl*)(int,ITEM_INFO*,ITEM_INFO*,__int16*)) 0x0042F370) diff --git a/game/lot.cpp b/game/lot.cpp index 0a411f2..67ec371 100644 --- a/game/lot.cpp +++ b/game/lot.cpp @@ -21,18 +21,177 @@ #include "global/precompiled.h" #include "game/lot.h" +#include "specific/init.h" #include "global/vars.h" +#ifdef FEATURE_GOLD +extern bool IsGold(); +#endif +void __cdecl InitialiseLOTarray() { + ActiveCreatures = (CREATURE_INFO*)game_malloc(MAXIMUM_CREATURE_SLOTS * sizeof(CREATURE_INFO), GBUF_CreatureData); + for (int i = 0; i < MAXIMUM_CREATURE_SLOTS; i++) { + CREATURE_INFO *creature = &ActiveCreatures[i]; + creature->item_num = -1; + creature->LOT.node = (BOX_NODE*)game_malloc(sizeof(BOX_NODE) * BoxesCount, GBUF_CreatureLOT); + } + ActiveCreaturesUsed = 0; +} + +void __cdecl DisableBaddieAI(__int16 itemNum) { + CREATURE_INFO *creature = NULL; + ITEM_INFO *item = &Items[itemNum]; + + if (itemNum == Lara.item_number) { + creature = Lara.creature; + Lara.creature = NULL; + } else { + creature = (CREATURE_INFO*)item->data; + item->data = NULL; + } + + if (creature != NULL) { + creature->item_num = -1; + ActiveCreaturesUsed--; + } +} + +BOOL __cdecl EnableBaddieAI(__int16 itemNum, BOOL always) { + if (itemNum == Lara.item_number && Lara.creature != NULL) + return TRUE; + + ITEM_INFO *item = &Items[itemNum]; + if (item->data != NULL) + return TRUE; + + CREATURE_INFO *creature = NULL; + if (ActiveCreaturesUsed >= MAXIMUM_CREATURE_SLOTS) { + int x, y, z; + int distance, bestdistance, slot = -1; + if (!always) { + item = &Items[itemNum]; + x = (item->pos.x - Camera.pos.x) >> 8; + y = (item->pos.y - Camera.pos.y) >> 8; + z = (item->pos.z - Camera.pos.z) >> 8; + bestdistance = SQR(x) + SQR(y) + SQR(z); + } else { + bestdistance = 0; + } + + for (int i = 0; i < MAXIMUM_CREATURE_SLOTS; i++) { + item = &Items[ActiveCreatures[i].item_num]; + x = (item->pos.x - Camera.pos.x) >> 8; + y = (item->pos.y - Camera.pos.y) >> 8; + z = (item->pos.z - Camera.pos.z) >> 8; + distance = SQR(x) + SQR(y) + SQR(z); + if (distance > bestdistance) { + bestdistance = distance; + slot = i; + } + } + + if (slot >= 0 && slot < MAXIMUM_CREATURE_SLOTS) { + creature = &ActiveCreatures[slot]; + item = &Items[creature->item_num]; + item->status = ITEM_INVISIBLE; + DisableBaddieAI(creature->item_num); + InitialiseSlot(itemNum, slot); + return TRUE; + } + } else { + for (int i = 0; i < MAXIMUM_CREATURE_SLOTS; i++) { + creature = &ActiveCreatures[i]; + if (creature->item_num == -1) { + InitialiseSlot(itemNum, i); + return TRUE; + } + } + } + + return FALSE; +} + +void __cdecl InitialiseSlot(__int16 itemNum, int creatureNum) { + CREATURE_INFO *creature = &ActiveCreatures[creatureNum]; + ITEM_INFO *item = &Items[itemNum]; + + if (itemNum == Lara.item_number) + Lara.creature = creature; + else + item->data = creature; + creature->item_num = itemNum; + creature->mood = MOOD_BORED; + creature->neck_rotation = 0; + creature->head_rotation = 0; + creature->maximum_turn = PHD_DEGREE; + creature->flags = 0; + creature->enemy = NULL; + creature->LOT.step = 256; + creature->LOT.drop = -512; + creature->LOT.block_mask = 0x8000; + creature->LOT.fly = 0; + + switch (item->objectID) { + case ID_LARA: + creature->LOT.step = 20480; + creature->LOT.drop = -20480; + creature->LOT.fly = 256; + break; + case ID_SHARK: + case ID_BARRACUDA: + case ID_DIVER: + case ID_JELLY: + case ID_CROW: + case ID_EAGLE: + creature->LOT.step = 20480; + creature->LOT.drop = -20480; + creature->LOT.fly = 16; + if (item->objectID == ID_SHARK) + creature->LOT.block_mask = 0x8000; + break; + case ID_WORKER3: + case ID_WORKER4: + case ID_YETI: + creature->LOT.step = 1024; + creature->LOT.drop = -1024; + break; +#ifdef FEATURE_GOLD + case ID_SPIDER_or_WOLF: // NOTE: don't include wolf since he not climb ! + if (!IsGold()) { + creature->LOT.step = 512; + creature->LOT.drop = -1024; + } + break; + case ID_SKIDOO_ARMED: + creature->LOT.step = 512; + creature->LOT.drop = -1024; + break; +#else + case ID_SPIDER_or_WOLF: + case ID_SKIDOO_ARMED: + creature->LOT.step = 512; + creature->LOT.drop = -1024; + break; +#endif + case ID_DINO: + creature->LOT.block_mask = 0x8000; + break; + } + + ClearLOT(&creature->LOT); + if (itemNum != Lara.item_number) + CreateZone(item); + ActiveCreaturesUsed++; +} /* * Inject function */ void Inject_Lot() { -// INJECT(0x00432B10, InitialiseLOTarray); -// INJECT(0x00432B70, DisableBaddieAI); -// INJECT(0x00432BC0, EnableBaddieAI); -// INJECT(0x00432D70, InitialiseSlot); + INJECT(0x00432B10, InitialiseLOTarray); + INJECT(0x00432B70, DisableBaddieAI); + INJECT(0x00432BC0, EnableBaddieAI); + INJECT(0x00432D70, InitialiseSlot); // INJECT(0x00432F80, CreateZone); // INJECT(0x00433040, ClearLOT); } diff --git a/game/lot.h b/game/lot.h index 9ac03bb..702960c 100644 --- a/game/lot.h +++ b/game/lot.h @@ -24,15 +24,17 @@ #include "global/types.h" +#define MAXIMUM_CREATURE_SLOTS 16 + /* * Function list */ -#define InitialiseLOTarray ((void(__cdecl*)(void)) 0x00432B10) -#define DisableBaddieAI ((void(__cdecl*)(__int16)) 0x00432B70) -#define EnableBaddieAI ((int(__cdecl*)(__int16, BOOL)) 0x00432BC0) -// 0x00432D70: InitialiseSlot -// 0x00432F80: CreateZone -// 0x00433040: ClearLOT +void __cdecl InitialiseLOTarray(); // 0x00432B10 +void __cdecl DisableBaddieAI(__int16 itemNum); // 0x00432B70 +BOOL __cdecl EnableBaddieAI(__int16 itemNum, BOOL always); // 0x00432BC0 +void __cdecl InitialiseSlot(__int16 itemNum, int creatureNum); // 0x00432D70 +#define CreateZone ((void(__cdecl*)(ITEM_INFO*)) 0x00432F80) +#define ClearLOT ((void(__cdecl*)(LOT_INFO*)) 0x00433040) #endif // LOT_H_INCLUDED diff --git a/global/vars.h b/global/vars.h index d8f4cf1..507542f 100644 --- a/global/vars.h +++ b/global/vars.h @@ -422,6 +422,9 @@ extern APP_SETTINGS SavedAppSettings; #define IMPtr VAR_U_(0x00526188, PHD_MATRIX*) #define IMStack ARRAY_(0x005252C0, PHD_MATRIX, [32]) #define InterpolateBounds ARRAY_(0x005261A0, __int16, [6]) +#define ActiveCreatures VAR_U_(0x005206C0, CREATURE_INFO*) +#define ActiveCreaturesUsed VAR_U_(0x004D7C40, int) +#define MonksAttackLara VAR_U_(0x004D77D8, BOOL) // Initialized arrays #define TrackIDs ARRAY_(0x004642F0, __int16, [16]) /* = {2, 0}; */