diff options
Diffstat (limited to '')
-rw-r--r-- | src/control/PedStats.cpp | 122 | ||||
-rw-r--r-- | src/control/PedStats.h | 75 | ||||
-rw-r--r-- | src/control/PedType.cpp | 2 |
3 files changed, 189 insertions, 10 deletions
diff --git a/src/control/PedStats.cpp b/src/control/PedStats.cpp index 3cb40d76..e669ab43 100644 --- a/src/control/PedStats.cpp +++ b/src/control/PedStats.cpp @@ -1,5 +1,125 @@ #include "common.h" #include "patcher.h" +#include "FileMgr.h" #include "PedStats.h" -WRAPPER int32 CPedStats::GetPedStatType(char *type) { EAXJMP(0x4EF780); } +CPedStat *(&CPedStats::ms_apPedStats)[NUM_PEDSTATS] = *(CPedStat *(*)[NUM_PEDSTATS]) *(uintptr*)0x9404D4; + +void +CPedStats::Initialise(void) +{ + int i; + + debug("Initialising CPedStats...\n"); + for(i = 0; i < NUM_PEDSTATS; i++){ + ms_apPedStats[i] = new CPedStat; + ms_apPedStats[i]->m_type = PEDSTAT_PLAYER; + ms_apPedStats[i]->m_name[8] = 'R'; // WHAT? + ms_apPedStats[i]->m_fleeDistance = 20.0f; + ms_apPedStats[i]->m_headingChangeRate = 15.0f; + ms_apPedStats[i]->m_fear = 50; + ms_apPedStats[i]->m_temper = 50; + ms_apPedStats[i]->m_lawfulness = 50; + ms_apPedStats[i]->m_sexiness = 50; + ms_apPedStats[i]->m_attackStrength = 1.0f; + ms_apPedStats[i]->m_defendWeakness = 1.0f; + ms_apPedStats[i]->m_flags = 0; + } + debug("Loading pedstats data...\n"); + CPedStats::LoadPedStats(); + debug("CPedStats ready\n"); +} + +void +CPedStats::Shutdown(void) +{ + int i; + debug("Shutting down CPedStats...\n"); + for(i = 0; i < NUM_PEDSTATS; i++) + delete ms_apPedStats[i]; + debug("CPedStats shut down\n"); +} + +void +CPedStats::LoadPedStats(void) +{ + char *buf; + char line[256]; + char name[32]; + int bp, buflen; + int lp, linelen; + int type; + float fleeDist, headingChangeRate, attackStrength, defendWeakness; + int fear, temper, lawfullness, sexiness, flags; + + + type = 0; + buf = new char[16 * 1024]; + + CFileMgr::SetDir("DATA"); + buflen = CFileMgr::LoadFile("PEDSTATS.DAT", (uint8*)buf, 16 * 1024, "r"); + CFileMgr::SetDir(""); + + for(bp = 0; bp < buflen; ){ + // read file line by line + for(linelen = 0; buf[bp] != '\n' && bp < buflen; bp++){ + if(buf[bp] == '\r' || buf[bp] == ',' || buf[bp] == '\t') + line[linelen++] = ' '; + else + line[linelen++] = buf[bp]; + line[linelen] = '\0'; + } + bp++; + + // skip white space + for(lp = 0; line[lp] <= ' '; lp++); + + if(lp >= linelen || // FIX: game uses == here, but this is safer if we have empty lines + line[lp] == '#') + continue; + + sscanf(&line[lp], "%s %f %f %d %d %d %d %f %f %d", + name, + &fleeDist, + &headingChangeRate, + &fear, + &temper, + &lawfullness, + &sexiness, + &attackStrength, + &defendWeakness, + &flags); + ms_apPedStats[type]->m_type = (ePedStats)type; + strncpy(ms_apPedStats[type]->m_name, name, 24); // FIX: game uses strcpy + ms_apPedStats[type]->m_fleeDistance = fleeDist; + ms_apPedStats[type]->m_headingChangeRate = headingChangeRate; + ms_apPedStats[type]->m_fear = fear; + ms_apPedStats[type]->m_temper = temper; + ms_apPedStats[type]->m_lawfulness = lawfullness; + ms_apPedStats[type]->m_sexiness = sexiness; + ms_apPedStats[type]->m_attackStrength = attackStrength; + ms_apPedStats[type]->m_defendWeakness = defendWeakness; + ms_apPedStats[type]->m_flags = flags; + type++; + } + + delete[] buf; +} + +int32 +CPedStats::GetPedStatType(char *name) +{ + int type; + + for(type = 0; type < NUM_PEDSTATS; type++) + if(strcmp(ms_apPedStats[type]->m_name, name) == 0) + return type; + return NUM_PEDSTATS; +} + +STARTPATCHES + InjectHook(0x4EF460, &CPedStats::Initialise, PATCH_JUMP); + InjectHook(0x4EF540, &CPedStats::Shutdown, PATCH_JUMP); + InjectHook(0x4EF580, &CPedStats::LoadPedStats, PATCH_JUMP); + InjectHook(0x4EF780, &CPedStats::GetPedStatType, PATCH_JUMP); +ENDPATCHES diff --git a/src/control/PedStats.h b/src/control/PedStats.h index 12ebdbc2..6b53ea37 100644 --- a/src/control/PedStats.h +++ b/src/control/PedStats.h @@ -1,23 +1,82 @@ #pragma once -struct PedStat +enum ePedStats { - uint32 m_id; + PEDSTAT_PLAYER, + PEDSTAT_COP, + PEDSTAT_MEDIC, + PEDSTAT_FIREMAN, + PEDSTAT_GANG1, + PEDSTAT_GANG2, + PEDSTAT_GANG3, + PEDSTAT_GANG4, + PEDSTAT_GANG5, + PEDSTAT_GANG6, + PEDSTAT_GANG7, + PEDSTAT_STREET_GUY, + PEDSTAT_SUIT_GUY, + PEDSTAT_SENSIBLE_GUY, + PEDSTAT_GEEK_GUY, + PEDSTAT_OLD_GUY, + PEDSTAT_TOUGH_GUY, + PEDSTAT_STREET_GIRL, + PEDSTAT_SUIT_GIRL, + PEDSTAT_SENSIBLE_GIRL, + PEDSTAT_GEEK_GIRL, + PEDSTAT_OLD_GIRL, + PEDSTAT_TOUGH_GIRL, + PEDSTAT_TRAMP_MALE, + PEDSTAT_TRAMP_FEMALE, + PEDSTAT_TOURIST, + PEDSTAT_PROSTITUTE, + PEDSTAT_CRIMINAL, + PEDSTAT_BUSKER, + PEDSTAT_TAXIDRIVER, + PEDSTAT_PSYCHO, + PEDSTAT_STEWARD, + PEDSTAT_SPORTSFAN, + PEDSTAT_SHOPPER, + PEDSTAT_OLDSHOPPER, + + NUM_PEDSTATS +}; + +// flags +enum +{ + STAT_PUNCH_ONLY = 1, + STAT_CAN_KNEE_HEAD = 2, + STAT_CAN_KICK = 4, + STAT_CAN_ROUNDHOUSE = 8, + STAT_NO_DIVE = 0x10, + STAT_ONE_HIT_KNOCKDOWN = 0x20, + STAT_SHOPPING_BAGS = 0x40, + STAT_GUN_PANIC = 0x80 +}; + +struct CPedStat +{ + ePedStats m_type; char m_name[24]; - int32 m_fleeDistance; - int32 m_headingChangeRate; + float m_fleeDistance; + float m_headingChangeRate; int8 m_fear; int8 m_temper; int8 m_lawfulness; int8 m_sexiness; - int32 m_attackStrength; - int32 m_defendWeakness; + float m_attackStrength; + float m_defendWeakness; int16 m_flags; }; -static_assert(sizeof(PedStat) == 0x34, "PedStat: error"); +static_assert(sizeof(CPedStat) == 0x34, "CPedStat: error"); class CPedStats { + static CPedStat *(&ms_apPedStats)[NUM_PEDSTATS]; + public: - static int32 GetPedStatType(char *type); + static void Initialise(void); + static void Shutdown(void); + static void LoadPedStats(void); + static int32 GetPedStatType(char *name); }; diff --git a/src/control/PedType.cpp b/src/control/PedType.cpp index ae046e3c..66eb49a1 100644 --- a/src/control/PedType.cpp +++ b/src/control/PedType.cpp @@ -3,7 +3,7 @@ #include "FileMgr.h" #include "PedType.h" -CPedType *(&CPedType::ms_apPedType)[NUM_PEDTYPES] = *(CPedType *(*)[NUM_PEDTYPES]) *(int*)0x941594; +CPedType *(&CPedType::ms_apPedType)[NUM_PEDTYPES] = *(CPedType *(*)[NUM_PEDTYPES]) *(uintptr*)0x941594; void CPedType::Initialise(void) |