summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/SurfaceTable.cpp53
-rw-r--r--src/SurfaceTable.h6
-rw-r--r--src/audio/DMAudio.cpp5
-rw-r--r--src/audio/DMAudio.h9
-rw-r--r--src/control/CarCtrl.cpp5
-rw-r--r--src/control/CarCtrl.h9
-rw-r--r--src/entities/Physical.cpp398
-rw-r--r--src/entities/Physical.h11
8 files changed, 397 insertions, 99 deletions
diff --git a/src/SurfaceTable.cpp b/src/SurfaceTable.cpp
index e9ef459a..107734e4 100644
--- a/src/SurfaceTable.cpp
+++ b/src/SurfaceTable.cpp
@@ -1,7 +1,11 @@
#include "common.h"
#include "patcher.h"
+#include "Weather.h"
+#include "Collision.h"
#include "SurfaceTable.h"
+float (*CSurfaceTable::ms_aAdhesiveLimitTable)[NUMADHESIVEGROUPS] = (float (*)[NUMADHESIVEGROUPS])0x8E29D4;
+
int
CSurfaceTable::GetAdhesionGroup(uint8 surfaceType)
{
@@ -42,3 +46,52 @@ CSurfaceTable::GetAdhesionGroup(uint8 surfaceType)
default: return ADHESIVE_ROAD;
}
}
+
+float
+CSurfaceTable::GetWetMultiplier(uint8 surfaceType)
+{
+ switch(surfaceType){
+ case SURFACE_0:
+ case SURFACE_1:
+ case SURFACE_4:
+ case SURFACE_5:
+ case SURFACE_8:
+ case SURFACE_20:
+ case SURFACE_21:
+ case SURFACE_22:
+ case SURFACE_25:
+ case SURFACE_30:
+ case SURFACE_31:
+ return 1.0f - CWeather::WetRoads*0.25f;
+
+ case SURFACE_2:
+ case SURFACE_6:
+ case SURFACE_7:
+ case SURFACE_9:
+ case SURFACE_10:
+ case SURFACE_11:
+ case SURFACE_12:
+ case SURFACE_13:
+ case SURFACE_14:
+ case SURFACE_15:
+ case SURFACE_16:
+ case SURFACE_17:
+ case SURFACE_23:
+ case SURFACE_24:
+ case SURFACE_26:
+ case SURFACE_27:
+ case SURFACE_28:
+ case SURFACE_29:
+ case SURFACE_32:
+ return 1.0f - CWeather::WetRoads*0.4f;
+
+ default:
+ return 1.0f;
+ }
+}
+
+float
+CSurfaceTable::GetAdhesiveLimit(CColPoint &colpoint)
+{
+ return ms_aAdhesiveLimitTable[GetAdhesionGroup(colpoint.surfaceB)][GetAdhesionGroup(colpoint.surfaceA)];
+}
diff --git a/src/SurfaceTable.h b/src/SurfaceTable.h
index 556a6e04..f1ef3002 100644
--- a/src/SurfaceTable.h
+++ b/src/SurfaceTable.h
@@ -92,8 +92,14 @@ enum
NUMADHESIVEGROUPS
};
+struct CColPoint;
+
class CSurfaceTable
{
+// static float ms_aAdhesiveLimitTable[NUMADHESIVEGROUPS][NUMADHESIVEGROUPS];
+ static float (*ms_aAdhesiveLimitTable)[NUMADHESIVEGROUPS];
public:
static int GetAdhesionGroup(uint8 surfaceType);
+ static float GetWetMultiplier(uint8 surfaceType);
+ static float GetAdhesiveLimit(CColPoint &colpoint);
};
diff --git a/src/audio/DMAudio.cpp b/src/audio/DMAudio.cpp
new file mode 100644
index 00000000..cc8d4e8b
--- /dev/null
+++ b/src/audio/DMAudio.cpp
@@ -0,0 +1,5 @@
+#include "common.h"
+#include "patcher.h"
+#include "DMAudio.h"
+
+WRAPPER void cDMAudio::ReportCollision(CEntity *A, CEntity *B, uint8 surfA, uint8 surfB, float impulse, float speed) { EAXJMP(0x161684); }
diff --git a/src/audio/DMAudio.h b/src/audio/DMAudio.h
new file mode 100644
index 00000000..8d49be27
--- /dev/null
+++ b/src/audio/DMAudio.h
@@ -0,0 +1,9 @@
+#pragma once
+
+class CEntity;
+
+class cDMAudio
+{
+public:
+ static void ReportCollision(CEntity *A, CEntity *B, uint8 surfA, uint8 surfB, float impulse, float speed);
+};
diff --git a/src/control/CarCtrl.cpp b/src/control/CarCtrl.cpp
new file mode 100644
index 00000000..54491cd2
--- /dev/null
+++ b/src/control/CarCtrl.cpp
@@ -0,0 +1,5 @@
+#include "common.h"
+#include "patcher.h"
+#include "CarCtrl.h"
+
+WRAPPER void CCarCtrl::SwitchVehicleToRealPhysics(CVehicle*) { EAXJMP(0x41F7F0); } \ No newline at end of file
diff --git a/src/control/CarCtrl.h b/src/control/CarCtrl.h
new file mode 100644
index 00000000..fbe36f28
--- /dev/null
+++ b/src/control/CarCtrl.h
@@ -0,0 +1,9 @@
+#pragma once
+
+class CVehicle;
+
+class CCarCtrl
+{
+public:
+ static void SwitchVehicleToRealPhysics(CVehicle*);
+};
diff --git a/src/entities/Physical.cpp b/src/entities/Physical.cpp
index c528444e..947ac47c 100644
--- a/src/entities/Physical.cpp
+++ b/src/entities/Physical.cpp
@@ -10,6 +10,8 @@
#include "ParticleObject.h"
#include "Particle.h"
#include "SurfaceTable.h"
+#include "CarCtrl.h"
+#include "DMAudio.h"
#include "Physical.h"
void
@@ -171,6 +173,145 @@ CPhysical::RemoveFromMovingList(void)
}
}
+void
+CPhysical::SetDamagedPieceRecord(uint16 piece, float impulse, CEntity *entity, CVector dir)
+{
+ m_nCollisionPieceType = piece;
+ m_fCollisionImpulse = impulse;
+ m_pCollidingEntity = entity;
+ entity->RegisterReference(&m_pCollidingEntity);
+ m_vecCollisionDirection = dir;
+}
+
+void
+CPhysical::AddCollisionRecord(CEntity *ent)
+{
+ AddCollisionRecord_Treadable(ent);
+ this->bHasCollided = true;
+ ent->bHasCollided = true;
+ if(IsVehicle() && ent->IsVehicle()){
+ if(((CVehicle*)this)->m_nAlarmState == -1)
+ ((CVehicle*)this)->m_nAlarmState = 15000;
+ if(((CVehicle*)ent)->m_nAlarmState == -1)
+ ((CVehicle*)ent)->m_nAlarmState = 15000;
+ }
+ if(bUseCollisionRecords){
+ int i;
+ for(i = 0; i < m_nCollisionRecords; i++)
+ if(m_aCollisionRecords[i] == ent)
+ return;
+ if(m_nCollisionRecords < PHYSICAL_MAX_COLLISIONRECORDS)
+ m_aCollisionRecords[m_nCollisionRecords++] = ent;
+ m_nLastTimeCollided = CTimer::GetTimeInMilliseconds();
+ }
+}
+
+void
+CPhysical::AddCollisionRecord_Treadable(CEntity *ent)
+{
+ if(ent->IsBuilding() && ((CBuilding*)ent)->GetIsATreadable()){
+ CTreadable *t = (CTreadable*)ent;
+ if(t->m_nodeIndicesPeds[0] >= 0 ||
+ t->m_nodeIndicesPeds[1] >= 0 ||
+ t->m_nodeIndicesPeds[2] >= 0 ||
+ t->m_nodeIndicesPeds[3] >= 0)
+ m_pedTreadable = t;
+ if(t->m_nodeIndicesCars[0] >= 0 ||
+ t->m_nodeIndicesCars[1] >= 0 ||
+ t->m_nodeIndicesCars[2] >= 0 ||
+ t->m_nodeIndicesCars[3] >= 0)
+ m_carTreadable = t;
+ }
+}
+
+bool
+CPhysical::GetHasCollidedWith(CEntity *ent)
+{
+ int i;
+ if(bUseCollisionRecords)
+ for(i = 0; i < m_nCollisionRecords; i++)
+ if(m_aCollisionRecords[i] == ent)
+ return true;
+ return false;
+}
+
+void
+CPhysical::RemoveRefsToEntity(CEntity *ent)
+{
+ int i, j;
+
+ for(i = 0; i < m_nCollisionRecords; i++){
+ if(m_aCollisionRecords[i] == ent){
+ for(j = i; j < m_nCollisionRecords-1; j++)
+ m_aCollisionRecords[j] = m_aCollisionRecords[j+1];
+ m_nCollisionRecords--;
+ }
+ }
+}
+
+int32
+CPhysical::ProcessEntityCollision(CEntity *ent, CColPoint *colpoints)
+{
+ int32 numSpheres = CCollision::ProcessColModels(
+ GetMatrix(), *CModelInfo::GetModelInfo(GetModelIndex())->GetColModel(),
+ ent->GetMatrix(), *CModelInfo::GetModelInfo(ent->GetModelIndex())->GetColModel(),
+ colpoints,
+ nil, nil); // No Lines allowed!
+ if(numSpheres > 0){
+ AddCollisionRecord(ent);
+ if(!ent->IsBuilding()) // Can't this catch dummies too?
+ ((CPhysical*)ent)->AddCollisionRecord(this);
+ if(ent->IsBuilding() || ent->bIsStatic)
+ this->bHasHitWall = true;
+ }
+ return numSpheres;
+}
+
+void
+CPhysical::ProcessControl(void)
+{
+ if(!IsPed())
+ m_phy_flagA8 = false;
+ bHasContacted = false;
+ bIsInSafePosition = false;
+ bWasPostponed = false;
+ bHasHitWall = false;
+
+ if(m_status == STATUS_SIMPLE)
+ return;
+
+ m_nCollisionRecords = 0;
+ bHasCollided = false;
+ m_nCollisionPieceType = 0;
+ m_fCollisionImpulse = 0.0f;
+ m_pCollidingEntity = nil;
+
+ if(!bIsStuck){
+ if(IsObject() ||
+ IsPed() && !bPedPhysics){
+ m_vecMoveSpeedAvg = (m_vecMoveSpeedAvg + m_vecMoveSpeed)/2.0f;
+ m_vecTurnSpeedAvg = (m_vecTurnSpeedAvg + m_vecTurnSpeed)/2.0f;
+ float step = CTimer::GetTimeStep() * 0.003;
+ if(m_vecMoveSpeedAvg.MagnitudeSqr() < step*step &&
+ m_vecTurnSpeedAvg.MagnitudeSqr() < step*step){
+ m_nStaticFrames++;
+ if(m_nStaticFrames > 10){
+ m_nStaticFrames = 10;
+ bIsStatic = true;
+ m_vecMoveSpeed = CVector(0.0f, 0.0f, 0.0f);
+ m_vecTurnSpeed = CVector(0.0f, 0.0f, 0.0f);
+ m_vecMoveFriction = m_vecMoveSpeed;
+ m_vecTurnFriction = m_vecTurnSpeed;
+ return;
+ }
+ }else
+ m_nStaticFrames = 0;
+ }
+ }
+ ApplyGravity();
+ ApplyFriction();
+ ApplyAirResistance();
+}
/*
* Some quantities (german in parens):
@@ -245,8 +386,8 @@ CPhysical::ApplySpringCollision(float f1, CVector &v, CVector &p, float f2, floa
return;
float step = min(CTimer::GetTimeStep(), 3.0f);
float strength = -0.008f*m_fMass*2.0f*step * f1 * (1.0f-f2) * f3;
- ApplyMoveForce(v.x*strength, v.y*strength, v.z*strength);
- ApplyTurnForce(v.x*strength, v.y*strength, v.z*strength, p.x, p.y, p.z);
+ ApplyMoveForce(v*strength);
+ ApplyTurnForce(v*strength, p);
}
void
@@ -798,58 +939,6 @@ CPhysical::ApplyFriction(float adhesiveLimit, CColPoint &colpoint)
// ProcessCollisionSectorList
// ProcessShiftSectorList
-void
-CPhysical::AddCollisionRecord(CEntity *ent)
-{
- AddCollisionRecord_Treadable(ent);
- this->bHasCollided = true;
- ent->bHasCollided = true;
- if(IsVehicle() && ent->IsVehicle()){
- if(((CVehicle*)this)->m_nAlarmState == -1)
- ((CVehicle*)this)->m_nAlarmState = 15000;
- if(((CVehicle*)ent)->m_nAlarmState == -1)
- ((CVehicle*)ent)->m_nAlarmState = 15000;
- }
- if(bUseCollisionRecords){
- int i;
- for(i = 0; i < m_nCollisionRecords; i++)
- if(m_aCollisionRecords[i] == ent)
- return;
- if(m_nCollisionRecords < PHYSICAL_MAX_COLLISIONRECORDS)
- m_aCollisionRecords[m_nCollisionRecords++] = ent;
- m_nLastTimeCollided = CTimer::GetTimeInMilliseconds();
- }
-}
-
-void
-CPhysical::AddCollisionRecord_Treadable(CEntity *ent)
-{
- if(ent->IsBuilding() && ((CBuilding*)ent)->GetIsATreadable()){
- CTreadable *t = (CTreadable*)ent;
- if(t->m_nodeIndicesPeds[0] >= 0 ||
- t->m_nodeIndicesPeds[1] >= 0 ||
- t->m_nodeIndicesPeds[2] >= 0 ||
- t->m_nodeIndicesPeds[3] >= 0)
- m_pedTreadable = t;
- if(t->m_nodeIndicesCars[0] >= 0 ||
- t->m_nodeIndicesCars[1] >= 0 ||
- t->m_nodeIndicesCars[2] >= 0 ||
- t->m_nodeIndicesCars[3] >= 0)
- m_carTreadable = t;
- }
-}
-
-bool
-CPhysical::GetHasCollidedWith(CEntity *ent)
-{
- int i;
- if(bUseCollisionRecords)
- for(i = 0; i < m_nCollisionRecords; i++)
- if(m_aCollisionRecords[i] == ent)
- return true;
- return false;
-}
-
bool
CPhysical::ProcessShiftSectorList(CPtrList *lists)
{
@@ -1012,65 +1101,181 @@ CPhysical::ProcessShiftSectorList(CPtrList *lists)
return true;
}
-void
-CPhysical::ProcessControl(void)
+bool
+CPhysical::ProcessCollisionSectorList_SimpleCar(CPtrList *lists)
{
- if(!IsPed())
- m_phy_flagA8 = false;
- bHasContacted = false;
- bIsInSafePosition = false;
- bWasPostponed = false;
- bHasHitWall = false;
+ static CColPoint aColPoints[32];
+ float radius;
+ CVector center;
+ int listtype;
+ CPhysical *A, *B;
+ int numCollisions;
+ int i;
+ float impulseA = -1.0f;
+ float impulseB = -1.0f;
- if(m_status == STATUS_SIMPLE)
- return;
+ A = (CPhysical*)this;
- m_nCollisionRecords = 0;
- bHasCollided = false;
- m_nCollisionPieceType = 0;
- m_fCollisionImpulse = 0.0f;
- m_pCollidingEntity = nil;
+ radius = A->GetBoundRadius();
+ A->GetBoundCentre(center);
- if(!bIsStuck){
- if(IsObject() ||
- IsPed() && !bPedPhysics){
- m_vecMoveSpeedAvg = (m_vecMoveSpeedAvg + m_vecMoveSpeed)/2.0f;
- m_vecTurnSpeedAvg = (m_vecTurnSpeedAvg + m_vecTurnSpeed)/2.0f;
- float step = CTimer::GetTimeStep() * 0.003;
- if(m_vecMoveSpeedAvg.MagnitudeSqr() < step*step &&
- m_vecTurnSpeedAvg.MagnitudeSqr() < step*step){
- m_nStaticFrames++;
- if(m_nStaticFrames > 10){
- m_nStaticFrames = 10;
- bIsStatic = true;
- m_vecMoveSpeed = CVector(0.0f, 0.0f, 0.0f);
- m_vecTurnSpeed = CVector(0.0f, 0.0f, 0.0f);
- m_vecMoveFriction = m_vecMoveSpeed;
- m_vecTurnFriction = m_vecTurnSpeed;
- return;
- }
- }else
- m_nStaticFrames = 0;
+ for(listtype = 3; listtype >= 0; listtype--){
+ // Go through vehicles and objects
+ CPtrList *list;
+ switch(listtype){
+ case 0: list = &lists[ENTITYLIST_VEHICLES]; break;
+ case 1: list = &lists[ENTITYLIST_VEHICLES_OVERLAP]; break;
+ case 2: list = &lists[ENTITYLIST_OBJECTS]; break;
+ case 3: list = &lists[ENTITYLIST_OBJECTS_OVERLAP]; break;
+ }
+
+ // Find first collision in list
+ CPtrNode *listnode;
+ for(listnode = list->first; listnode; listnode = listnode->next){
+ B = (CPhysical*)listnode->item;
+ if(B != A &&
+ B->m_scanCode != CWorld::GetCurrentScanCode() &&
+ B->bUsesCollision &&
+ B->GetIsTouching(center, radius)){
+ B->m_scanCode = CWorld::GetCurrentScanCode();
+ numCollisions = A->ProcessEntityCollision(B, aColPoints);
+ if(numCollisions > 0)
+ goto collision;
+ }
}
}
- ApplyGravity();
- ApplyFriction();
- ApplyAirResistance();
+ // no collision
+ return false;
+
+collision:
+
+ if(A->bHasContacted && B->bHasContacted){
+ for(i = 0; i < numCollisions; i++){
+ if(!A->ApplyCollision(B, aColPoints[i], impulseA, impulseB))
+ continue;
+
+ if(impulseA > A->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceA, impulseA, B, aColPoints[i].normal);
+
+ if(impulseB > B->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceB, impulseB, A, aColPoints[i].normal);
+
+ float turnSpeedDiff = (B->m_vecTurnSpeed - A->m_vecTurnSpeed).MagnitudeSqr();
+ float moveSpeedDiff = (B->m_vecMoveSpeed - A->m_vecMoveSpeed).MagnitudeSqr();
+
+ cDMAudio::ReportCollision(A, B, aColPoints[i].surfaceA, aColPoints[i].surfaceB, impulseA, max(turnSpeedDiff, moveSpeedDiff));
+ }
+ }else if(A->bHasContacted){
+ CVector savedMoveFriction = A->m_vecMoveFriction;
+ CVector savedTurnFriction = A->m_vecTurnFriction;
+ A->m_vecMoveFriction = CVector(0.0f, 0.0f, 0.0f);
+ A->m_vecTurnFriction = CVector(0.0f, 0.0f, 0.0f);
+ A->bHasContacted = false;
+
+ for(i = 0; i < numCollisions; i++){
+ if(!A->ApplyCollision(B, aColPoints[i], impulseA, impulseB))
+ continue;
+
+ if(impulseA > A->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceA, impulseA, B, aColPoints[i].normal);
+
+ if(impulseB > B->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceB, impulseB, A, aColPoints[i].normal);
+
+ float turnSpeedDiff = (B->m_vecTurnSpeed - A->m_vecTurnSpeed).MagnitudeSqr();
+ float moveSpeedDiff = (B->m_vecMoveSpeed - A->m_vecMoveSpeed).MagnitudeSqr();
+
+ cDMAudio::ReportCollision(A, B, aColPoints[i].surfaceA, aColPoints[i].surfaceB, impulseA, max(turnSpeedDiff, moveSpeedDiff));
+
+ if(A->ApplyFriction(B, CSurfaceTable::GetAdhesiveLimit(aColPoints[i])/numCollisions, aColPoints[i])){
+ A->bHasContacted = true;
+ B->bHasContacted = true;
+ }
+ }
+
+ if(!A->bHasContacted){
+ A->bHasContacted = true;
+ A->m_vecMoveFriction = savedMoveFriction;
+ A->m_vecTurnFriction = savedTurnFriction;
+ }
+ }else if(B->bHasContacted){
+ CVector savedMoveFriction = B->m_vecMoveFriction;
+ CVector savedTurnFriction = B->m_vecTurnFriction;
+ B->m_vecMoveFriction = CVector(0.0f, 0.0f, 0.0f);
+ B->m_vecTurnFriction = CVector(0.0f, 0.0f, 0.0f);
+ B->bHasContacted = false;
+
+ for(i = 0; i < numCollisions; i++){
+ if(!A->ApplyCollision(B, aColPoints[i], impulseA, impulseB))
+ continue;
+
+ if(impulseA > A->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceA, impulseA, B, aColPoints[i].normal);
+
+ if(impulseB > B->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceB, impulseB, A, aColPoints[i].normal);
+
+ float turnSpeedDiff = (B->m_vecTurnSpeed - A->m_vecTurnSpeed).MagnitudeSqr();
+ float moveSpeedDiff = (B->m_vecMoveSpeed - A->m_vecMoveSpeed).MagnitudeSqr();
+
+ cDMAudio::ReportCollision(A, B, aColPoints[i].surfaceA, aColPoints[i].surfaceB, impulseA, max(turnSpeedDiff, moveSpeedDiff));
+
+ if(A->ApplyFriction(B, CSurfaceTable::GetAdhesiveLimit(aColPoints[i])/numCollisions, aColPoints[i])){
+ A->bHasContacted = true;
+ B->bHasContacted = true;
+ }
+ }
+
+ if(!B->bHasContacted){
+ B->bHasContacted = true;
+ B->m_vecMoveFriction = savedMoveFriction;
+ B->m_vecTurnFriction = savedTurnFriction;
+ }
+ }else{
+ for(i = 0; i < numCollisions; i++){
+ if(!A->ApplyCollision(B, aColPoints[i], impulseA, impulseB))
+ continue;
+
+ if(impulseA > A->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceA, impulseA, B, aColPoints[i].normal);
+
+ if(impulseB > B->m_fCollisionImpulse)
+ A->SetDamagedPieceRecord(aColPoints[i].pieceB, impulseB, A, aColPoints[i].normal);
+
+ float turnSpeedDiff = (B->m_vecTurnSpeed - A->m_vecTurnSpeed).MagnitudeSqr();
+ float moveSpeedDiff = (B->m_vecMoveSpeed - A->m_vecMoveSpeed).MagnitudeSqr();
+
+ cDMAudio::ReportCollision(A, B, aColPoints[i].surfaceA, aColPoints[i].surfaceB, impulseA, max(turnSpeedDiff, moveSpeedDiff));
+
+ if(A->ApplyFriction(B, CSurfaceTable::GetAdhesiveLimit(aColPoints[i])/numCollisions, aColPoints[i])){
+ A->bHasContacted = true;
+ B->bHasContacted = true;
+ }
+ }
+ }
+
+ if(B->m_status == STATUS_SIMPLE){
+ B->m_status = STATUS_PHYSICS;
+ if(B->IsVehicle())
+ CCarCtrl::SwitchVehicleToRealPhysics((CVehicle*)B);
+ }
+
+ return true;
}
+
STARTPATCHES
InjectHook(0x4951F0, &CPhysical::Add_, PATCH_JUMP);
InjectHook(0x4954B0, &CPhysical::Remove_, PATCH_JUMP);
InjectHook(0x495540, &CPhysical::RemoveAndAdd, PATCH_JUMP);
InjectHook(0x495F10, &CPhysical::ProcessControl_, PATCH_JUMP);
+ InjectHook(0x49F790, &CPhysical::ProcessEntityCollision_, PATCH_JUMP);
InjectHook(0x4958F0, &CPhysical::AddToMovingList, PATCH_JUMP);
InjectHook(0x495940, &CPhysical::RemoveFromMovingList, PATCH_JUMP);
-
InjectHook(0x497180, &CPhysical::AddCollisionRecord, PATCH_JUMP);
InjectHook(0x4970C0, &CPhysical::AddCollisionRecord_Treadable, PATCH_JUMP);
InjectHook(0x497240, &CPhysical::GetHasCollidedWith, PATCH_JUMP);
-
- InjectHook(0x49DA10, &CPhysical::ProcessShiftSectorList, PATCH_JUMP);
+ InjectHook(0x49F820, &CPhysical::RemoveRefsToEntity, PATCH_JUMP);
#define F3 float, float, float
InjectHook(0x495B10, &CPhysical::ApplyMoveSpeed, PATCH_JUMP);
@@ -1088,4 +1293,7 @@ STARTPATCHES
InjectHook(0x4992A0, &CPhysical::ApplyCollisionAlt, PATCH_JUMP);
InjectHook(0x499BE0, (bool (CPhysical::*)(float, CColPoint&))&CPhysical::ApplyFriction, PATCH_JUMP);
InjectHook(0x49A180, (bool (CPhysical::*)(CPhysical*, float, CColPoint&))&CPhysical::ApplyFriction, PATCH_JUMP);
+
+ InjectHook(0x49DA10, &CPhysical::ProcessShiftSectorList, PATCH_JUMP);
+ InjectHook(0x49E790, &CPhysical::ProcessCollisionSectorList_SimpleCar, PATCH_JUMP);
ENDPATCHES
diff --git a/src/entities/Physical.h b/src/entities/Physical.h
index 9867c33c..574238ab 100644
--- a/src/entities/Physical.h
+++ b/src/entities/Physical.h
@@ -82,6 +82,11 @@ public:
void RemoveAndAdd(void);
void AddToMovingList(void);
void RemoveFromMovingList(void);
+ void SetDamagedPieceRecord(uint16 piece, float impulse, CEntity *entity, CVector dir);
+ void AddCollisionRecord(CEntity *ent);
+ void AddCollisionRecord_Treadable(CEntity *ent);
+ bool GetHasCollidedWith(CEntity *ent);
+ void RemoveRefsToEntity(CEntity *ent);
// get speed of point p relative to entity center
CVector GetSpeed(const CVector &r);
@@ -126,16 +131,14 @@ public:
bool ApplyFriction(CPhysical *B, float adhesiveLimit, CColPoint &colpoint);
bool ApplyFriction(float adhesiveLimit, CColPoint &colpoint);
- void AddCollisionRecord(CEntity *ent);
- void AddCollisionRecord_Treadable(CEntity *ent);
- bool GetHasCollidedWith(CEntity *ent);
-
bool ProcessShiftSectorList(CPtrList *ptrlists);
+ bool ProcessCollisionSectorList_SimpleCar(CPtrList *lists);
// to make patching virtual functions possible
void Add_(void) { CPhysical::Add(); }
void Remove_(void) { CPhysical::Remove(); }
CRect GetBoundRect_(void) { return CPhysical::GetBoundRect(); }
void ProcessControl_(void) { CPhysical::ProcessControl(); }
+ int32 ProcessEntityCollision_(CEntity *ent, CColPoint *point) { return CPhysical::ProcessEntityCollision(ent, point); }
};
static_assert(sizeof(CPhysical) == 0x128, "CPhysical: error");