Merge branch 'master' of git://github.com/GTAmodding/re3 into erorcun
This commit is contained in:
commit
0974447f58
@ -5,6 +5,7 @@
|
|||||||
#include "World.h"
|
#include "World.h"
|
||||||
#include "Vehicle.h"
|
#include "Vehicle.h"
|
||||||
#include "Ped.h"
|
#include "Ped.h"
|
||||||
|
#include "PlayerPed.h"
|
||||||
#include "Pad.h"
|
#include "Pad.h"
|
||||||
#include "General.h"
|
#include "General.h"
|
||||||
#include "CullZones.h"
|
#include "CullZones.h"
|
||||||
|
@ -1,7 +1,21 @@
|
|||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
|
#include "main.h"
|
||||||
|
#include "Lists.h"
|
||||||
#include "Game.h"
|
#include "Game.h"
|
||||||
|
#include "Zones.h"
|
||||||
#include "General.h"
|
#include "General.h"
|
||||||
|
#include "CullZones.h"
|
||||||
|
#include "World.h"
|
||||||
|
#include "Entity.h"
|
||||||
|
#include "Train.h"
|
||||||
|
#include "Streaming.h"
|
||||||
|
#include "Pad.h"
|
||||||
|
#include "DMAudio.h"
|
||||||
|
#include "Population.h"
|
||||||
|
#include "FileLoader.h"
|
||||||
|
#include "Replay.h"
|
||||||
|
#include "CutsceneMgr.h"
|
||||||
#include "RenderBuffer.h"
|
#include "RenderBuffer.h"
|
||||||
#include "SurfaceTable.h"
|
#include "SurfaceTable.h"
|
||||||
#include "Collision.h"
|
#include "Collision.h"
|
||||||
@ -19,8 +33,6 @@ enum Direction
|
|||||||
eLevelName &CCollision::ms_collisionInMemory = *(eLevelName*)0x8F6250;
|
eLevelName &CCollision::ms_collisionInMemory = *(eLevelName*)0x8F6250;
|
||||||
CLinkList<CColModel*> &CCollision::ms_colModelCache = *(CLinkList<CColModel*>*)0x95CB58;
|
CLinkList<CColModel*> &CCollision::ms_colModelCache = *(CLinkList<CColModel*>*)0x95CB58;
|
||||||
|
|
||||||
#if 0
|
|
||||||
|
|
||||||
void
|
void
|
||||||
CCollision::Init(void)
|
CCollision::Init(void)
|
||||||
{
|
{
|
||||||
@ -28,72 +40,205 @@ CCollision::Init(void)
|
|||||||
ms_collisionInMemory = LEVEL_NONE;
|
ms_collisionInMemory = LEVEL_NONE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CCollision::Shutdown(void)
|
||||||
|
{
|
||||||
|
ms_colModelCache.Shutdown();
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
CCollision::Update(void)
|
CCollision::Update(void)
|
||||||
{
|
{
|
||||||
CVector pos = FindPlayerCoors();
|
CVector playerCoors;
|
||||||
|
playerCoors = FindPlayerCoors();
|
||||||
eLevelName level = CTheZones::m_CurrLevel;
|
eLevelName level = CTheZones::m_CurrLevel;
|
||||||
bool changeLevel = false;
|
bool forceLevelChange = false;
|
||||||
|
|
||||||
|
if(CTimer::GetTimeInMilliseconds() < 2000 || CCutsceneMgr::IsCutsceneProcessing())
|
||||||
|
return;
|
||||||
|
|
||||||
// hardcode a level if there are no zones
|
// hardcode a level if there are no zones
|
||||||
if(level == LEVEL_NONE){
|
if(level == LEVEL_NONE){
|
||||||
if(CGame::currLevel == LEVEL_INDUSTRIAL &&
|
if(CGame::currLevel == LEVEL_INDUSTRIAL &&
|
||||||
pos.x < 400.0f){
|
playerCoors.x < 400.0f){
|
||||||
level = LEVEL_COMMERCIAL;
|
level = LEVEL_COMMERCIAL;
|
||||||
changeLevel = true;
|
forceLevelChange = true;
|
||||||
}else if(CGame::currLevel == LEVEL_SUBURBAN &&
|
}else if(CGame::currLevel == LEVEL_SUBURBAN &&
|
||||||
pos.x > -450.0f && pos.y < -1400.0f){
|
playerCoors.x > -450.0f && playerCoors.y < -1400.0f){
|
||||||
level = LEVEL_COMMERCIAL;
|
level = LEVEL_COMMERCIAL;
|
||||||
changeLevel = true;
|
forceLevelChange = true;
|
||||||
}else{
|
}else{
|
||||||
if(pos.x > 800.0f){
|
if(playerCoors.x > 800.0f){
|
||||||
level = LEVEL_INDUSTRIAL;
|
level = LEVEL_INDUSTRIAL;
|
||||||
changeLevel = true;
|
forceLevelChange = true;
|
||||||
}else if(pos.x < -800.0f){
|
}else if(playerCoors.x < -800.0f){
|
||||||
level = LEVEL_SUBURBAN;
|
level = LEVEL_SUBURBAN;
|
||||||
changeLevel = true;
|
forceLevelChange = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(level != LEVEL_NONE && level != CGame::currLevel){
|
if(level != LEVEL_NONE && level != CGame::currLevel)
|
||||||
debug("changing level %d -> %d\n", CGame::currLevel, level);
|
|
||||||
CGame::currLevel = level;
|
CGame::currLevel = level;
|
||||||
}
|
|
||||||
if(ms_collisionInMemory != CGame::currLevel)
|
if(ms_collisionInMemory != CGame::currLevel)
|
||||||
LoadCollisionWhenINeedIt(changeLevel);
|
LoadCollisionWhenINeedIt(forceLevelChange);
|
||||||
CStreaming::HaveAllBigBuildingsLoaded(CGame::currLevel);
|
CStreaming::HaveAllBigBuildingsLoaded(CGame::currLevel);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
eLevelName
|
||||||
CCollision::LoadCollisionWhenINeedIt(bool changeLevel)
|
GetCollisionInSectorList(CPtrList &list)
|
||||||
{
|
{
|
||||||
eLevelName level;
|
CPtrNode *node;
|
||||||
|
CEntity *e;
|
||||||
|
int level;
|
||||||
|
|
||||||
|
for(node = list.first; node; node = node->next){
|
||||||
|
e = (CEntity*)node->item;
|
||||||
|
level = CModelInfo::GetModelInfo(e->GetModelIndex())->GetColModel()->level;
|
||||||
|
if(level != LEVEL_NONE)
|
||||||
|
return (eLevelName)level;
|
||||||
|
}
|
||||||
|
return LEVEL_NONE;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get a level this sector is in based on collision models
|
||||||
|
eLevelName
|
||||||
|
GetCollisionInSector(CSector §)
|
||||||
|
{
|
||||||
|
int level;
|
||||||
|
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_BUILDINGS]);
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_BUILDINGS_OVERLAP]);
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_OBJECTS]);
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_OBJECTS_OVERLAP]);
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_DUMMIES]);
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = GetCollisionInSectorList(sect.m_lists[ENTITYLIST_DUMMIES_OVERLAP]);
|
||||||
|
return (eLevelName)level;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CCollision::LoadCollisionWhenINeedIt(bool forceChange)
|
||||||
|
{
|
||||||
|
eLevelName level, l;
|
||||||
|
bool multipleLevels;
|
||||||
|
CVector playerCoors;
|
||||||
|
CVehicle *veh;
|
||||||
|
CEntryInfoNode *ei;
|
||||||
|
int sx, sy;
|
||||||
|
int xmin, xmax, ymin, ymax;
|
||||||
|
int x, y;
|
||||||
|
|
||||||
level = LEVEL_NONE;
|
level = LEVEL_NONE;
|
||||||
if(!changeLevel){
|
|
||||||
//assert(0 && "unimplemented");
|
playerCoors = FindPlayerCoors();
|
||||||
|
sx = CWorld::GetSectorIndexX(playerCoors.x);
|
||||||
|
sy = CWorld::GetSectorIndexY(playerCoors.y);
|
||||||
|
multipleLevels = false;
|
||||||
|
|
||||||
|
veh = FindPlayerVehicle();
|
||||||
|
if(veh && veh->IsTrain()){
|
||||||
|
if(((CTrain*)veh)->m_doorState != TRAIN_DOOR_STATE2)
|
||||||
|
return ;
|
||||||
|
}else if(playerCoors.z < 4.0f && !CCullZones::DoINeedToLoadCollision())
|
||||||
|
return;
|
||||||
|
|
||||||
|
// Figure out whose level's collisions we're most likely to be interested in
|
||||||
|
if(!forceChange){
|
||||||
|
if(veh && veh->IsBoat()){
|
||||||
|
// on water we expect to be between levels
|
||||||
|
multipleLevels = true;
|
||||||
|
}else{
|
||||||
|
xmin = max(sx - 1, 0);
|
||||||
|
xmax = min(sx + 1, NUMSECTORS_X-1);
|
||||||
|
ymin = max(sy - 1, 0);
|
||||||
|
ymax = min(sy + 1, NUMSECTORS_Y-1);
|
||||||
|
|
||||||
|
for(x = xmin; x <= xmax; x++)
|
||||||
|
for(y = ymin; y <= ymax; y++){
|
||||||
|
l = GetCollisionInSector(*CWorld::GetSector(x, y));
|
||||||
|
if(l != LEVEL_NONE){
|
||||||
|
if(level == LEVEL_NONE)
|
||||||
|
level = l;
|
||||||
|
if(level != l)
|
||||||
|
multipleLevels = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(multipleLevels && veh && veh->IsBoat())
|
||||||
|
for(ei = veh->m_entryInfoList.first; ei; ei = ei->next){
|
||||||
|
level = GetCollisionInSector(*ei->sector);
|
||||||
|
if(level != LEVEL_NONE)
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(level != CGame::currLevel || changeLevel){
|
if(level == CGame::currLevel || forceChange){
|
||||||
CTimer::Stop();
|
CTimer::Stop();
|
||||||
|
DMAudio.SetEffectsFadeVol(0);
|
||||||
|
CPad::StopPadsShaking();
|
||||||
|
LoadCollisionScreen(CGame::currLevel);
|
||||||
|
DMAudio.Service();
|
||||||
|
CPopulation::DealWithZoneChange(ms_collisionInMemory, CGame::currLevel, false);
|
||||||
CStreaming::RemoveIslandsNotUsed(LEVEL_INDUSTRIAL);
|
CStreaming::RemoveIslandsNotUsed(LEVEL_INDUSTRIAL);
|
||||||
CStreaming::RemoveIslandsNotUsed(LEVEL_COMMERCIAL);
|
CStreaming::RemoveIslandsNotUsed(LEVEL_COMMERCIAL);
|
||||||
CStreaming::RemoveIslandsNotUsed(LEVEL_SUBURBAN);
|
CStreaming::RemoveIslandsNotUsed(LEVEL_SUBURBAN);
|
||||||
CStreaming::RemoveBigBuildings(LEVEL_INDUSTRIAL);
|
CStreaming::RemoveBigBuildings(LEVEL_INDUSTRIAL);
|
||||||
CStreaming::RemoveBigBuildings(LEVEL_COMMERCIAL);
|
CStreaming::RemoveBigBuildings(LEVEL_COMMERCIAL);
|
||||||
CStreaming::RemoveBigBuildings(LEVEL_SUBURBAN);
|
CStreaming::RemoveBigBuildings(LEVEL_SUBURBAN);
|
||||||
|
CModelInfo::RemoveColModelsFromOtherLevels(CGame::currLevel);
|
||||||
|
CStreaming::RemoveUnusedModelsInLoadedList();
|
||||||
|
CGame::TidyUpMemory(true, true);
|
||||||
|
CFileLoader::LoadCollisionFromDatFile(CGame::currLevel);
|
||||||
ms_collisionInMemory = CGame::currLevel;
|
ms_collisionInMemory = CGame::currLevel;
|
||||||
|
CReplay::EmptyReplayBuffer();
|
||||||
|
if(CGame::currLevel != LEVEL_NONE)
|
||||||
|
LoadSplash(GetLevelSplashScreen(CGame::currLevel));
|
||||||
CStreaming::RemoveUnusedBigBuildings(CGame::currLevel);
|
CStreaming::RemoveUnusedBigBuildings(CGame::currLevel);
|
||||||
CStreaming::RemoveUnusedBuildings(CGame::currLevel);
|
CStreaming::RemoveUnusedBuildings(CGame::currLevel);
|
||||||
CStreaming::RequestBigBuildings(CGame::currLevel);
|
CStreaming::RequestBigBuildings(CGame::currLevel);
|
||||||
CStreaming::LoadAllRequestedModels();
|
CStreaming::LoadAllRequestedModels(true);
|
||||||
CStreaming::HaveAllBigBuildingsLoaded(CGame::currLevel);
|
CStreaming::HaveAllBigBuildingsLoaded(CGame::currLevel);
|
||||||
|
CGame::TidyUpMemory(true, true);
|
||||||
CTimer::Update();
|
CTimer::Update();
|
||||||
|
DMAudio.SetEffectsFadeVol(127);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
void
|
||||||
|
CCollision::SortOutCollisionAfterLoad(void)
|
||||||
|
{
|
||||||
|
if(ms_collisionInMemory == CGame::currLevel)
|
||||||
|
return;
|
||||||
|
|
||||||
WRAPPER void CCollision::SortOutCollisionAfterLoad(void) { EAXJMP(0x40B900); }
|
CModelInfo::RemoveColModelsFromOtherLevels(CGame::currLevel);
|
||||||
|
if(CGame::currLevel != LEVEL_NONE){
|
||||||
|
CFileLoader::LoadCollisionFromDatFile(CGame::currLevel);
|
||||||
|
if(!CGame::playingIntro)
|
||||||
|
LoadSplash(GetLevelSplashScreen(CGame::currLevel));
|
||||||
|
}
|
||||||
|
ms_collisionInMemory = CGame::currLevel;
|
||||||
|
CGame::TidyUpMemory(true, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CCollision::LoadCollisionScreen(eLevelName level)
|
||||||
|
{
|
||||||
|
static char *levelNames[4] = {
|
||||||
|
"",
|
||||||
|
"IND_ZON",
|
||||||
|
"COM_ZON",
|
||||||
|
"SUB_ZON"
|
||||||
|
};
|
||||||
|
|
||||||
|
// Why twice?
|
||||||
|
LoadingIslandScreen(levelNames[level]);
|
||||||
|
LoadingIslandScreen(levelNames[level]);
|
||||||
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
// Test
|
// Test
|
||||||
@ -1585,11 +1730,119 @@ CColModel::GetTrianglePoint(CVector &v, int i) const
|
|||||||
v = vertices[i];
|
v = vertices[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
WRAPPER CColModel& CColModel::operator=(const CColModel& other) { EAXJMP(0x411710); }
|
CColModel&
|
||||||
|
CColModel::operator=(const CColModel &other)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
int numVerts;
|
||||||
|
|
||||||
|
assert(0);
|
||||||
|
|
||||||
|
boundingSphere = other.boundingSphere;
|
||||||
|
boundingBox = other.boundingBox;
|
||||||
|
|
||||||
|
// copy spheres
|
||||||
|
if(other.numSpheres){
|
||||||
|
if(numSpheres != other.numSpheres){
|
||||||
|
numSpheres = other.numSpheres;
|
||||||
|
if(spheres)
|
||||||
|
RwFree(spheres);
|
||||||
|
spheres = (CColSphere*)RwMalloc(numSpheres*sizeof(CColSphere));
|
||||||
|
}
|
||||||
|
for(i = 0; i < numSpheres; i++)
|
||||||
|
spheres[i] = other.spheres[i];
|
||||||
|
}else{
|
||||||
|
numSpheres = 0;
|
||||||
|
if(spheres)
|
||||||
|
RwFree(spheres);
|
||||||
|
spheres = nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
// copy lines
|
||||||
|
if(other.numLines){
|
||||||
|
if(numLines != other.numLines){
|
||||||
|
numLines = other.numLines;
|
||||||
|
if(lines)
|
||||||
|
RwFree(lines);
|
||||||
|
lines = (CColLine*)RwMalloc(numLines*sizeof(CColLine));
|
||||||
|
}
|
||||||
|
for(i = 0; i < numLines; i++)
|
||||||
|
lines[i] = other.lines[i];
|
||||||
|
}else{
|
||||||
|
numLines = 0;
|
||||||
|
if(lines)
|
||||||
|
RwFree(lines);
|
||||||
|
lines = nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
// copy boxes
|
||||||
|
if(other.numBoxes){
|
||||||
|
if(numBoxes != other.numBoxes){
|
||||||
|
numBoxes = other.numBoxes;
|
||||||
|
if(boxes)
|
||||||
|
RwFree(boxes);
|
||||||
|
boxes = (CColBox*)RwMalloc(numBoxes*sizeof(CColBox));
|
||||||
|
}
|
||||||
|
for(i = 0; i < numBoxes; i++)
|
||||||
|
boxes[i] = other.boxes[i];
|
||||||
|
}else{
|
||||||
|
numBoxes = 0;
|
||||||
|
if(boxes)
|
||||||
|
RwFree(boxes);
|
||||||
|
boxes = nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
// copy mesh
|
||||||
|
if(other.numTriangles){
|
||||||
|
// copy vertices
|
||||||
|
numVerts = 0;
|
||||||
|
for(i = 0; i < other.numTriangles; i++){
|
||||||
|
if(other.triangles[i].a > numVerts)
|
||||||
|
other.triangles[i].a = numVerts;
|
||||||
|
if(other.triangles[i].b > numVerts)
|
||||||
|
other.triangles[i].b = numVerts;
|
||||||
|
if(other.triangles[i].c > numVerts)
|
||||||
|
other.triangles[i].c = numVerts;
|
||||||
|
}
|
||||||
|
numVerts++;
|
||||||
|
if(vertices)
|
||||||
|
RwFree(vertices);
|
||||||
|
if(numVerts){
|
||||||
|
vertices = (CVector*)RwMalloc(numVerts*sizeof(CVector));
|
||||||
|
for(i = 0; i < numVerts; i++)
|
||||||
|
vertices[i] = other.vertices[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
// copy triangles
|
||||||
|
if(numTriangles != other.numTriangles){
|
||||||
|
numTriangles = other.numTriangles;
|
||||||
|
if(triangles)
|
||||||
|
RwFree(triangles);
|
||||||
|
triangles = (CColTriangle*)RwMalloc(numTriangles*sizeof(CColTriangle));
|
||||||
|
}
|
||||||
|
for(i = 0; i < numTriangles; i++)
|
||||||
|
triangles[i] = other.triangles[i];
|
||||||
|
}else{
|
||||||
|
numTriangles = 0;
|
||||||
|
if(triangles)
|
||||||
|
RwFree(triangles);
|
||||||
|
triangles = nil;
|
||||||
|
if(vertices)
|
||||||
|
RwFree(vertices);
|
||||||
|
vertices = nil;
|
||||||
|
}
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
STARTPATCHES
|
STARTPATCHES
|
||||||
InjectHook(0x4B9C30, (CMatrix& (*)(const CMatrix &src, CMatrix &dst))Invert, PATCH_JUMP);
|
InjectHook(0x4B9C30, (CMatrix& (*)(const CMatrix &src, CMatrix &dst))Invert, PATCH_JUMP);
|
||||||
|
|
||||||
|
InjectHook(0x40B380, CCollision::Init, PATCH_JUMP);
|
||||||
|
InjectHook(0x40B3A0, CCollision::Shutdown, PATCH_JUMP);
|
||||||
|
InjectHook(0x40B3B0, CCollision::Update, PATCH_JUMP);
|
||||||
|
InjectHook(0x40B5B0, CCollision::LoadCollisionWhenINeedIt, PATCH_JUMP);
|
||||||
|
InjectHook(0x40B900, CCollision::SortOutCollisionAfterLoad, PATCH_JUMP);
|
||||||
|
|
||||||
InjectHook(0x40BB70, CCollision::TestSphereBox, PATCH_JUMP);
|
InjectHook(0x40BB70, CCollision::TestSphereBox, PATCH_JUMP);
|
||||||
InjectHook(0x40E130, CCollision::TestLineBox, PATCH_JUMP);
|
InjectHook(0x40E130, CCollision::TestLineBox, PATCH_JUMP);
|
||||||
InjectHook(0x40E5C0, CCollision::TestVerticalLineBox, PATCH_JUMP);
|
InjectHook(0x40E5C0, CCollision::TestVerticalLineBox, PATCH_JUMP);
|
||||||
|
@ -118,9 +118,11 @@ public:
|
|||||||
static CLinkList<CColModel*> &ms_colModelCache;
|
static CLinkList<CColModel*> &ms_colModelCache;
|
||||||
|
|
||||||
static void Init(void);
|
static void Init(void);
|
||||||
|
static void Shutdown(void);
|
||||||
static void Update(void);
|
static void Update(void);
|
||||||
static void LoadCollisionWhenINeedIt(bool changeLevel);
|
static void LoadCollisionWhenINeedIt(bool changeLevel);
|
||||||
static void SortOutCollisionAfterLoad(void);
|
static void SortOutCollisionAfterLoad(void);
|
||||||
|
static void LoadCollisionScreen(eLevelName level);
|
||||||
static void DrawColModel(const CMatrix &mat, const CColModel &colModel);
|
static void DrawColModel(const CMatrix &mat, const CColModel &colModel);
|
||||||
static void DrawColModel_Coloured(const CMatrix &mat, const CColModel &colModel, int32 id);
|
static void DrawColModel_Coloured(const CMatrix &mat, const CColModel &colModel, int32 id);
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
#include "Building.h"
|
#include "Building.h"
|
||||||
#include "Treadable.h"
|
#include "Treadable.h"
|
||||||
|
#include "Train.h"
|
||||||
#include "Pools.h"
|
#include "Pools.h"
|
||||||
#include "Timer.h"
|
#include "Timer.h"
|
||||||
#include "Camera.h"
|
#include "Camera.h"
|
||||||
@ -71,7 +72,6 @@ void
|
|||||||
CCullZones::Update(void)
|
CCullZones::Update(void)
|
||||||
{
|
{
|
||||||
bool invisible;
|
bool invisible;
|
||||||
CVector v;
|
|
||||||
|
|
||||||
if(bCullZonesDisabled)
|
if(bCullZonesDisabled)
|
||||||
return;
|
return;
|
||||||
@ -95,7 +95,7 @@ CCullZones::Update(void)
|
|||||||
|
|
||||||
case 6:
|
case 6:
|
||||||
/* Update player attributes */
|
/* Update player attributes */
|
||||||
CurrentFlags_Player = FindAttributesForCoors(FindPlayerCoors(v),
|
CurrentFlags_Player = FindAttributesForCoors(FindPlayerCoors(),
|
||||||
&CurrentWantedLevelDrop_Player);
|
&CurrentWantedLevelDrop_Player);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -152,7 +152,7 @@ CCullZones::FindZoneWithStairsAttributeForPlayer(void)
|
|||||||
int i;
|
int i;
|
||||||
CVector coors;
|
CVector coors;
|
||||||
|
|
||||||
FindPlayerCoors(coors);
|
coors = FindPlayerCoors();
|
||||||
for(i = 0; i < NumAttributeZones; i++)
|
for(i = 0; i < NumAttributeZones; i++)
|
||||||
if(aAttributeZones[i].attributes & ATTRZONE_STAIRS &&
|
if(aAttributeZones[i].attributes & ATTRZONE_STAIRS &&
|
||||||
coors.x >= aAttributeZones[i].minx && coors.x <= aAttributeZones[i].maxx &&
|
coors.x >= aAttributeZones[i].minx && coors.x <= aAttributeZones[i].maxx &&
|
||||||
@ -162,9 +162,33 @@ CCullZones::FindZoneWithStairsAttributeForPlayer(void)
|
|||||||
return nil;
|
return nil;
|
||||||
}
|
}
|
||||||
|
|
||||||
WRAPPER void
|
void
|
||||||
CCullZones::MarkSubwayAsInvisible(bool visible)
|
CCullZones::MarkSubwayAsInvisible(bool visible)
|
||||||
{ EAXJMP(0x525AF0);
|
{
|
||||||
|
int i, n;
|
||||||
|
CEntity *e;
|
||||||
|
CVehicle *v;
|
||||||
|
|
||||||
|
n = CPools::GetBuildingPool()->GetSize();
|
||||||
|
for(i = 0; i < n; i++){
|
||||||
|
e = CPools::GetBuildingPool()->GetSlot(i);
|
||||||
|
if(e && e->bIsSubway)
|
||||||
|
e->bIsVisible = visible;
|
||||||
|
}
|
||||||
|
|
||||||
|
n = CPools::GetTreadablePool()->GetSize();
|
||||||
|
for(i = 0; i < n; i++){
|
||||||
|
e = CPools::GetTreadablePool()->GetSlot(i);
|
||||||
|
if(e && e->bIsSubway)
|
||||||
|
e->bIsVisible = visible;
|
||||||
|
}
|
||||||
|
|
||||||
|
n = CPools::GetVehiclePool()->GetSize();
|
||||||
|
for(i = 0; i < n; i++){
|
||||||
|
v = CPools::GetVehiclePool()->GetSlot(i);
|
||||||
|
if(v && v->IsTrain() && ((CTrain*)v)->m_trackId != 0)
|
||||||
|
v->bIsVisible = visible;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -46,7 +46,7 @@ CFileLoader::LoadLevel(const char *filename)
|
|||||||
{
|
{
|
||||||
int fd;
|
int fd;
|
||||||
RwTexDictionary *savedTxd;
|
RwTexDictionary *savedTxd;
|
||||||
int savedLevel;
|
eLevelName savedLevel;
|
||||||
bool objectsLoaded;
|
bool objectsLoaded;
|
||||||
char *line;
|
char *line;
|
||||||
char txdname[64];
|
char txdname[64];
|
||||||
@ -79,7 +79,7 @@ CFileLoader::LoadLevel(const char *filename)
|
|||||||
}else if(strncmp(line, "COLFILE", 7) == 0){
|
}else if(strncmp(line, "COLFILE", 7) == 0){
|
||||||
int level;
|
int level;
|
||||||
sscanf(line+8, "%d", &level);
|
sscanf(line+8, "%d", &level);
|
||||||
CGame::currLevel = level;
|
CGame::currLevel = (eLevelName)level;
|
||||||
LoadingScreenLoadingFile(line+10);
|
LoadingScreenLoadingFile(line+10);
|
||||||
LoadCollisionFile(line+10);
|
LoadCollisionFile(line+10);
|
||||||
CGame::currLevel = savedLevel;
|
CGame::currLevel = savedLevel;
|
||||||
|
@ -265,10 +265,10 @@ CFileMgr::Seek(int fd, int offset, int whence)
|
|||||||
return !!myfseek(fd, offset, whence);
|
return !!myfseek(fd, offset, whence);
|
||||||
}
|
}
|
||||||
|
|
||||||
char*
|
bool
|
||||||
CFileMgr::ReadLine(int fd, char *buf, int len)
|
CFileMgr::ReadLine(int fd, char *buf, int len)
|
||||||
{
|
{
|
||||||
return myfgets(buf, len, fd);
|
return myfgets(buf, len, fd) != nil;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
@ -15,7 +15,7 @@ public:
|
|||||||
static int Read(int fd, char *buf, int len);
|
static int Read(int fd, char *buf, int len);
|
||||||
static int Write(int fd, char *buf, int len);
|
static int Write(int fd, char *buf, int len);
|
||||||
static bool Seek(int fd, int offset, int whence);
|
static bool Seek(int fd, int offset, int whence);
|
||||||
static char *ReadLine(int fd, char *buf, int len);
|
static bool ReadLine(int fd, char *buf, int len);
|
||||||
static int CloseFile(int fd);
|
static int CloseFile(int fd);
|
||||||
static int GetErrorReadWrite(int fd);
|
static int GetErrorReadWrite(int fd);
|
||||||
};
|
};
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
#include "Game.h"
|
#include "Game.h"
|
||||||
|
|
||||||
int &CGame::currLevel = *(int*)0x941514;
|
eLevelName &CGame::currLevel = *(eLevelName*)0x941514;
|
||||||
bool &CGame::bDemoMode = *(bool*)0x5F4DD0;
|
bool &CGame::bDemoMode = *(bool*)0x5F4DD0;
|
||||||
bool &CGame::nastyGame = *(bool*)0x5F4DD4;
|
bool &CGame::nastyGame = *(bool*)0x5F4DD4;
|
||||||
bool &CGame::frenchGame = *(bool*)0x95CDCB;
|
bool &CGame::frenchGame = *(bool*)0x95CDCB;
|
||||||
@ -11,6 +11,7 @@ bool &CGame::noProstitutes = *(bool*)0x95CDCF;
|
|||||||
bool &CGame::playingIntro = *(bool*)0x95CDC2;
|
bool &CGame::playingIntro = *(bool*)0x95CDC2;
|
||||||
char *CGame::aDatFile = (char*)0x773A48;
|
char *CGame::aDatFile = (char*)0x773A48;
|
||||||
|
|
||||||
|
WRAPPER void CGame::Initialise(const char *datFile) { EAXJMP(0x48BED0); }
|
||||||
WRAPPER void CGame::Process(void) { EAXJMP(0x48C850); }
|
WRAPPER void CGame::Process(void) { EAXJMP(0x48C850); }
|
||||||
WRAPPER bool CGame::InitialiseOnceBeforeRW(void) { EAXJMP(0x48BB80); }
|
WRAPPER bool CGame::InitialiseOnceBeforeRW(void) { EAXJMP(0x48BB80); }
|
||||||
WRAPPER bool CGame::InitialiseRenderWare(void) { EAXJMP(0x48BBA0); }
|
WRAPPER bool CGame::InitialiseRenderWare(void) { EAXJMP(0x48BBA0); }
|
||||||
|
15
src/Game.h
15
src/Game.h
@ -11,7 +11,7 @@ enum eLevelName
|
|||||||
class CGame
|
class CGame
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static int &currLevel;
|
static eLevelName &currLevel;
|
||||||
static bool &bDemoMode;
|
static bool &bDemoMode;
|
||||||
static bool &nastyGame;
|
static bool &nastyGame;
|
||||||
static bool &frenchGame;
|
static bool &frenchGame;
|
||||||
@ -20,13 +20,18 @@ public:
|
|||||||
static bool &playingIntro;
|
static bool &playingIntro;
|
||||||
static char *aDatFile; //[32];
|
static char *aDatFile; //[32];
|
||||||
|
|
||||||
static void Process(void);
|
static void Initialise(const char *datFile);
|
||||||
static bool InitialiseOnceBeforeRW(void);
|
static bool InitialiseOnceBeforeRW(void);
|
||||||
static bool InitialiseRenderWare(void);
|
static bool InitialiseRenderWare(void);
|
||||||
|
static bool InitialiseOnceAfterRW(void);
|
||||||
|
static void InitialiseWhenRestarting(void);
|
||||||
|
static void ShutDown(void);
|
||||||
static void ShutdownRenderWare(void);
|
static void ShutdownRenderWare(void);
|
||||||
static void FinalShutdown(void);
|
static void FinalShutdown(void);
|
||||||
static void ShutDown(void);
|
|
||||||
static void ShutDownForRestart(void);
|
static void ShutDownForRestart(void);
|
||||||
static void InitialiseWhenRestarting(void);
|
static void Process(void);
|
||||||
static bool InitialiseOnceAfterRW(void);
|
|
||||||
|
// NB: these do something on PS2
|
||||||
|
static void TidyUpMemory(bool, bool) {}
|
||||||
|
static void DrasticTidyUpMemory(void) {}
|
||||||
};
|
};
|
||||||
|
@ -279,7 +279,7 @@ void CRadar::DrawBlips()
|
|||||||
if (TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWN1)
|
if (TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWN1)
|
||||||
angle = PI + FindPlayerHeading();
|
angle = PI + FindPlayerHeading();
|
||||||
else
|
else
|
||||||
angle = FindPlayerHeading() - (PI + atan2(-TheCamera.GetForward().x, TheCamera.GetForward().y));
|
angle = FindPlayerHeading() - (PI + TheCamera.GetForward().Heading());
|
||||||
|
|
||||||
DrawRotatingRadarSprite(CentreSprite, out.x, out.y, angle, 255);
|
DrawRotatingRadarSprite(CentreSprite, out.x, out.y, angle, 255);
|
||||||
|
|
||||||
@ -868,8 +868,8 @@ void CRadar::TransformRadarPointToRealWorldSpace(CVector2D &out, const CVector2D
|
|||||||
{
|
{
|
||||||
float s, c;
|
float s, c;
|
||||||
|
|
||||||
s = -sin(atan2(-TheCamera.GetForward().x, TheCamera.GetForward().y));
|
s = -sin(TheCamera.GetForward().Heading());
|
||||||
c = cos(atan2(-TheCamera.GetForward().x, TheCamera.GetForward().y));
|
c = cos(TheCamera.GetForward().Heading());
|
||||||
|
|
||||||
if (TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWN1 || TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWNPED) {
|
if (TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWN1 || TheCamera.Cams[TheCamera.ActiveCam].Mode == CCam::MODE_TOPDOWNPED) {
|
||||||
s = 0.0f;
|
s = 0.0f;
|
||||||
@ -885,8 +885,8 @@ void CRadar::TransformRadarPointToRealWorldSpace(CVector2D &out, const CVector2D
|
|||||||
else
|
else
|
||||||
forward = TheCamera.Cams[TheCamera.ActiveCam].CamTargetEntity->GetPosition() - TheCamera.Cams[TheCamera.ActiveCam].SourceBeforeLookBehind;
|
forward = TheCamera.Cams[TheCamera.ActiveCam].CamTargetEntity->GetPosition() - TheCamera.Cams[TheCamera.ActiveCam].SourceBeforeLookBehind;
|
||||||
|
|
||||||
s = -sin(atan2(-forward.x, forward.y));
|
s = -sin(forward.Heading());
|
||||||
c = cos(atan2(-forward.x, forward.y));
|
c = cos(forward.Heading());
|
||||||
}
|
}
|
||||||
|
|
||||||
out.x = s * in.y + c * in.x;
|
out.x = s * in.y + c * in.x;
|
||||||
@ -915,8 +915,8 @@ void CRadar::TransformRealWorldPointToRadarSpace(CVector2D &out, const CVector2D
|
|||||||
c = 1.0f;
|
c = 1.0f;
|
||||||
}
|
}
|
||||||
else if (TheCamera.GetLookDirection() == LOOKING_FORWARD) {
|
else if (TheCamera.GetLookDirection() == LOOKING_FORWARD) {
|
||||||
s = sin(atan2(-TheCamera.GetForward().x, TheCamera.GetForward().y));
|
s = sin(TheCamera.GetForward().Heading());
|
||||||
c = cos(atan2(-TheCamera.GetForward().x, TheCamera.GetForward().y));
|
c = cos(TheCamera.GetForward().Heading());
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
CVector forward;
|
CVector forward;
|
||||||
@ -928,8 +928,8 @@ void CRadar::TransformRealWorldPointToRadarSpace(CVector2D &out, const CVector2D
|
|||||||
else
|
else
|
||||||
forward = TheCamera.Cams[TheCamera.ActiveCam].CamTargetEntity->GetPosition() - TheCamera.Cams[TheCamera.ActiveCam].SourceBeforeLookBehind;
|
forward = TheCamera.Cams[TheCamera.ActiveCam].CamTargetEntity->GetPosition() - TheCamera.Cams[TheCamera.ActiveCam].SourceBeforeLookBehind;
|
||||||
|
|
||||||
s = sin(atan2(-forward.x, forward.y));
|
s = sin(forward.Heading());
|
||||||
c = cos(atan2(-forward.x, forward.y));
|
c = cos(forward.Heading());
|
||||||
}
|
}
|
||||||
|
|
||||||
float x = (in.x - vec2DRadarOrigin.x) * (1.0f / m_RadarRange);
|
float x = (in.x - vec2DRadarOrigin.x) * (1.0f / m_RadarRange);
|
||||||
|
212
src/RwMatFX.cpp
Normal file
212
src/RwMatFX.cpp
Normal file
@ -0,0 +1,212 @@
|
|||||||
|
#define WITHD3D
|
||||||
|
#include "common.h"
|
||||||
|
#include "patcher.h"
|
||||||
|
|
||||||
|
struct MatFXNothing { int pad[5]; int effect; };
|
||||||
|
|
||||||
|
struct MatFXBump
|
||||||
|
{
|
||||||
|
RwFrame *bumpFrame;
|
||||||
|
RwTexture *bumpedTex;
|
||||||
|
RwTexture *bumpTex;
|
||||||
|
float negBumpCoefficient;
|
||||||
|
int pad;
|
||||||
|
int effect;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct MatFXEnv
|
||||||
|
{
|
||||||
|
RwFrame *envFrame;
|
||||||
|
RwTexture *envTex;
|
||||||
|
float envCoeff;
|
||||||
|
int envFBalpha;
|
||||||
|
int pad;
|
||||||
|
int effect;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct MatFXDual
|
||||||
|
{
|
||||||
|
RwTexture *dualTex;
|
||||||
|
RwInt32 srcBlend;
|
||||||
|
RwInt32 dstBlend;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct MatFX
|
||||||
|
{
|
||||||
|
union {
|
||||||
|
MatFXNothing n;
|
||||||
|
MatFXBump b;
|
||||||
|
MatFXEnv e;
|
||||||
|
MatFXDual d;
|
||||||
|
} fx[2];
|
||||||
|
int effects;
|
||||||
|
};
|
||||||
|
|
||||||
|
int &MatFXMaterialDataOffset = *(int*)0x66188C;
|
||||||
|
int &MatFXAtomicDataOffset = *(int*)0x66189C;
|
||||||
|
|
||||||
|
#ifdef PS2_MATFX
|
||||||
|
|
||||||
|
void
|
||||||
|
_rpMatFXD3D8AtomicMatFXDefaultRender(RxD3D8InstanceData *inst, int flags, RwTexture *texture)
|
||||||
|
{
|
||||||
|
if(flags & (rpGEOMETRYTEXTURED|rpGEOMETRYTEXTURED2) && texture)
|
||||||
|
RwD3D8SetTexture(texture, 0);
|
||||||
|
else
|
||||||
|
RwD3D8SetTexture(NULL, 0);
|
||||||
|
RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void*)(inst->vertexAlpha || inst->material->color.alpha != 0xFF));
|
||||||
|
RwD3D8SetRenderState(D3DRS_DIFFUSEMATERIALSOURCE, inst->vertexAlpha != 0);
|
||||||
|
RwD3D8SetPixelShader(0);
|
||||||
|
RwD3D8SetVertexShader(inst->vertexShader);
|
||||||
|
RwD3D8SetStreamSource(0, inst->vertexBuffer, inst->stride);
|
||||||
|
|
||||||
|
if(inst->indexBuffer){
|
||||||
|
RwD3D8SetIndices(inst->indexBuffer, inst->baseIndex);
|
||||||
|
RwD3D8DrawIndexedPrimitive(inst->primType, 0, inst->numVertices, 0, inst->numIndices);
|
||||||
|
}else
|
||||||
|
RwD3D8DrawPrimitive(inst->primType, inst->baseIndex, inst->numVertices);
|
||||||
|
}
|
||||||
|
|
||||||
|
// map [-1; -1] -> [0; 1], flip V
|
||||||
|
static RwMatrix scalenormal = {
|
||||||
|
{ 0.5f, 0.0f, 0.0f }, 0,
|
||||||
|
{ 0.0f, -0.5f, 0.0f }, 0,
|
||||||
|
{ 0.0f, 0.0f, 1.0f }, 0,
|
||||||
|
{ 0.5f, 0.5f, 0.0f }, 0,
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
// flipped U for PS2
|
||||||
|
static RwMatrix scalenormal_flipU = {
|
||||||
|
{ -0.5f, 0.0f, 0.0f }, 0,
|
||||||
|
{ 0.0f, -0.5f, 0.0f }, 0,
|
||||||
|
{ 0.0f, 0.0f, 1.0f }, 0,
|
||||||
|
{ 0.5f, 0.5f, 0.0f }, 0,
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
void
|
||||||
|
ApplyEnvMapTextureMatrix(RwTexture *tex, int n, RwFrame *frame)
|
||||||
|
{
|
||||||
|
RwD3D8SetTexture(tex, n);
|
||||||
|
RwD3D8SetTextureStageState(n, D3DRS_ALPHAREF, 2);
|
||||||
|
RwD3D8SetTextureStageState(n, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_CAMERASPACENORMAL);
|
||||||
|
if(frame){
|
||||||
|
RwMatrix *envframemat = RwMatrixCreate();
|
||||||
|
RwMatrix *tmpmat = RwMatrixCreate();
|
||||||
|
RwMatrix *envmat = RwMatrixCreate();
|
||||||
|
|
||||||
|
RwMatrixInvert(envframemat, RwFrameGetLTM(frame));
|
||||||
|
// PS2
|
||||||
|
// can this be simplified?
|
||||||
|
*tmpmat = *RwFrameGetLTM(RwCameraGetFrame((RwCamera*)RWSRCGLOBAL(curCamera)));
|
||||||
|
RwV3dNegate(&tmpmat->right, &tmpmat->right);
|
||||||
|
tmpmat->flags = 0;
|
||||||
|
tmpmat->pos.x = 0.0f;
|
||||||
|
tmpmat->pos.y = 0.0f;
|
||||||
|
tmpmat->pos.z = 0.0f;
|
||||||
|
RwMatrixMultiply(envmat, tmpmat, envframemat);
|
||||||
|
*tmpmat = *envmat;
|
||||||
|
// important because envframemat can have a translation that we don't like
|
||||||
|
tmpmat->pos.x = 0.0f;
|
||||||
|
tmpmat->pos.y = 0.0f;
|
||||||
|
tmpmat->pos.z = 0.0f;
|
||||||
|
// for some reason we flip in U as well
|
||||||
|
RwMatrixMultiply(envmat, tmpmat, &scalenormal_flipU);
|
||||||
|
|
||||||
|
RwD3D8SetTransform(D3DTS_TEXTURE0+n, envmat);
|
||||||
|
|
||||||
|
RwMatrixDestroy(envmat);
|
||||||
|
RwMatrixDestroy(tmpmat);
|
||||||
|
RwMatrixDestroy(envframemat);
|
||||||
|
}else
|
||||||
|
RwD3D8SetTransform(D3DTS_TEXTURE0+n, &scalenormal);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
_rpMatFXD3D8AtomicMatFXEnvRender_ps2(RxD3D8InstanceData *inst, int flags, int sel, RwTexture *texture, RwTexture *envMap)
|
||||||
|
{
|
||||||
|
MatFX *matfx = *RWPLUGINOFFSET(MatFX*, inst->material, MatFXMaterialDataOffset);
|
||||||
|
MatFXEnv *env = &matfx->fx[sel].e;
|
||||||
|
|
||||||
|
uint8 intens = (uint8)(env->envCoeff*255.0f);
|
||||||
|
|
||||||
|
if(intens == 0 || envMap == nil){
|
||||||
|
if(sel == 0)
|
||||||
|
_rpMatFXD3D8AtomicMatFXDefaultRender(inst, flags, texture);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void*)(inst->vertexAlpha || inst->material->color.alpha != 0xFF));
|
||||||
|
if(flags & (rpGEOMETRYTEXTURED|rpGEOMETRYTEXTURED2) && texture)
|
||||||
|
RwD3D8SetTexture(texture, 0);
|
||||||
|
else
|
||||||
|
RwD3D8SetTexture(nil, 0);
|
||||||
|
RwD3D8SetVertexShader(inst->vertexShader);
|
||||||
|
RwD3D8SetStreamSource(0, inst->vertexBuffer, inst->stride);
|
||||||
|
RwD3D8SetIndices(inst->indexBuffer, inst->baseIndex);
|
||||||
|
if(inst->indexBuffer)
|
||||||
|
RwD3D8DrawIndexedPrimitive(inst->primType, 0, inst->numVertices, 0, inst->numIndices);
|
||||||
|
else
|
||||||
|
RwD3D8DrawPrimitive(inst->primType, inst->baseIndex, inst->numVertices);
|
||||||
|
|
||||||
|
// Effect pass
|
||||||
|
|
||||||
|
ApplyEnvMapTextureMatrix(envMap, 0, env->envFrame);
|
||||||
|
RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void*)TRUE);
|
||||||
|
RwUInt32 src, dst, lighting, zwrite, fog, fogcol;
|
||||||
|
RwRenderStateGet(rwRENDERSTATESRCBLEND, &src);
|
||||||
|
RwRenderStateGet(rwRENDERSTATEDESTBLEND, &dst);
|
||||||
|
|
||||||
|
// This is of course not using framebuffer alpha,
|
||||||
|
// but if the diffuse texture had no alpha, the result should actually be rather the same
|
||||||
|
if(env->envFBalpha)
|
||||||
|
RwRenderStateSet(rwRENDERSTATESRCBLEND, (void*)rwBLENDSRCALPHA);
|
||||||
|
else
|
||||||
|
RwRenderStateSet(rwRENDERSTATESRCBLEND, (void*)rwBLENDONE);
|
||||||
|
RwRenderStateSet(rwRENDERSTATEDESTBLEND, (void*)rwBLENDONE);
|
||||||
|
RwD3D8GetRenderState(D3DRS_LIGHTING, &lighting);
|
||||||
|
RwD3D8GetRenderState(D3DRS_ZWRITEENABLE, &zwrite);
|
||||||
|
RwD3D8GetRenderState(D3DRS_FOGENABLE, &fog);
|
||||||
|
RwD3D8SetRenderState(D3DRS_ZWRITEENABLE, FALSE);
|
||||||
|
if(fog){
|
||||||
|
RwD3D8GetRenderState(D3DRS_FOGCOLOR, &fogcol);
|
||||||
|
RwD3D8SetRenderState(D3DRS_FOGCOLOR, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
D3DCOLOR texfactor = D3DCOLOR_RGBA(intens, intens, intens, intens);
|
||||||
|
RwD3D8SetRenderState(D3DRS_TEXTUREFACTOR, texfactor);
|
||||||
|
RwD3D8SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_MODULATE);
|
||||||
|
RwD3D8SetTextureStageState(1, D3DTSS_COLORARG1, D3DTA_CURRENT);
|
||||||
|
RwD3D8SetTextureStageState(1, D3DTSS_COLORARG2, D3DTA_TFACTOR);
|
||||||
|
// alpha unused
|
||||||
|
//RwD3D8SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1);
|
||||||
|
//RwD3D8SetTextureStageState(1, D3DTSS_ALPHAARG1, D3DTA_CURRENT);
|
||||||
|
//RwD3D8SetTextureStageState(1, D3DTSS_ALPHAARG2, D3DTA_TFACTOR);
|
||||||
|
|
||||||
|
if(inst->indexBuffer)
|
||||||
|
RwD3D8DrawIndexedPrimitive(inst->primType, 0, inst->numVertices, 0, inst->numIndices);
|
||||||
|
else
|
||||||
|
RwD3D8DrawPrimitive(inst->primType, inst->baseIndex, inst->numVertices);
|
||||||
|
|
||||||
|
// Reset states
|
||||||
|
|
||||||
|
RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void*)FALSE);
|
||||||
|
RwRenderStateSet(rwRENDERSTATESRCBLEND, (void*)src);
|
||||||
|
RwRenderStateSet(rwRENDERSTATEDESTBLEND, (void*)dst);
|
||||||
|
RwD3D8SetRenderState(D3DRS_LIGHTING, lighting);
|
||||||
|
RwD3D8SetRenderState(D3DRS_ZWRITEENABLE, zwrite);
|
||||||
|
if(fog)
|
||||||
|
RwD3D8SetRenderState(D3DRS_FOGCOLOR, fogcol);
|
||||||
|
RwD3D8SetTextureStageState(1, D3DTSS_COLOROP, D3DTOP_DISABLE);
|
||||||
|
RwD3D8SetTextureStageState(1, D3DTSS_ALPHAOP, D3DTOP_DISABLE);
|
||||||
|
RwD3D8SetTextureStageState(0, D3DTSS_TEXTURETRANSFORMFLAGS, 0);
|
||||||
|
RwD3D8SetTextureStageState(0, D3DTSS_TEXCOORDINDEX, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
STARTPATCHES
|
||||||
|
InjectHook(0x5CF6C0, _rpMatFXD3D8AtomicMatFXEnvRender_ps2, PATCH_JUMP);
|
||||||
|
ENDPATCHES
|
||||||
|
|
||||||
|
#endif
|
@ -250,7 +250,6 @@ void
|
|||||||
CStreaming::Update(void)
|
CStreaming::Update(void)
|
||||||
{
|
{
|
||||||
CEntity *train;
|
CEntity *train;
|
||||||
CVector playerPos;
|
|
||||||
CStreamingInfo *si, *prev;
|
CStreamingInfo *si, *prev;
|
||||||
bool requestedSubway = false;
|
bool requestedSubway = false;
|
||||||
|
|
||||||
@ -280,8 +279,7 @@ CStreaming::Update(void)
|
|||||||
ms_numModelsRequested < 5 &&
|
ms_numModelsRequested < 5 &&
|
||||||
!CRenderer::m_loadingPriority){
|
!CRenderer::m_loadingPriority){
|
||||||
StreamVehiclesAndPeds();
|
StreamVehiclesAndPeds();
|
||||||
FindPlayerCoors(playerPos);
|
StreamZoneModels(FindPlayerCoors());
|
||||||
StreamZoneModels(playerPos);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
LoadRequestedModels();
|
LoadRequestedModels();
|
||||||
|
31
src/Text.cpp
31
src/Text.cpp
@ -15,7 +15,7 @@ CText::CText(void)
|
|||||||
keyArray.numEntries = 0;
|
keyArray.numEntries = 0;
|
||||||
data.chars = nil;
|
data.chars = nil;
|
||||||
data.numChars = 0;
|
data.numChars = 0;
|
||||||
unknown = 101; // What's this? version number?
|
encoding = 101;
|
||||||
memset(WideErrorString, 0, sizeof(WideErrorString));
|
memset(WideErrorString, 0, sizeof(WideErrorString));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -96,6 +96,25 @@ CText::Get(const char *key)
|
|||||||
return keyArray.Search(key);
|
return keyArray.Search(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
wchar
|
||||||
|
CText::GetUpperCase(wchar c)
|
||||||
|
{
|
||||||
|
// TODO: do this depending on encoding
|
||||||
|
if(islower(c))
|
||||||
|
return toupper(c);
|
||||||
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CText::UpperCase(wchar *s)
|
||||||
|
{
|
||||||
|
while(*s){
|
||||||
|
*s = GetUpperCase(*s);
|
||||||
|
s++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
CKeyArray::Load(uint32 length, uint8 *data, int *offset)
|
CKeyArray::Load(uint32 length, uint8 *data, int *offset)
|
||||||
{
|
{
|
||||||
@ -186,9 +205,15 @@ CData::Unload(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
AsciiToUnicode(const char *cs, uint16 *ws)
|
AsciiToUnicode(const char *src, uint16 *dst)
|
||||||
{
|
{
|
||||||
while((*ws++ = *cs++) != '\0');
|
while((*dst++ = *src++) != '\0');
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
TextCopy(wchar *dst, const wchar *src)
|
||||||
|
{
|
||||||
|
while((*dst++ = *src++) != '\0');
|
||||||
}
|
}
|
||||||
|
|
||||||
STARTPATCHES
|
STARTPATCHES
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
void AsciiToUnicode(const char *cs, wchar *ws);
|
void AsciiToUnicode(const char *src, wchar *dst);
|
||||||
|
void TextCopy(wchar *dst, const wchar *src);
|
||||||
|
|
||||||
struct CKeyEntry
|
struct CKeyEntry
|
||||||
{
|
{
|
||||||
@ -37,13 +38,15 @@ class CText
|
|||||||
{
|
{
|
||||||
CKeyArray keyArray;
|
CKeyArray keyArray;
|
||||||
CData data;
|
CData data;
|
||||||
int8 unknown;
|
int8 encoding;
|
||||||
public:
|
public:
|
||||||
CText(void);
|
CText(void);
|
||||||
~CText(void);
|
~CText(void);
|
||||||
void Load(void);
|
void Load(void);
|
||||||
void Unload(void);
|
void Unload(void);
|
||||||
wchar *Get(const char *key);
|
wchar *Get(const char *key);
|
||||||
|
wchar GetUpperCase(wchar c);
|
||||||
|
void UpperCase(wchar *s);
|
||||||
};
|
};
|
||||||
|
|
||||||
extern CText &TheText;
|
extern CText &TheText;
|
||||||
|
141
src/World.cpp
141
src/World.cpp
@ -2,13 +2,16 @@
|
|||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
#include "Entity.h"
|
#include "Entity.h"
|
||||||
#include "Ped.h"
|
#include "Ped.h"
|
||||||
|
#include "PlayerPed.h"
|
||||||
|
#include "Vehicle.h"
|
||||||
#include "Object.h"
|
#include "Object.h"
|
||||||
|
#include "Camera.h"
|
||||||
|
#include "DMAudio.h"
|
||||||
|
#include "CarCtrl.h"
|
||||||
#include "Garages.h"
|
#include "Garages.h"
|
||||||
#include "TempColModels.h"
|
#include "TempColModels.h"
|
||||||
#include "World.h"
|
#include "World.h"
|
||||||
|
|
||||||
WRAPPER void CWorld::Add(CEntity *entity) { EAXJMP(0x4AE930); }
|
|
||||||
|
|
||||||
CPtrList *CWorld::ms_bigBuildingsList = (CPtrList*)0x6FAB60;
|
CPtrList *CWorld::ms_bigBuildingsList = (CPtrList*)0x6FAB60;
|
||||||
CPtrList &CWorld::ms_listMovingEntityPtrs = *(CPtrList*)0x8F433C;
|
CPtrList &CWorld::ms_listMovingEntityPtrs = *(CPtrList*)0x8F433C;
|
||||||
CSector (*CWorld::ms_aSectors)[NUMSECTORS_X] = (CSector (*)[NUMSECTORS_Y])0x665608;
|
CSector (*CWorld::ms_aSectors)[NUMSECTORS_X] = (CSector (*)[NUMSECTORS_Y])0x665608;
|
||||||
@ -23,6 +26,41 @@ bool &CWorld::bSecondShift = *(bool*)0x95CD54;
|
|||||||
bool &CWorld::bForceProcessControl = *(bool*)0x95CD6C;
|
bool &CWorld::bForceProcessControl = *(bool*)0x95CD6C;
|
||||||
bool &CWorld::bProcessCutsceneOnly = *(bool*)0x95CD8B;
|
bool &CWorld::bProcessCutsceneOnly = *(bool*)0x95CD8B;
|
||||||
|
|
||||||
|
void
|
||||||
|
CWorld::Add(CEntity *ent)
|
||||||
|
{
|
||||||
|
if(ent->IsVehicle() || ent->IsPed())
|
||||||
|
DMAudio.SetEntityStatus(((CPhysical*)ent)->m_audioEntityId, true);
|
||||||
|
|
||||||
|
if(ent->bIsBIGBuilding)
|
||||||
|
ms_bigBuildingsList[ent->m_level].InsertItem(ent);
|
||||||
|
else
|
||||||
|
ent->Add();
|
||||||
|
|
||||||
|
if(ent->IsBuilding() || ent->IsDummy())
|
||||||
|
return;
|
||||||
|
|
||||||
|
if(!ent->bIsStatic)
|
||||||
|
((CPhysical*)ent)->AddToMovingList();
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CWorld::Remove(CEntity *ent)
|
||||||
|
{
|
||||||
|
if(ent->IsVehicle() || ent->IsPed())
|
||||||
|
DMAudio.SetEntityStatus(((CPhysical*)ent)->m_audioEntityId, false);
|
||||||
|
|
||||||
|
if(ent->bIsBIGBuilding)
|
||||||
|
ms_bigBuildingsList[ent->m_level].RemoveItem(ent);
|
||||||
|
else
|
||||||
|
ent->Remove();
|
||||||
|
|
||||||
|
if(ent->IsBuilding() || ent->IsDummy())
|
||||||
|
return;
|
||||||
|
|
||||||
|
if(!ent->bIsStatic)
|
||||||
|
((CPhysical*)ent)->RemoveFromMovingList();
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
CWorld::ClearScanCodes(void)
|
CWorld::ClearScanCodes(void)
|
||||||
@ -571,7 +609,98 @@ CWorld::FindRoofZFor3DCoord(float x, float y, float z, bool *found)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CPlayerPed*
|
||||||
|
FindPlayerPed(void)
|
||||||
|
{
|
||||||
|
return CWorld::Players[CWorld::PlayerInFocus].m_pPed;
|
||||||
|
}
|
||||||
|
|
||||||
|
CVehicle*
|
||||||
|
FindPlayerVehicle(void)
|
||||||
|
{
|
||||||
|
CPlayerPed *ped = CWorld::Players[CWorld::PlayerInFocus].m_pPed;
|
||||||
|
if(ped->bInVehicle && ped->m_pMyVehicle)
|
||||||
|
return ped->m_pMyVehicle;
|
||||||
|
else
|
||||||
|
return nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
CVehicle*
|
||||||
|
FindPlayerTrain(void)
|
||||||
|
{
|
||||||
|
if(FindPlayerVehicle() && FindPlayerVehicle()->IsTrain())
|
||||||
|
return FindPlayerVehicle();
|
||||||
|
else
|
||||||
|
return nil;
|
||||||
|
}
|
||||||
|
|
||||||
|
CEntity*
|
||||||
|
FindPlayerEntity(void)
|
||||||
|
{
|
||||||
|
CPlayerPed *ped = CWorld::Players[CWorld::PlayerInFocus].m_pPed;
|
||||||
|
if(ped->bInVehicle && ped->m_pMyVehicle)
|
||||||
|
return ped->m_pMyVehicle;
|
||||||
|
else
|
||||||
|
return ped;
|
||||||
|
}
|
||||||
|
|
||||||
|
CVector
|
||||||
|
FindPlayerCoors(void)
|
||||||
|
{
|
||||||
|
CPlayerPed *ped = CWorld::Players[CWorld::PlayerInFocus].m_pPed;
|
||||||
|
if(ped->bInVehicle && ped->m_pMyVehicle)
|
||||||
|
return ped->m_pMyVehicle->GetPosition();
|
||||||
|
else
|
||||||
|
return ped->GetPosition();
|
||||||
|
}
|
||||||
|
|
||||||
|
CVector&
|
||||||
|
FindPlayerSpeed(void)
|
||||||
|
{
|
||||||
|
CPlayerPed *ped = CWorld::Players[CWorld::PlayerInFocus].m_pPed;
|
||||||
|
if(ped->bInVehicle && ped->m_pMyVehicle)
|
||||||
|
return ped->m_pMyVehicle->m_vecMoveSpeed;
|
||||||
|
else
|
||||||
|
return ped->m_vecMoveSpeed;
|
||||||
|
}
|
||||||
|
|
||||||
|
CVector&
|
||||||
|
FindPlayerCentreOfWorld(int32 player)
|
||||||
|
{
|
||||||
|
if(CCarCtrl::bCarsGeneratedAroundCamera)
|
||||||
|
return TheCamera.GetPosition();
|
||||||
|
if(CWorld::Players[player].m_pRemoteVehicle)
|
||||||
|
return CWorld::Players[player].m_pRemoteVehicle->GetPosition();
|
||||||
|
if(FindPlayerVehicle())
|
||||||
|
return FindPlayerVehicle()->GetPosition();
|
||||||
|
return CWorld::Players[player].m_pPed->GetPosition();
|
||||||
|
}
|
||||||
|
|
||||||
|
CVector&
|
||||||
|
FindPlayerCentreOfWorld_NoSniperShift(void)
|
||||||
|
{
|
||||||
|
if(CCarCtrl::bCarsGeneratedAroundCamera)
|
||||||
|
return TheCamera.GetPosition();
|
||||||
|
if(CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle)
|
||||||
|
return CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle->GetPosition();
|
||||||
|
if(FindPlayerVehicle())
|
||||||
|
return FindPlayerVehicle()->GetPosition();
|
||||||
|
return CWorld::Players[CWorld::PlayerInFocus].m_pPed->GetPosition();
|
||||||
|
}
|
||||||
|
|
||||||
|
float
|
||||||
|
FindPlayerHeading(void)
|
||||||
|
{
|
||||||
|
if(CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle)
|
||||||
|
return CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle->GetForward().Heading();
|
||||||
|
if(FindPlayerVehicle())
|
||||||
|
return FindPlayerVehicle()->GetForward().Heading();
|
||||||
|
return CWorld::Players[CWorld::PlayerInFocus].m_pPed->GetForward().Heading();
|
||||||
|
}
|
||||||
|
|
||||||
STARTPATCHES
|
STARTPATCHES
|
||||||
|
InjectHook(0x4AE930, CWorld::Add, PATCH_JUMP);
|
||||||
|
InjectHook(0x4AE9D0, CWorld::Remove, PATCH_JUMP);
|
||||||
InjectHook(0x4B1F60, CWorld::ClearScanCodes, PATCH_JUMP);
|
InjectHook(0x4B1F60, CWorld::ClearScanCodes, PATCH_JUMP);
|
||||||
InjectHook(0x4AF970, CWorld::ProcessLineOfSight, PATCH_JUMP);
|
InjectHook(0x4AF970, CWorld::ProcessLineOfSight, PATCH_JUMP);
|
||||||
InjectHook(0x4B0A80, CWorld::ProcessLineOfSightSector, PATCH_JUMP);
|
InjectHook(0x4B0A80, CWorld::ProcessLineOfSightSector, PATCH_JUMP);
|
||||||
@ -587,11 +716,3 @@ STARTPATCHES
|
|||||||
InjectHook(0x4B3AE0, CWorld::FindGroundZFor3DCoord, PATCH_JUMP);
|
InjectHook(0x4B3AE0, CWorld::FindGroundZFor3DCoord, PATCH_JUMP);
|
||||||
InjectHook(0x4B3B50, CWorld::FindRoofZFor3DCoord, PATCH_JUMP);
|
InjectHook(0x4B3B50, CWorld::FindRoofZFor3DCoord, PATCH_JUMP);
|
||||||
ENDPATCHES
|
ENDPATCHES
|
||||||
|
|
||||||
WRAPPER CPlayerPed *FindPlayerPed(void) { EAXJMP(0x4A1150); }
|
|
||||||
WRAPPER CVector &FindPlayerCoors(CVector &v) { EAXJMP(0x4A1030); }
|
|
||||||
WRAPPER CVehicle *FindPlayerVehicle(void) { EAXJMP(0x4A10C0); }
|
|
||||||
WRAPPER CVehicle *FindPlayerTrain(void) { EAXJMP(0x4A1120); }
|
|
||||||
WRAPPER CVector &FindPlayerSpeed(void) { EAXJMP(0x4A1090); }
|
|
||||||
WRAPPER CVector FindPlayerCentreOfWorld_NoSniperShift(void) { EAXJMP(0x4A11C0); }
|
|
||||||
WRAPPER float FindPlayerHeading(void) { EAXJMP(0x4A1220); }
|
|
||||||
|
@ -68,6 +68,7 @@ public:
|
|||||||
static bool &bProcessCutsceneOnly;
|
static bool &bProcessCutsceneOnly;
|
||||||
|
|
||||||
static void Add(CEntity *entity);
|
static void Add(CEntity *entity);
|
||||||
|
static void Remove(CEntity *ent);
|
||||||
|
|
||||||
static CSector *GetSector(int x, int y) { return &ms_aSectors[y][x]; }
|
static CSector *GetSector(int x, int y) { return &ms_aSectors[y][x]; }
|
||||||
static CPtrList &GetBigBuildingList(eLevelName i) { return ms_bigBuildingsList[i]; }
|
static CPtrList &GetBigBuildingList(eLevelName i) { return ms_bigBuildingsList[i]; }
|
||||||
@ -108,9 +109,11 @@ public:
|
|||||||
class CPlayerPed;
|
class CPlayerPed;
|
||||||
class CVehicle;
|
class CVehicle;
|
||||||
CPlayerPed *FindPlayerPed(void);
|
CPlayerPed *FindPlayerPed(void);
|
||||||
CVector &FindPlayerCoors(CVector &v);
|
|
||||||
CVehicle *FindPlayerVehicle(void);
|
CVehicle *FindPlayerVehicle(void);
|
||||||
CVehicle *FindPlayerTrain(void);
|
CVehicle *FindPlayerTrain(void);
|
||||||
|
CEntity *FindPlayerEntity(void);
|
||||||
|
CVector FindPlayerCoors(void);
|
||||||
CVector &FindPlayerSpeed(void);
|
CVector &FindPlayerSpeed(void);
|
||||||
CVector FindPlayerCentreOfWorld_NoSniperShift(void);
|
CVector &FindPlayerCentreOfWorld(int32 player);
|
||||||
|
CVector &FindPlayerCentreOfWorld_NoSniperShift(void);
|
||||||
float FindPlayerHeading(void);
|
float FindPlayerHeading(void);
|
||||||
|
@ -114,7 +114,7 @@ void
|
|||||||
CTheZones::Update(void)
|
CTheZones::Update(void)
|
||||||
{
|
{
|
||||||
CVector pos;
|
CVector pos;
|
||||||
FindPlayerCoors(pos);
|
pos = FindPlayerCoors();
|
||||||
m_pPlayersZone = FindSmallestZonePosition(&pos);
|
m_pPlayersZone = FindSmallestZonePosition(&pos);
|
||||||
m_CurrLevel = GetLevelFromPosition(pos);
|
m_CurrLevel = GetLevelFromPosition(pos);
|
||||||
}
|
}
|
||||||
|
@ -25,5 +25,5 @@ WRAPPER uint8 cDMAudio::IsMP3RadioChannelAvailable() { EAXJMP(0x57C9F0); }
|
|||||||
WRAPPER void cDMAudio::SetEffectsFadeVol(uint8) { EAXJMP(0x57C8F0); }
|
WRAPPER void cDMAudio::SetEffectsFadeVol(uint8) { EAXJMP(0x57C8F0); }
|
||||||
WRAPPER void cDMAudio::SetMusicFadeVol(uint8) { EAXJMP(0x57C920); }
|
WRAPPER void cDMAudio::SetMusicFadeVol(uint8) { EAXJMP(0x57C920); }
|
||||||
WRAPPER int32 cDMAudio::CreateEntity(int, void*) { EAXJMP(0x57C7C0); }
|
WRAPPER int32 cDMAudio::CreateEntity(int, void*) { EAXJMP(0x57C7C0); }
|
||||||
WRAPPER void cDMAudio::SetEntityStatus(int32, int8) { EAXJMP(0x57C810); }
|
WRAPPER void cDMAudio::SetEntityStatus(int32 id, uint8 enable) { EAXJMP(0x57C810); }
|
||||||
WRAPPER void cDMAudio::SetRadioInCar(int32) { EAXJMP(0x57CE60); }
|
WRAPPER void cDMAudio::SetRadioInCar(int32) { EAXJMP(0x57CE60); }
|
@ -193,7 +193,7 @@ public:
|
|||||||
void SetEffectsFadeVol(uint8);
|
void SetEffectsFadeVol(uint8);
|
||||||
void SetMusicFadeVol(uint8);
|
void SetMusicFadeVol(uint8);
|
||||||
int32 CreateEntity(int, void*);
|
int32 CreateEntity(int, void*);
|
||||||
void SetEntityStatus(int32, int8);
|
void SetEntityStatus(int32 id, uint8 enable);
|
||||||
void SetRadioInCar(int32);
|
void SetRadioInCar(int32);
|
||||||
uint8 IsMP3RadioChannelAvailable();
|
uint8 IsMP3RadioChannelAvailable();
|
||||||
|
|
||||||
|
@ -77,3 +77,5 @@ enum Config {
|
|||||||
#define NO_MOVIES
|
#define NO_MOVIES
|
||||||
//#define USE_MY_DOCUMENTS
|
//#define USE_MY_DOCUMENTS
|
||||||
#define NASTY_GAME
|
#define NASTY_GAME
|
||||||
|
#define PS2_MATFX
|
||||||
|
|
||||||
|
@ -3,6 +3,7 @@
|
|||||||
#include "CarCtrl.h"
|
#include "CarCtrl.h"
|
||||||
|
|
||||||
int &CCarCtrl::NumLawEnforcerCars = *(int*)0x8F1B38;
|
int &CCarCtrl::NumLawEnforcerCars = *(int*)0x8F1B38;
|
||||||
|
bool &CCarCtrl::bCarsGeneratedAroundCamera = *(bool*)0x95CD8A;
|
||||||
|
|
||||||
WRAPPER void CCarCtrl::SwitchVehicleToRealPhysics(CVehicle*) { EAXJMP(0x41F7F0); }
|
WRAPPER void CCarCtrl::SwitchVehicleToRealPhysics(CVehicle*) { EAXJMP(0x41F7F0); }
|
||||||
WRAPPER void CCarCtrl::AddToCarArray(int32 id, int32 vehclass) { EAXJMP(0x4182F0); }
|
WRAPPER void CCarCtrl::AddToCarArray(int32 id, int32 vehclass) { EAXJMP(0x4182F0); }
|
||||||
|
@ -11,4 +11,5 @@ public:
|
|||||||
static int32 ChooseCarModel(int32 vehclass);
|
static int32 ChooseCarModel(int32 vehclass);
|
||||||
|
|
||||||
static int32 &NumLawEnforcerCars;
|
static int32 &NumLawEnforcerCars;
|
||||||
|
static bool &bCarsGeneratedAroundCamera;
|
||||||
};
|
};
|
||||||
|
@ -1,8 +1,10 @@
|
|||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
|
#include "Game.h"
|
||||||
#include "Population.h"
|
#include "Population.h"
|
||||||
|
|
||||||
PedGroup *CPopulation::ms_pPedGroups = (PedGroup*)0x6E9248;
|
PedGroup *CPopulation::ms_pPedGroups = (PedGroup*)0x6E9248;
|
||||||
bool &CPopulation::ms_bGivePedsWeapons = *(bool*)0x95CCF6;
|
bool &CPopulation::ms_bGivePedsWeapons = *(bool*)0x95CCF6;
|
||||||
|
|
||||||
WRAPPER void CPopulation::UpdatePedCount(uint32, bool) { EAXJMP(0x4F5A60); }
|
WRAPPER void CPopulation::UpdatePedCount(uint32, bool) { EAXJMP(0x4F5A60); }
|
||||||
|
WRAPPER void CPopulation::DealWithZoneChange(eLevelName oldLevel, eLevelName newLevel, bool) { EAXJMP(0x4F6200); }
|
||||||
|
@ -14,4 +14,5 @@ public:
|
|||||||
static bool &ms_bGivePedsWeapons;
|
static bool &ms_bGivePedsWeapons;
|
||||||
|
|
||||||
static void UpdatePedCount(uint32, bool);
|
static void UpdatePedCount(uint32, bool);
|
||||||
|
static void DealWithZoneChange(eLevelName oldLevel, eLevelName newLevel, bool);
|
||||||
};
|
};
|
||||||
|
@ -165,6 +165,8 @@ void CReplay::Init(void)
|
|||||||
bDoLoadSceneWhenDone = false;
|
bDoLoadSceneWhenDone = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
WRAPPER void CReplay::EmptyReplayBuffer(void) { EAXJMP(0x595BD0); }
|
||||||
|
|
||||||
void CReplay::DisableReplays(void)
|
void CReplay::DisableReplays(void)
|
||||||
{
|
{
|
||||||
bReplayEnabled = false;
|
bReplayEnabled = false;
|
||||||
@ -212,7 +214,7 @@ void CReplay::RecordThisFrame(void)
|
|||||||
tGeneralPacket* general = (tGeneralPacket*)&Record.m_pBase[Record.m_nOffset];
|
tGeneralPacket* general = (tGeneralPacket*)&Record.m_pBase[Record.m_nOffset];
|
||||||
general->type = REPLAYPACKET_GENERAL;
|
general->type = REPLAYPACKET_GENERAL;
|
||||||
general->camera_pos.CopyOnlyMatrix(&TheCamera.GetMatrix());
|
general->camera_pos.CopyOnlyMatrix(&TheCamera.GetMatrix());
|
||||||
FindPlayerCoors(general->player_pos);
|
general->player_pos = FindPlayerCoors();
|
||||||
general->in_rcvehicle = CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle ? true : false;
|
general->in_rcvehicle = CWorld::Players[CWorld::PlayerInFocus].m_pRemoteVehicle ? true : false;
|
||||||
Record.m_nOffset += sizeof(*general);
|
Record.m_nOffset += sizeof(*general);
|
||||||
tClockPacket* clock = (tClockPacket*)&Record.m_pBase[Record.m_nOffset];
|
tClockPacket* clock = (tClockPacket*)&Record.m_pBase[Record.m_nOffset];
|
||||||
@ -601,8 +603,8 @@ void CReplay::RestoreStuffFromMem(void)
|
|||||||
ped->m_modelIndex = -1;
|
ped->m_modelIndex = -1;
|
||||||
ped->SetModelIndex(mi);
|
ped->SetModelIndex(mi);
|
||||||
ped->m_pVehicleAnim = 0;
|
ped->m_pVehicleAnim = 0;
|
||||||
ped->uAudioEntityId = DMAudio.CreateEntity(0, ped);
|
ped->m_audioEntityId = DMAudio.CreateEntity(0, ped);
|
||||||
DMAudio.SetEntityStatus(ped->uAudioEntityId, 1);
|
DMAudio.SetEntityStatus(ped->m_audioEntityId, true);
|
||||||
CPopulation::UpdatePedCount(ped->m_nPedType, false);
|
CPopulation::UpdatePedCount(ped->m_nPedType, false);
|
||||||
if (ped->m_wepModelID >= 0)
|
if (ped->m_wepModelID >= 0)
|
||||||
ped->AddWeaponModel(ped->m_wepModelID);
|
ped->AddWeaponModel(ped->m_wepModelID);
|
||||||
@ -639,8 +641,8 @@ void CReplay::RestoreStuffFromMem(void)
|
|||||||
car->SetDoorDamage(16, 4, true); /* DOOR_BACK_LEFT */
|
car->SetDoorDamage(16, 4, true); /* DOOR_BACK_LEFT */
|
||||||
car->SetDoorDamage(12, 5, true); /* DOOR_BACK_RIGHT */
|
car->SetDoorDamage(12, 5, true); /* DOOR_BACK_RIGHT */
|
||||||
}
|
}
|
||||||
vehicle->uAudioEntityId = DMAudio.CreateEntity(0, vehicle);
|
vehicle->m_audioEntityId = DMAudio.CreateEntity(0, vehicle);
|
||||||
DMAudio.SetEntityStatus(vehicle->uAudioEntityId, 1);
|
DMAudio.SetEntityStatus(vehicle->m_audioEntityId, true);
|
||||||
CCarCtrl::UpdateCarCount(vehicle, false);
|
CCarCtrl::UpdateCarCount(vehicle, false);
|
||||||
if ((mi == MI_AIRTRAIN || mi == MI_DEADDODO) && vehicle->m_rwObject){
|
if ((mi == MI_AIRTRAIN || mi == MI_DEADDODO) && vehicle->m_rwObject){
|
||||||
CVehicleModelInfo* info = (CVehicleModelInfo*)CModelInfo::GetModelInfo(mi);
|
CVehicleModelInfo* info = (CVehicleModelInfo*)CModelInfo::GetModelInfo(mi);
|
||||||
|
@ -244,6 +244,7 @@ private:
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
static void Init(void);
|
static void Init(void);
|
||||||
|
static void EmptyReplayBuffer(void);
|
||||||
static void DisableReplays(void);
|
static void DisableReplays(void);
|
||||||
static void EnableReplays(void);
|
static void EnableReplays(void);
|
||||||
static void Update(void);
|
static void Update(void);
|
||||||
|
@ -4,18 +4,18 @@
|
|||||||
enum eCrimeType
|
enum eCrimeType
|
||||||
{
|
{
|
||||||
CRIME_NONE,
|
CRIME_NONE,
|
||||||
CRIME_SHOT_FIRED,
|
CRIME_POSSESSION_GUN,
|
||||||
CRIME_PED_FIGHT,
|
CRIME_HIT_PED,
|
||||||
CRIME_COP_FIGHT,
|
CRIME_HIT_COP,
|
||||||
CRIME_DAMAGED_PED,
|
CRIME_SHOOT_PED,
|
||||||
CRIME_DAMAGED_COP,
|
CRIME_SHOOT_COP,
|
||||||
CRIME_CAR_THEFT,
|
CRIME_STEAL_CAR,
|
||||||
CRIME_CRIME7,
|
CRIME_RUN_REDLIGHT,
|
||||||
CRIME_COP_EVASIVE_DIVE,
|
CRIME_RECKLESS_DRIVING,
|
||||||
CRIME_COP_EVASIVE_DIVE2,
|
CRIME_SPEEDING,
|
||||||
CRIME_PED_RUN_OVER,
|
CRIME_RUNOVER_PED,
|
||||||
CRIME_COP_RUN_OVER,
|
CRIME_RUNOVER_COP,
|
||||||
CRIME_DESTROYED_HELI,
|
CRIME_SHOOT_HELI,
|
||||||
CRIME_PED_BURNED,
|
CRIME_PED_BURNED,
|
||||||
CRIME_COP_BURNED,
|
CRIME_COP_BURNED,
|
||||||
CRIME_VEHICLE_BURNED,
|
CRIME_VEHICLE_BURNED,
|
||||||
|
@ -1,7 +1,57 @@
|
|||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "patcher.h"
|
#include "patcher.h"
|
||||||
#include "Dummy.h"
|
|
||||||
#include "Pools.h"
|
#include "Pools.h"
|
||||||
|
#include "World.h"
|
||||||
|
#include "Dummy.h"
|
||||||
|
|
||||||
void *CDummy::operator new(size_t sz) { return CPools::GetDummyPool()->New(); }
|
void *CDummy::operator new(size_t sz) { return CPools::GetDummyPool()->New(); }
|
||||||
void CDummy::operator delete(void *p, size_t sz) { CPools::GetDummyPool()->Delete((CDummy*)p); }
|
void CDummy::operator delete(void *p, size_t sz) { CPools::GetDummyPool()->Delete((CDummy*)p); }
|
||||||
|
|
||||||
|
void
|
||||||
|
CDummy::Add(void)
|
||||||
|
{
|
||||||
|
int x, xstart, xmid, xend;
|
||||||
|
int y, ystart, ymid, yend;
|
||||||
|
CSector *s;
|
||||||
|
CPtrList *list;
|
||||||
|
|
||||||
|
CRect bounds = GetBoundRect();
|
||||||
|
xstart = CWorld::GetSectorIndexX(bounds.left);
|
||||||
|
xend = CWorld::GetSectorIndexX(bounds.right);
|
||||||
|
xmid = CWorld::GetSectorIndexX((bounds.left + bounds.right)/2.0f);
|
||||||
|
ystart = CWorld::GetSectorIndexY(bounds.top);
|
||||||
|
yend = CWorld::GetSectorIndexY(bounds.bottom);
|
||||||
|
ymid = CWorld::GetSectorIndexY((bounds.top + bounds.bottom)/2.0f);
|
||||||
|
assert(xstart >= 0);
|
||||||
|
assert(xend < NUMSECTORS_X);
|
||||||
|
assert(ystart >= 0);
|
||||||
|
assert(yend < NUMSECTORS_Y);
|
||||||
|
|
||||||
|
for(y = ystart; y <= yend; y++)
|
||||||
|
for(x = xstart; x <= xend; x++){
|
||||||
|
s = CWorld::GetSector(x, y);
|
||||||
|
if(x == xmid && y == ymid)
|
||||||
|
list = &s->m_lists[ENTITYLIST_OBJECTS];
|
||||||
|
else
|
||||||
|
list = &s->m_lists[ENTITYLIST_DUMMIES_OVERLAP];
|
||||||
|
CPtrNode *node = list->InsertItem(this);
|
||||||
|
assert(node);
|
||||||
|
m_entryInfoList.InsertItem(list, node, s);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CDummy::Remove(void)
|
||||||
|
{
|
||||||
|
CEntryInfoNode *node, *next;
|
||||||
|
for(node = m_entryInfoList.first; node; node = next){
|
||||||
|
next = node->next;
|
||||||
|
node->list->DeleteNode(node->listnode);
|
||||||
|
m_entryInfoList.DeleteNode(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
STARTPATCHES
|
||||||
|
InjectHook(0x473860, &CDummy::Add_, PATCH_JUMP);
|
||||||
|
InjectHook(0x473AD0, &CDummy::Remove_, PATCH_JUMP);
|
||||||
|
ENDPATCHES
|
||||||
|
@ -9,9 +9,14 @@ public:
|
|||||||
CEntryInfoList m_entryInfoList;
|
CEntryInfoList m_entryInfoList;
|
||||||
|
|
||||||
CDummy(void) { m_type = ENTITY_TYPE_DUMMY; }
|
CDummy(void) { m_type = ENTITY_TYPE_DUMMY; }
|
||||||
// TODO: Add, Remove
|
void Add(void);
|
||||||
|
void Remove(void);
|
||||||
|
|
||||||
static void *operator new(size_t);
|
static void *operator new(size_t);
|
||||||
static void operator delete(void*, size_t);
|
static void operator delete(void*, size_t);
|
||||||
|
|
||||||
|
// to make patching virtual functions possible
|
||||||
|
void Add_(void) { CDummy::Add(); }
|
||||||
|
void Remove_(void) { CDummy::Remove(); }
|
||||||
};
|
};
|
||||||
static_assert(sizeof(CDummy) == 0x68, "CDummy: error");
|
static_assert(sizeof(CDummy) == 0x68, "CDummy: error");
|
||||||
|
@ -771,9 +771,9 @@ CPed::Attack(void)
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (weaponAnimAssoc->animId == ANIM_WEAPON_BAT_V || weaponAnimAssoc->animId == ANIM_WEAPON_BAT_H) {
|
if (weaponAnimAssoc->animId == ANIM_WEAPON_BAT_V || weaponAnimAssoc->animId == ANIM_WEAPON_BAT_H) {
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, SOUND_WEAPON_BAT_ATTACK, 1.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, SOUND_WEAPON_BAT_ATTACK, 1.0f);
|
||||||
} else if (weaponAnimAssoc->animId == ANIM_FIGHT_PPUNCH) {
|
} else if (weaponAnimAssoc->animId == ANIM_FIGHT_PPUNCH) {
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, SOUND_WEAPON_PUNCH_ATTACK, 0.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, SOUND_WEAPON_PUNCH_ATTACK, 0.0f);
|
||||||
}
|
}
|
||||||
|
|
||||||
weaponAnimAssoc->speed = 0.5f;
|
weaponAnimAssoc->speed = 0.5f;
|
||||||
@ -843,13 +843,13 @@ CPed::Attack(void)
|
|||||||
if (weaponAnimAssoc->currentTime - weaponAnimAssoc->timeStep <= ourWeapon->m_fAnimLoopEnd) {
|
if (weaponAnimAssoc->currentTime - weaponAnimAssoc->timeStep <= ourWeapon->m_fAnimLoopEnd) {
|
||||||
switch (ourWeaponType) {
|
switch (ourWeaponType) {
|
||||||
case WEAPONTYPE_UZI:
|
case WEAPONTYPE_UZI:
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, SOUND_WEAPON_UZI_BULLET_ECHO, 0.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, SOUND_WEAPON_UZI_BULLET_ECHO, 0.0f);
|
||||||
break;
|
break;
|
||||||
case WEAPONTYPE_AK47:
|
case WEAPONTYPE_AK47:
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, SOUND_WEAPON_AK47_BULLET_ECHO, 0.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, SOUND_WEAPON_AK47_BULLET_ECHO, 0.0f);
|
||||||
break;
|
break;
|
||||||
case WEAPONTYPE_M16:
|
case WEAPONTYPE_M16:
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, SOUND_WEAPON_M16_BULLET_ECHO, 0.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, SOUND_WEAPON_M16_BULLET_ECHO, 0.0f);
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
@ -1281,19 +1281,19 @@ CPed::LineUpPedWithCar(PedLineUpPhase phase)
|
|||||||
|
|
||||||
if (m_vehEnterType == VEHICLE_ENTER_FRONT_RIGHT || m_vehEnterType == VEHICLE_ENTER_REAR_RIGHT) {
|
if (m_vehEnterType == VEHICLE_ENTER_FRONT_RIGHT || m_vehEnterType == VEHICLE_ENTER_REAR_RIGHT) {
|
||||||
if (vehIsUpsideDown) {
|
if (vehIsUpsideDown) {
|
||||||
m_fRotationDest = -PI + atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = -PI + veh->GetForward().Heading();
|
||||||
} else if (veh->bIsBus) {
|
} else if (veh->bIsBus) {
|
||||||
m_fRotationDest = 0.5 * PI + atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = 0.5 * PI + veh->GetForward().Heading();
|
||||||
} else {
|
} else {
|
||||||
m_fRotationDest = atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = veh->GetForward().Heading();
|
||||||
}
|
}
|
||||||
} else if (m_vehEnterType == VEHICLE_ENTER_FRONT_LEFT || m_vehEnterType == VEHICLE_ENTER_REAR_LEFT) {
|
} else if (m_vehEnterType == VEHICLE_ENTER_FRONT_LEFT || m_vehEnterType == VEHICLE_ENTER_REAR_LEFT) {
|
||||||
if (vehIsUpsideDown) {
|
if (vehIsUpsideDown) {
|
||||||
m_fRotationDest = atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = veh->GetForward().Heading();
|
||||||
} else if (veh->bIsBus) {
|
} else if (veh->bIsBus) {
|
||||||
m_fRotationDest = -0.5 * PI + atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = -0.5 * PI + veh->GetForward().Heading();
|
||||||
} else {
|
} else {
|
||||||
m_fRotationDest = atan2(-veh->GetForward().x, veh->GetForward().y);
|
m_fRotationDest = veh->GetForward().Heading();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1539,7 +1539,7 @@ CPed::PlayFootSteps(void)
|
|||||||
stepPart = 2;
|
stepPart = 2;
|
||||||
|
|
||||||
if (stepPart != 0) {
|
if (stepPart != 0) {
|
||||||
DMAudio.PlayOneShot(uAudioEntityId, stepPart == 1 ? SOUND_STEP_START : SOUND_STEP_END, 1.0f);
|
DMAudio.PlayOneShot(m_audioEntityId, stepPart == 1 ? SOUND_STEP_START : SOUND_STEP_END, 1.0f);
|
||||||
CVector footPos(0.0f, 0.0f, 0.0f);
|
CVector footPos(0.0f, 0.0f, 0.0f);
|
||||||
|
|
||||||
for (RwFrame *frame = GetNodeFrame(stepPart == 1 ? PED_FOOTL : PED_FOOTR); frame; frame = RwFrameGetParent(frame))
|
for (RwFrame *frame = GetNodeFrame(stepPart == 1 ? PED_FOOTL : PED_FOOTR); frame; frame = RwFrameGetParent(frame))
|
||||||
|
@ -42,7 +42,7 @@ CPhysical::CPhysical(void)
|
|||||||
m_vecDamageNormal = CVector(0.0f, 0.0f, 0.0f);
|
m_vecDamageNormal = CVector(0.0f, 0.0f, 0.0f);
|
||||||
|
|
||||||
bUsesCollision = true;
|
bUsesCollision = true;
|
||||||
uAudioEntityId = -5;
|
m_audioEntityId = -5;
|
||||||
unk1 = 100.0f;
|
unk1 = 100.0f;
|
||||||
m_vecCentreOfMass = CVector(0.0f, 0.0f, 0.0f);
|
m_vecCentreOfMass = CVector(0.0f, 0.0f, 0.0f);
|
||||||
field_EC = 0;
|
field_EC = 0;
|
||||||
|
@ -14,7 +14,7 @@ class CPhysical : public CEntity
|
|||||||
public:
|
public:
|
||||||
// The not properly indented fields haven't been checked properly yet
|
// The not properly indented fields haven't been checked properly yet
|
||||||
|
|
||||||
int uAudioEntityId;
|
int32 m_audioEntityId;
|
||||||
float unk1;
|
float unk1;
|
||||||
CTreadable *m_carTreadable;
|
CTreadable *m_carTreadable;
|
||||||
CTreadable *m_pedTreadable;
|
CTreadable *m_pedTreadable;
|
||||||
@ -58,9 +58,8 @@ public:
|
|||||||
uint8 bHitByTrain : 1; // from nick
|
uint8 bHitByTrain : 1; // from nick
|
||||||
uint8 m_phy_flagA80 : 1;
|
uint8 m_phy_flagA80 : 1;
|
||||||
|
|
||||||
uint8 m_nLastCollType;
|
uint8 m_nLastCollType;
|
||||||
uint8 m_nZoneLevel;
|
uint8 m_nZoneLevel;
|
||||||
uint8 pad[3];
|
|
||||||
|
|
||||||
CPhysical(void);
|
CPhysical(void);
|
||||||
~CPhysical(void);
|
~CPhysical(void);
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#include "Automobile.h"
|
|
||||||
#include "PlayerPed.h"
|
#include "Collision.h"
|
||||||
|
|
||||||
enum eWastedBustedState
|
enum eWastedBustedState
|
||||||
{
|
{
|
||||||
@ -10,10 +10,9 @@ enum eWastedBustedState
|
|||||||
WBSTATE_FAILED_CRITICAL_MISSION,
|
WBSTATE_FAILED_CRITICAL_MISSION,
|
||||||
};
|
};
|
||||||
|
|
||||||
struct CCivilianPed
|
class CVehicle;
|
||||||
{
|
class CPlayerPed;
|
||||||
|
class CCivilianPed;
|
||||||
};
|
|
||||||
|
|
||||||
class CPlayerInfo
|
class CPlayerInfo
|
||||||
{
|
{
|
||||||
@ -22,10 +21,7 @@ public:
|
|||||||
CVehicle *m_pRemoteVehicle;
|
CVehicle *m_pRemoteVehicle;
|
||||||
CColModel m_ColModel;
|
CColModel m_ColModel;
|
||||||
CVehicle *m_pVehicleEx;
|
CVehicle *m_pVehicleEx;
|
||||||
char m_aszPlayerName[70];
|
char m_aPlayerName[70];
|
||||||
private:
|
|
||||||
int8 _pad0[2];
|
|
||||||
public:
|
|
||||||
int32 m_nMoney;
|
int32 m_nMoney;
|
||||||
int32 m_nVisibleMoney;
|
int32 m_nVisibleMoney;
|
||||||
int32 m_nCollectedPackages;
|
int32 m_nCollectedPackages;
|
||||||
@ -40,7 +36,7 @@ public:
|
|||||||
int32 m_nNextSexMoneyUpdateTime;
|
int32 m_nNextSexMoneyUpdateTime;
|
||||||
int32 m_nSexFrequency;
|
int32 m_nSexFrequency;
|
||||||
CCivilianPed *m_pHooker;
|
CCivilianPed *m_pHooker;
|
||||||
int8 m_bWBState; // eWastedBustedState
|
int8 m_WBState; // eWastedBustedState
|
||||||
int8 field_217;
|
int8 field_217;
|
||||||
int8 field_218;
|
int8 field_218;
|
||||||
int8 field_219;
|
int8 field_219;
|
||||||
@ -71,4 +67,4 @@ public:
|
|||||||
RwTexture *m_pSkinTexture;
|
RwTexture *m_pSkinTexture;
|
||||||
};
|
};
|
||||||
|
|
||||||
static_assert(sizeof(CPlayerInfo) == 0x13C, "CPlayerPed: error");
|
static_assert(sizeof(CPlayerInfo) == 0x13C, "CPlayerInfo: error");
|
||||||
|
@ -2,10 +2,19 @@
|
|||||||
|
|
||||||
#include "Vehicle.h"
|
#include "Vehicle.h"
|
||||||
|
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
TRAIN_DOOR_STATE2 = 2
|
||||||
|
};
|
||||||
|
|
||||||
class CTrain : public CVehicle
|
class CTrain : public CVehicle
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
// 0x288
|
// 0x288
|
||||||
uint8 stuff[92];
|
uint8 stuff1[20];
|
||||||
|
uint8 m_trackId;
|
||||||
|
uint8 stuff2[7];
|
||||||
|
int16 m_doorState;
|
||||||
|
uint8 stuff3[62];
|
||||||
};
|
};
|
||||||
static_assert(sizeof(CTrain) == 0x2E4, "CTrain: error");
|
static_assert(sizeof(CTrain) == 0x2E4, "CTrain: error");
|
||||||
|
62
src/main.cpp
62
src/main.cpp
@ -90,6 +90,13 @@ void PrintGameVersion();
|
|||||||
|
|
||||||
RwRGBA gColourTop;
|
RwRGBA gColourTop;
|
||||||
|
|
||||||
|
void
|
||||||
|
InitialiseGame(void)
|
||||||
|
{
|
||||||
|
LoadingScreen(nil, nil, "loadsc0");
|
||||||
|
CGame::Initialise("DATA\\GTA3.DAT");
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
Idle(void *arg)
|
Idle(void *arg)
|
||||||
{
|
{
|
||||||
@ -591,6 +598,61 @@ ResetLoadingScreenBar(void)
|
|||||||
NumberOfChunksLoaded = 0.0f;
|
NumberOfChunksLoaded = 0.0f;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
LoadingIslandScreen(const char *levelName)
|
||||||
|
{
|
||||||
|
CSprite2d *splash;
|
||||||
|
wchar *name;
|
||||||
|
char str[100];
|
||||||
|
wchar wstr[80];
|
||||||
|
CRGBA col;
|
||||||
|
|
||||||
|
splash = LoadSplash(nil);
|
||||||
|
name = TheText.Get(levelName);
|
||||||
|
if(!DoRWStuffStartOfFrame(0, 0, 0, 0, 0, 0, 255))
|
||||||
|
return;
|
||||||
|
|
||||||
|
CSprite2d::SetRecipNearClip();
|
||||||
|
CSprite2d::InitPerFrame();
|
||||||
|
CFont::InitPerFrame();
|
||||||
|
DefinedState();
|
||||||
|
col = CRGBA(255, 255, 255, 255);
|
||||||
|
splash->Draw(CRect(0.0f, 0.0f, SCREENW, SCREENH), col, col, col, col);
|
||||||
|
CFont::SetBackgroundOff();
|
||||||
|
CFont::SetScale(1.5f, 1.5f);
|
||||||
|
CFont::SetPropOn();
|
||||||
|
CFont::SetRightJustifyOn();
|
||||||
|
CFont::SetRightJustifyWrap(150.0f);
|
||||||
|
CFont::SetFontStyle(FONT_HEADING);
|
||||||
|
sprintf(str, "WELCOME TO");
|
||||||
|
AsciiToUnicode(str, wstr);
|
||||||
|
CFont::SetDropColor(CRGBA(0, 0, 0, 255));
|
||||||
|
CFont::SetDropShadowPosition(3);
|
||||||
|
CFont::SetColor(CRGBA(243, 237, 71, 255));
|
||||||
|
CFont::SetScale(SCREEN_STRETCH_X(1.2f), SCREEN_STRETCH_Y(1.2f));
|
||||||
|
CFont::PrintString(SCREENW - 20, SCREEN_STRETCH_FROM_BOTTOM(110.0f), TheText.Get("WELCOME"));
|
||||||
|
TextCopy(wstr, name);
|
||||||
|
TheText.UpperCase(wstr);
|
||||||
|
CFont::SetColor(CRGBA(243, 237, 71, 255));
|
||||||
|
CFont::SetScale(SCREEN_STRETCH_X(1.2f), SCREEN_STRETCH_Y(1.2f));
|
||||||
|
CFont::PrintString(SCREENW-20, SCREEN_STRETCH_FROM_BOTTOM(80.0f), wstr);
|
||||||
|
CFont::DrawFonts();
|
||||||
|
DoRWStuffEndOfFrame();
|
||||||
|
}
|
||||||
|
|
||||||
|
char*
|
||||||
|
GetLevelSplashScreen(int level)
|
||||||
|
{
|
||||||
|
static char *splashScreens[4] = {
|
||||||
|
nil,
|
||||||
|
"splash1",
|
||||||
|
"splash2",
|
||||||
|
"splash3",
|
||||||
|
};
|
||||||
|
|
||||||
|
return splashScreens[level];
|
||||||
|
}
|
||||||
|
|
||||||
char*
|
char*
|
||||||
GetRandomSplashScreen(void)
|
GetRandomSplashScreen(void)
|
||||||
{
|
{
|
||||||
|
@ -13,6 +13,9 @@ extern wchar *gUString;
|
|||||||
|
|
||||||
class CSprite2d;
|
class CSprite2d;
|
||||||
|
|
||||||
|
void InitialiseGame(void);
|
||||||
void LoadingScreen(const char *str1, const char *str2, const char *splashscreen);
|
void LoadingScreen(const char *str1, const char *str2, const char *splashscreen);
|
||||||
|
void LoadingIslandScreen(const char *levelName);
|
||||||
CSprite2d *LoadSplash(const char *name);
|
CSprite2d *LoadSplash(const char *name);
|
||||||
|
char *GetLevelSplashScreen(int level);
|
||||||
char *GetRandomSplashScreen(void);
|
char *GetRandomSplashScreen(void);
|
||||||
|
@ -22,6 +22,7 @@ public:
|
|||||||
return *((RwV3d*)this);
|
return *((RwV3d*)this);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
float Heading(void) const { return atan2(-x, y); }
|
||||||
float Magnitude(void) const { return sqrt(x*x + y*y + z*z); }
|
float Magnitude(void) const { return sqrt(x*x + y*y + z*z); }
|
||||||
float MagnitudeSqr(void) const { return x*x + y*y + z*z; }
|
float MagnitudeSqr(void) const { return x*x + y*y + z*z; }
|
||||||
float Magnitude2D(void) const { return sqrt(x*x + y*y); }
|
float Magnitude2D(void) const { return sqrt(x*x + y*y); }
|
||||||
|
@ -175,6 +175,23 @@ CModelInfo::IsBoatModel(int32 id)
|
|||||||
((CVehicleModelInfo*)GetModelInfo(id))->m_vehicleType == VEHICLE_TYPE_BOAT;
|
((CVehicleModelInfo*)GetModelInfo(id))->m_vehicleType == VEHICLE_TYPE_BOAT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
CModelInfo::RemoveColModelsFromOtherLevels(eLevelName level)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
CBaseModelInfo *mi;
|
||||||
|
CColModel *colmodel;
|
||||||
|
|
||||||
|
for(i = 0; i < MODELINFOSIZE; i++){
|
||||||
|
mi = GetModelInfo(i);
|
||||||
|
if(mi){
|
||||||
|
colmodel = mi->GetColModel();
|
||||||
|
if(colmodel && colmodel->level != LEVEL_NONE && colmodel->level != level)
|
||||||
|
colmodel->RemoveCollisionVolumes();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
STARTPATCHES
|
STARTPATCHES
|
||||||
InjectHook(0x50B310, CModelInfo::Initialise, PATCH_JUMP);
|
InjectHook(0x50B310, CModelInfo::Initialise, PATCH_JUMP);
|
||||||
InjectHook(0x50B5B0, CModelInfo::ShutDown, PATCH_JUMP);
|
InjectHook(0x50B5B0, CModelInfo::ShutDown, PATCH_JUMP);
|
||||||
@ -184,4 +201,5 @@ STARTPATCHES
|
|||||||
InjectHook(0x50BAD0, CModelInfo::AddPedModel, PATCH_JUMP);
|
InjectHook(0x50BAD0, CModelInfo::AddPedModel, PATCH_JUMP);
|
||||||
InjectHook(0x50BA60, CModelInfo::AddVehicleModel, PATCH_JUMP);
|
InjectHook(0x50BA60, CModelInfo::AddVehicleModel, PATCH_JUMP);
|
||||||
InjectHook(0x50B860, (CBaseModelInfo *(*)(const char*, int*))CModelInfo::GetModelInfo, PATCH_JUMP);
|
InjectHook(0x50B860, (CBaseModelInfo *(*)(const char*, int*))CModelInfo::GetModelInfo, PATCH_JUMP);
|
||||||
|
InjectHook(0x50BBC0, CModelInfo::RemoveColModelsFromOtherLevels, PATCH_JUMP);
|
||||||
ENDPATCHES
|
ENDPATCHES
|
||||||
|
@ -36,4 +36,5 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
static bool IsBoatModel(int32 id);
|
static bool IsBoatModel(int32 id);
|
||||||
|
static void RemoveColModelsFromOtherLevels(eLevelName level);
|
||||||
};
|
};
|
||||||
|
@ -1006,7 +1006,9 @@ CVehicleModelInfo::SetEnvironmentMapCB(RpMaterial *material, void *data)
|
|||||||
if(RpMaterialGetTexture(material) == 0)
|
if(RpMaterialGetTexture(material) == 0)
|
||||||
RpMaterialSetTexture(material, gpWhiteTexture);
|
RpMaterialSetTexture(material, gpWhiteTexture);
|
||||||
RpMatFXMaterialSetEffects(material, rpMATFXEFFECTENVMAP);
|
RpMatFXMaterialSetEffects(material, rpMATFXEFFECTENVMAP);
|
||||||
|
#ifndef PS2_MATFX
|
||||||
spec *= 0.5f; // Tone down a bit for PC
|
spec *= 0.5f; // Tone down a bit for PC
|
||||||
|
#endif
|
||||||
RpMatFXMaterialSetupEnvMap(material, (RwTexture*)data, pMatFxIdentityFrame, false, spec);
|
RpMatFXMaterialSetupEnvMap(material, (RwTexture*)data, pMatFxIdentityFrame, false, spec);
|
||||||
}
|
}
|
||||||
return material;
|
return material;
|
||||||
|
@ -344,6 +344,8 @@ patch()
|
|||||||
|
|
||||||
Patch<float>(0x46BC61+6, 1.0f); // car distance
|
Patch<float>(0x46BC61+6, 1.0f); // car distance
|
||||||
InjectHook(0x59E460, printf, PATCH_JUMP);
|
InjectHook(0x59E460, printf, PATCH_JUMP);
|
||||||
|
InjectHook(0x475E00, printf, PATCH_JUMP); // _Error
|
||||||
|
|
||||||
|
|
||||||
// stolen from silentpatch (sorry)
|
// stolen from silentpatch (sorry)
|
||||||
Patch<WORD>(0x5382BF, 0x0EEB);
|
Patch<WORD>(0x5382BF, 0x0EEB);
|
||||||
|
@ -114,18 +114,11 @@ DWORD _dwMemAvailVideo;
|
|||||||
DWORD &_dwOperatingSystemVersion = *(DWORD*)0x70F290;
|
DWORD &_dwOperatingSystemVersion = *(DWORD*)0x70F290;
|
||||||
|
|
||||||
RwUInt32 &gGameState = *(RwUInt32*)0x8F5838;
|
RwUInt32 &gGameState = *(RwUInt32*)0x8F5838;
|
||||||
WRAPPER bool InitialiseGame(void) { EAXJMP(0x48E7E0); }
|
|
||||||
|
|
||||||
WRAPPER const char *GetLevelSplashScreen(int32 number) { EAXJMP(0x48D750); }
|
|
||||||
//
|
|
||||||
|
|
||||||
void LoadingScreen(char const *msg1, char const *msg2, char const *screen);
|
|
||||||
CSprite2d *LoadSplash(const char *name);
|
|
||||||
|
|
||||||
enum eJoypadState
|
enum eJoypadState
|
||||||
{
|
{
|
||||||
JOYPAD_UNUSED,
|
JOYPAD_UNUSED,
|
||||||
JOYPAD_ATTACHED,
|
JOYPAD_ATTACHED,
|
||||||
};
|
};
|
||||||
|
|
||||||
struct tJoy
|
struct tJoy
|
||||||
|
Loading…
Reference in New Issue
Block a user