summaryrefslogtreecommitdiff
path: root/src/peds/Population.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/peds/Population.cpp')
-rw-r--r--src/peds/Population.cpp212
1 files changed, 79 insertions, 133 deletions
diff --git a/src/peds/Population.cpp b/src/peds/Population.cpp
index 1566ba3d..2dc0bbab 100644
--- a/src/peds/Population.cpp
+++ b/src/peds/Population.cpp
@@ -31,6 +31,10 @@
// Transition areas between zones
const RegenerationPoint aSafeZones[] = {
+// TODO(MIAMI): this is totally bogus
+ { LEVEL_BEACH, LEVEL_MAINLAND, 400.0f, 814.0f, -954.0f, -903.0f, 30.0f, 100.0f,
+ CVector(790.0f, -917.0f, 39.0f), CVector(775.0f, -921.0f, 39.0f), CVector(424.0f, -942.0f, 38.0f), CVector(439.0f, -938.0f, 38.0f) },
+#ifndef MIAMI
{ LEVEL_INDUSTRIAL, LEVEL_COMMERCIAL, 400.0f, 814.0f, -954.0f, -903.0f, 30.0f, 100.0f,
CVector(790.0f, -917.0f, 39.0f), CVector(775.0f, -921.0f, 39.0f), CVector(424.0f, -942.0f, 38.0f), CVector(439.0f, -938.0f, 38.0f) },
{ LEVEL_INDUSTRIAL, LEVEL_COMMERCIAL, 555.0f, 711.0f, 118.0f, 186.0f, -30.0f, -10.0f,
@@ -47,6 +51,7 @@ const RegenerationPoint aSafeZones[] = {
CVector(-321.0f, -1043.0f, -13.2f), CVector(-328.0f, -1045.0f, -13.2f), CVector(-398.0f, -1044.0f, -13.5f), CVector(-390.0f, -1040.5f, -13.5f) },
{ LEVEL_COMMERCIAL, LEVEL_SUBURBAN, -425.0f, -280.0f, -471.0f, -447.0f, -20.0f, -5.0f,
CVector(-292.0f, -457.0f, -11.6f), CVector(-310.0f, -461.0f, -11.6f), CVector(-413.0f, -461.0f, -11.5f), CVector(-399.0f, -457.0f, -11.3f) }
+#endif
};
PedGroup CPopulation::ms_pPedGroups[NUMPEDGROUPS];
@@ -78,6 +83,9 @@ CVector CPopulation::RegenerationPoint_a;
CVector CPopulation::RegenerationPoint_b;
CVector CPopulation::RegenerationForward;
+uint32 CPopulation::ms_nTotalCarPassengerPeds;
+uint32 CPopulation::NumMiamiViceCops;
+
void
CPopulation::Initialise()
{
@@ -98,6 +106,8 @@ CPopulation::Initialise()
ms_nNumGang9 = 0;
ms_nNumDummy = 0;
+ ms_nTotalCarPassengerPeds = 0;
+
m_AllRandomPedsThisType = -1;
PedDensityMultiplier = 1.0f;
bZoneChangeHasHappened = false;
@@ -109,7 +119,6 @@ CPopulation::Initialise()
ms_nTotalCivPeds = 0;
LoadPedGroups();
- DealWithZoneChange(LEVEL_COMMERCIAL, LEVEL_INDUSTRIAL, true);
debug("CPopulation ready\n");
}
@@ -335,49 +344,10 @@ CPopulation::ChooseGangOccupation(int gangId)
return firstGangModel;
}
+//--MIAMI: done
void
CPopulation::DealWithZoneChange(eLevelName oldLevel, eLevelName newLevel, bool forceIndustrialZone)
{
- bZoneChangeHasHappened = true;
-
- CVector findSafeZoneAround;
- int safeZone;
-
- if (forceIndustrialZone) {
- // Commercial to industrial transition area on Callahan Bridge
- findSafeZoneAround.x = 690.0f;
- findSafeZoneAround.y = -920.0f;
- findSafeZoneAround.z = 42.0f;
- } else {
- findSafeZoneAround = FindPlayerCoors();
- }
- eLevelName level;
- FindCollisionZoneForCoors(&findSafeZoneAround, &safeZone, &level);
-
- // We aren't in a "safe zone", find closest one
- if (safeZone < 0)
- FindClosestZoneForCoors(&findSafeZoneAround, &safeZone, oldLevel, newLevel);
-
- // No, there should be one!
- if (safeZone < 0) {
- if (newLevel == LEVEL_INDUSTRIAL) {
- safeZone = 0;
- } else if (newLevel == LEVEL_SUBURBAN) {
- safeZone = 4;
- }
- }
-
- if (aSafeZones[safeZone].srcLevel == newLevel) {
- CPopulation::RegenerationPoint_a = aSafeZones[safeZone].srcPosA;
- CPopulation::RegenerationPoint_b = aSafeZones[safeZone].srcPosB;
- CPopulation::RegenerationForward = aSafeZones[safeZone].destPosA - aSafeZones[safeZone].srcPosA;
- RegenerationForward.Normalise();
- } else if (aSafeZones[safeZone].destLevel == newLevel) {
- CPopulation::RegenerationPoint_a = aSafeZones[safeZone].destPosA;
- CPopulation::RegenerationPoint_b = aSafeZones[safeZone].destPosB;
- CPopulation::RegenerationForward = aSafeZones[safeZone].srcPosA - aSafeZones[safeZone].destPosA;
- RegenerationForward.Normalise();
- }
}
void
@@ -433,6 +403,7 @@ CPopulation::Update()
+ ms_nNumGang2 + ms_nNumGang1;
ms_nTotalPeds = ms_nNumDummy + ms_nNumEmergency + ms_nNumCop
+ ms_nTotalGangPeds + ms_nNumCivFemale + ms_nNumCivMale;
+ ms_nTotalPeds -= ms_nTotalCarPassengerPeds;
if (!CCutsceneMgr::IsRunning()) {
float pcdm = PedCreationDistMultiplier();
AddToPopulation(pcdm * (MIN_CREATION_DIST * TheCamera.GenerationDistMultiplier),
@@ -454,6 +425,7 @@ CPopulation::GeneratePedsAtStartOfGame()
+ ms_nNumGang3 + ms_nNumGang2 + ms_nNumGang1;
ms_nTotalPeds = ms_nNumDummy + ms_nNumEmergency + ms_nNumCop
+ ms_nTotalGangPeds + ms_nNumCivFemale + ms_nNumCivMale;
+ ms_nTotalPeds -= ms_nTotalCarPassengerPeds;
// Min dist is 10.0f only for start of the game (naturally)
AddToPopulation(10.0f, PedCreationDistMultiplier() * (MIN_CREATION_DIST + CREATION_RANGE),
@@ -488,7 +460,7 @@ CPopulation::PedCreationDistMultiplier()
}
CPed*
-CPopulation::AddPed(ePedType pedType, uint32 miOrCopType, CVector const &coors)
+CPopulation::AddPed(ePedType pedType, uint32 miOrCopType, CVector const &coors, int32 modifier)
{
switch (pedType) {
case PEDTYPE_CIVMALE:
@@ -508,7 +480,7 @@ CPopulation::AddPed(ePedType pedType, uint32 miOrCopType, CVector const &coors)
}
case PEDTYPE_COP:
{
- CCopPed *ped = new CCopPed((eCopType)miOrCopType);
+ CCopPed *ped = new CCopPed((eCopType)miOrCopType, modifier);
ped->SetPosition(coors);
ped->SetOrientation(0.0f, 0.0f, 0.0f);
CWorld::Add(ped);
@@ -599,14 +571,12 @@ CPopulation::AddToPopulation(float minDist, float maxDist, float minDistOffScree
if (ms_nTotalPeds < maxPossiblePedsForArea || addCop) {
int decisionThreshold = CGeneral::GetRandomNumberInRange(0, 1000);
- if (decisionThreshold < zoneInfo.copDensity || addCop) {
+ if (decisionThreshold < zoneInfo.copPedThreshold || addCop) {
pedTypeToAdd = PEDTYPE_COP;
modelToAdd = ChoosePolicePedOccupation();
} else {
- int16 density = zoneInfo.copDensity;
for (int i = 0; i < NUM_GANGS; i++) {
- density += zoneInfo.gangDensity[i];
- if (decisionThreshold < density) {
+ if (decisionThreshold < zoneInfo.gangPedThreshold[i]) {
pedTypeToAdd = PEDTYPE_GANG1 + i;
break;
}
@@ -693,7 +663,7 @@ CPopulation::AddToPopulation(float minDist, float maxDist, float minDistOffScree
generatedCoors.y = yOffset + gangLeader->GetPosition().y;
}
}
- if (!CPedPlacement::IsPositionClearForPed(&generatedCoors))
+ if (!CPedPlacement::IsPositionClearForPed(generatedCoors))
break;
// Why no love for last gang member?!
@@ -743,9 +713,10 @@ CPopulation::AddToPopulation(float minDist, float maxDist, float minDistOffScree
}
CPed*
-CPopulation::AddPedInCar(CVehicle* car)
+CPopulation::AddPedInCar(CVehicle* car, bool isPassenger)
{
int defaultModel = MI_MALE01;
+ int miamiViceIndex = 0;
bool imSureThatModelIsLoaded = true;
CVector coors = FindPlayerCoors();
CZoneInfo zoneInfo;
@@ -769,6 +740,7 @@ CPopulation::AddPedInCar(CVehicle* car)
pedType = PEDTYPE_COP;
break;
case MI_POLICE:
+ case MI_PREDATOR:
preferredModel = COP_STREET;
pedType = PEDTYPE_COP;
break;
@@ -781,9 +753,15 @@ CPopulation::AddPedInCar(CVehicle* car)
preferredModel = COP_ARMY;
pedType = PEDTYPE_COP;
break;
+ case MI_VICECHEE: // TODO(MIAMI): figure out new structure of the function
+ preferredModel = COP_MIAMIVICE;
+ pedType = PEDTYPE_COP;
+ miamiViceIndex = (isPassenger ? 2 * CCarCtrl::MiamiViceCycle : 2 * CCarCtrl::MiamiViceCycle + 1);
+ break;
case MI_TAXI:
case MI_CABBIE:
- case MI_BORGNINE:
+ case MI_ZEBRA:
+ case MI_KAUFMAN:
if (CGeneral::GetRandomTrueFalse()) {
pedType = PEDTYPE_CIVMALE;
preferredModel = MI_TAXI_D;
@@ -826,7 +804,7 @@ CPopulation::AddPedInCar(CVehicle* car)
pedType = ((CPedModelInfo*)CModelInfo::GetModelInfo(defaultModel))->m_pedType;
}
- CPed *newPed = CPopulation::AddPed((ePedType)pedType, preferredModel, car->GetPosition());
+ CPed *newPed = CPopulation::AddPed((ePedType)pedType, preferredModel, car->GetPosition(), miamiViceIndex);
newPed->bUsesCollision = false;
// what??
@@ -858,88 +836,6 @@ CPopulation::AddPedInCar(CVehicle* car)
void
CPopulation::MoveCarsAndPedsOutOfAbandonedZones()
{
- eLevelName level;
- int zone;
- int frame = CTimer::GetFrameCounter() & 7;
- if (frame == 1) {
- int movedVehicleCount = 0;
- int poolSize = CPools::GetVehiclePool()->GetSize();
- for (int poolIndex = poolSize - 1; poolIndex >= 0; poolIndex--) {
-
- CVehicle* veh = CPools::GetVehiclePool()->GetSlot(poolIndex);
- if (veh && veh->m_nZoneLevel == LEVEL_NONE && veh->IsCar()) {
-
- if(veh->GetStatus() != STATUS_ABANDONED && veh->GetStatus() != STATUS_WRECKED && veh->GetStatus() != STATUS_PLAYER &&
- veh->GetStatus() != STATUS_PLAYER_REMOTE) {
-
- CVector vehPos(veh->GetPosition());
- CPopulation::FindCollisionZoneForCoors(&vehPos, &zone, &level);
-
- // Level 0 is transition zones, and we don't wanna touch cars on transition zones.
- if (level != LEVEL_NONE && level != CCollision::ms_collisionInMemory && vehPos.z > -4.0f) {
- if (veh->bIsLocked || !veh->CanBeDeleted()) {
- switch (movedVehicleCount & 3) {
- case 0:
- veh->SetPosition(RegenerationPoint_a);
- break;
- case 1:
- veh->SetPosition(RegenerationPoint_b);
- break;
- case 2:
- veh->SetPosition(RegenerationPoint_a.x, RegenerationPoint_b.y, RegenerationPoint_a.z);
- break;
- case 3:
- veh->SetPosition(RegenerationPoint_b.x, RegenerationPoint_a.y, RegenerationPoint_a.z);
- break;
- default:
- break;
- }
- veh->GetMatrix().GetPosition().z += (movedVehicleCount / 4) * 7.0f;
- veh->GetMatrix().GetForward() = RegenerationForward;
- ((CAutomobile*)veh)->PlaceOnRoadProperly();
- CCarCtrl::JoinCarWithRoadSystem(veh);
- CTheScripts::ClearSpaceForMissionEntity(veh->GetPosition(), veh);
- ++movedVehicleCount;
- } else {
- CWorld::Remove(veh);
- delete veh;
- }
- }
- }
- }
- }
- } else if (frame == 5) {
- int poolSize = CPools::GetPedPool()->GetSize();
- for (int poolIndex = poolSize - 1; poolIndex >= 0; poolIndex--) {
-
- CPed *ped = CPools::GetPedPool()->GetSlot(poolIndex);
- if (ped && ped->m_nZoneLevel == LEVEL_NONE && !ped->bInVehicle) {
-
- CVector pedPos(ped->GetPosition());
- CPopulation::FindCollisionZoneForCoors(&pedPos, &zone, &level);
-
- // Level 0 is transition zones, and we don't wanna touch peds on transition zones.
- if (level != LEVEL_NONE && level != CCollision::ms_collisionInMemory && pedPos.z > -4.0f) {
- if (ped->CanBeDeleted()) {
- CWorld::Remove(ped);
- delete ped;
- } else if (ped->m_nPedType != PEDTYPE_PLAYER1 && ped->m_nPedType != PEDTYPE_PLAYER2) {
- ped->SetPosition(RegenerationPoint_a);
-
- bool foundGround;
- float groundZ = CWorld::FindGroundZFor3DCoord(ped->GetPosition().x, ped->GetPosition().y,
- ped->GetPosition().z + 2.0f, &foundGround);
-
- if (foundGround) {
- ped->GetMatrix().GetPosition().z = 1.0f + groundZ;
- //ped->GetPosition().z += 0.0f;
- CTheScripts::ClearSpaceForMissionEntity(ped->GetPosition(), ped);
- }
- }
- }
- }
- }
- }
}
void
@@ -1133,6 +1029,10 @@ CPopulation::ManagePopulation(void)
}
float dist = (ped->GetPosition() - playerPos).Magnitude2D();
+
+ if (ped->IsGangMember() || (ped->bDeadPedInFrontOfCar && ped->m_vehicleInAccident))
+ dist -= 30.0f;
+
bool pedIsFarAway = false;
if (PedCreationDistMultiplier() * (PED_REMOVE_DIST_SPECIAL * TheCamera.GenerationDistMultiplier) < dist
|| (!ped->bCullExtraFarAway && PedCreationDistMultiplier() * PED_REMOVE_DIST * TheCamera.GenerationDistMultiplier < dist)
@@ -1179,3 +1079,49 @@ CPopulation::ManagePopulation(void)
}
}
}
+
+CPed*
+CPopulation::AddDeadPedInFrontOfCar(const CVector& pos, CVehicle* pCulprit)
+{
+ if (TheCamera.IsSphereVisible(pos, 2.0f)) {
+ float fDistanceToPlayer = (pos - FindPlayerPed()->GetPosition()).Magnitude2D();
+ float fDistanceMultiplier;
+ if (FindPlayerVehicle())
+ fDistanceMultiplier = clamp(FindPlayerVehicle()->GetMoveSpeed().Magnitude2D() - 0.1f + 1.0f, 1.0f, 1.5f);
+ else
+ fDistanceMultiplier = 1.0f;
+ if (40.0f * fDistanceMultiplier > fDistanceToPlayer)
+ return nil;
+ }
+ bool found;
+ float z = CWorld::FindGroundZFor3DCoord(pos.x, pos.y, pos.z, &found) + 1.0f;
+ if (!found)
+ return nil;
+ z = Max(z, pos.z);
+ if (!CModelInfo::GetModelInfo(MI_MALE01)->GetRwObject()) // strange way to check it
+ return nil;
+ CPed* pPed = CPopulation::AddPed(PEDTYPE_CIVMALE, MI_MALE01, pos); // TODO(MIAMI): 4th parameter
+ pPed->SetDie(ANIM_KO_SHOT_FRONT1, 4.0f, 0.0f);
+ //TODO(MIAMI): set money == 0
+ pPed->bDeadPedInFrontOfCar = true;
+ pPed->m_vehicleInAccident = pCulprit;
+ pCulprit->RegisterReference((CEntity**)&pPed->m_vehicleInAccident);
+ CEntity* pEntities[3] = { 0 };
+ if (!CPedPlacement::IsPositionClearForPed(pos, 2.0f, 3, pEntities)) {
+ for (int i = 0; i < 3; i++) {
+ if (pEntities[i] && pEntities[i] != pCulprit && pEntities[i] != pPed) {
+ CWorld::Remove(pPed);
+ delete pPed;
+ return nil;
+ }
+ }
+ }
+ CColPoint colpts[32];
+ if (CCollision::ProcessColModels(pCulprit->GetMatrix(), *pCulprit->GetColModel(), pPed->GetMatrix(), *pPed->GetColModel(), colpts, nil, nil)) {
+ CWorld::Remove(pPed);
+ delete pPed;
+ return nil;
+ }
+ CVisibilityPlugins::SetClumpAlpha(pPed->GetClump(), 0);
+ return pPed;
+}