mirror of
https://github.com/rwengine/openrw.git
synced 2024-11-22 18:32:44 +01:00
Merge pull request #232 from JayFoxRox/cheats
Cheat handler + Money display
This commit is contained in:
commit
243c3d7c4c
@ -69,17 +69,17 @@ struct BasicState
|
||||
BasicState ();
|
||||
};
|
||||
|
||||
/** Block 15 player info */
|
||||
/** Block 16 player info */
|
||||
struct PlayerInfo
|
||||
{
|
||||
uint16_t money;
|
||||
uint32_t money;
|
||||
uint8_t unknown1;
|
||||
uint16_t unknown2;
|
||||
uint8_t unknown3;
|
||||
uint32_t unknown2;
|
||||
uint16_t unknown3;
|
||||
float unknown4;
|
||||
uint16_t displayedMoney;
|
||||
uint16_t hiddenPackagesCollected;
|
||||
uint16_t hiddenPackageCount;
|
||||
uint32_t displayedMoney;
|
||||
uint32_t hiddenPackagesCollected;
|
||||
uint32_t hiddenPackageCount;
|
||||
uint8_t neverTired;
|
||||
uint8_t fastReload;
|
||||
uint8_t thaneOfLibertyCity;
|
||||
@ -92,26 +92,26 @@ struct PlayerInfo
|
||||
/** Block 17 */
|
||||
struct GameStats
|
||||
{
|
||||
uint16_t playerKills;
|
||||
uint16_t otherKills;
|
||||
uint16_t carsExploded;
|
||||
uint16_t shotsHit;
|
||||
uint16_t pedTypesKilled[23];
|
||||
uint16_t helicoptersDestroyed;
|
||||
uint16_t playerProgress;
|
||||
uint16_t explosiveKgsUsed;
|
||||
uint16_t bulletsFired;
|
||||
uint16_t bulletsHit;
|
||||
uint16_t carsCrushed;
|
||||
uint16_t headshots;
|
||||
uint16_t timesBusted;
|
||||
uint16_t timesHospital;
|
||||
uint16_t daysPassed;
|
||||
uint16_t mmRainfall;
|
||||
uint16_t insaneJumpMaxDistance;
|
||||
uint16_t insaneJumpMaxHeight;
|
||||
uint16_t insaneJumpMaxFlips;
|
||||
uint16_t insangeJumpMaxRotation;
|
||||
uint32_t playerKills;
|
||||
uint32_t otherKills;
|
||||
uint32_t carsExploded;
|
||||
uint32_t shotsHit;
|
||||
uint32_t pedTypesKilled[23];
|
||||
uint32_t helicoptersDestroyed;
|
||||
uint32_t playerProgress;
|
||||
uint32_t explosiveKgsUsed;
|
||||
uint32_t bulletsFired;
|
||||
uint32_t bulletsHit;
|
||||
uint32_t carsCrushed;
|
||||
uint32_t headshots;
|
||||
uint32_t timesBusted;
|
||||
uint32_t timesHospital;
|
||||
uint32_t daysPassed;
|
||||
uint32_t mmRainfall;
|
||||
uint32_t insaneJumpMaxDistance;
|
||||
uint32_t insaneJumpMaxHeight;
|
||||
uint32_t insaneJumpMaxFlips;
|
||||
uint32_t insangeJumpMaxRotation;
|
||||
/*
|
||||
* 0 none completed
|
||||
* 1 insane stunt
|
||||
@ -123,36 +123,36 @@ struct GameStats
|
||||
* 7 quadruple
|
||||
* 8 perfect quadruple
|
||||
*/
|
||||
uint16_t bestStunt;
|
||||
uint16_t uniqueStuntsFound;
|
||||
uint16_t uniqueStuntsTotal;
|
||||
uint16_t missionAttempts;
|
||||
uint16_t missionsPassed;
|
||||
uint16_t passengersDroppedOff;
|
||||
uint16_t taxiRevenue;
|
||||
uint16_t portlandPassed;
|
||||
uint16_t stauntonPassed;
|
||||
uint16_t shoresidePassed;
|
||||
uint16_t bestTurismoTime;
|
||||
uint32_t bestStunt;
|
||||
uint32_t uniqueStuntsFound;
|
||||
uint32_t uniqueStuntsTotal;
|
||||
uint32_t missionAttempts;
|
||||
uint32_t missionsPassed;
|
||||
uint32_t passengersDroppedOff;
|
||||
uint32_t taxiRevenue;
|
||||
uint32_t portlandPassed;
|
||||
uint32_t stauntonPassed;
|
||||
uint32_t shoresidePassed;
|
||||
uint32_t bestTurismoTime;
|
||||
float distanceWalked;
|
||||
float distanceDriven;
|
||||
uint16_t patriotPlaygroundTime;
|
||||
uint16_t aRideInTheParkTime;
|
||||
uint16_t grippedTime;
|
||||
uint16_t multistoryMayhemTime;
|
||||
uint16_t peopleSaved;
|
||||
uint16_t criminalsKilled;
|
||||
uint16_t highestParamedicLevel;
|
||||
uint16_t firesExtinguished;
|
||||
uint16_t longestDodoFlight;
|
||||
uint16_t bombDefusalTime;
|
||||
uint16_t rampagesPassed;
|
||||
uint16_t totalRampages;
|
||||
uint16_t totalMissions;
|
||||
uint16_t fastestTime[16]; // not used
|
||||
uint16_t highestScore[16];
|
||||
uint16_t peopleKilledSinceCheckpoint; // ?
|
||||
uint16_t peopleKilledSinceLastBustedOrWasted;
|
||||
uint32_t patriotPlaygroundTime;
|
||||
uint32_t aRideInTheParkTime;
|
||||
uint32_t grippedTime;
|
||||
uint32_t multistoryMayhemTime;
|
||||
uint32_t peopleSaved;
|
||||
uint32_t criminalsKilled;
|
||||
uint32_t highestParamedicLevel;
|
||||
uint32_t firesExtinguished;
|
||||
uint32_t longestDodoFlight;
|
||||
uint32_t bombDefusalTime;
|
||||
uint32_t rampagesPassed;
|
||||
uint32_t totalRampages;
|
||||
uint32_t totalMissions;
|
||||
uint32_t fastestTime[16]; // not used
|
||||
uint32_t highestScore[16];
|
||||
uint32_t peopleKilledSinceCheckpoint; // ?
|
||||
uint32_t peopleKilledSinceLastBustedOrWasted;
|
||||
char lastMissionGXT[8];
|
||||
|
||||
GameStats ();
|
||||
|
@ -86,7 +86,12 @@ void drawPlayerInfo(PlayerController* player, GameWorld* world, GameRenderer* re
|
||||
|
||||
infoTextY += ui_textHeight;
|
||||
|
||||
ti.text = GameSymbols::Money + GameStringUtil::fromString(std::to_string(world->state->playerInfo.money));
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << std::setw(8) << std::setfill('0') << world->state->playerInfo.displayedMoney;
|
||||
|
||||
ti.text = GameSymbols::Money + GameStringUtil::fromString(ss.str());
|
||||
}
|
||||
ti.baseColour = ui_shadowColour;
|
||||
ti.screenPosition = glm::vec2(infoTextX + 1.f, infoTextY+1.f);
|
||||
render->text.renderText(ti);
|
||||
|
@ -24,6 +24,7 @@
|
||||
#include <objects/VehicleObject.hpp>
|
||||
|
||||
#include <boost/algorithm/string/predicate.hpp>
|
||||
#include <functional>
|
||||
|
||||
#include "GitSHA1.h"
|
||||
|
||||
@ -271,6 +272,176 @@ PlayerController *RWGame::getPlayer()
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Modifiers for GTA3 we try to recreate
|
||||
#define RW_GAME_VERSION 1100
|
||||
#define RW_GAME_GTA3_GERMAN 0
|
||||
#define RW_GAME_GTA3_ANNIVERSARY 0
|
||||
|
||||
void RWGame::handleCheatInput(char symbol) {
|
||||
cheatInputWindow = cheatInputWindow.substr(1) + symbol;
|
||||
|
||||
// Helper to check for cheats
|
||||
auto checkForCheat = [this](std::string cheat, std::function<void()> action) {
|
||||
RW_CHECK(cheatInputWindow.length() >= cheat.length(), "Cheat too long");
|
||||
size_t offset = cheatInputWindow.length() - cheat.length();
|
||||
if (cheat == cheatInputWindow.substr(offset)) {
|
||||
log.info("Game", "Cheat triggered: '" + cheat + "'");
|
||||
if (action) {
|
||||
action();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// Player related cheats
|
||||
{
|
||||
auto player = static_cast<CharacterObject*>(world->pedestrianPool.find(state->playerObject));
|
||||
|
||||
#ifdef RW_GAME_GTA3_GERMAN // Germans got their own cheat
|
||||
std::string health_cheat = "GESUNDHEIT";
|
||||
#else
|
||||
std::string health_cheat = "HEALTH";
|
||||
#endif
|
||||
checkForCheat(health_cheat, [&]{
|
||||
player->getCurrentState().health = 100.f;
|
||||
// @todo ShowHelpMessage("CHEAT3"); // III / VC: Inputting health cheat.
|
||||
});
|
||||
|
||||
#if RW_GAME_VERSION >= 1100 // Changed cheat name in version 1.1
|
||||
std::string armor_cheat = "TORTOISE";
|
||||
#else
|
||||
std::string armor_cheat = "TURTOISE";
|
||||
#endif
|
||||
checkForCheat(armor_cheat, [&]{
|
||||
player->getCurrentState().armour = 100.f;
|
||||
// @todo ShowHelpMessage("CHEAT4"); // III / VC: Inputting armor cheat.
|
||||
});
|
||||
|
||||
checkForCheat("GUNSGUNSGUNS", [&]{
|
||||
// @todo give player weapons
|
||||
// @todo ShowHelpMessage("CHEAT2"); // III / VC: Inputting weapon cheats.
|
||||
});
|
||||
|
||||
checkForCheat("IFIWEREARICHMAN", [&]{
|
||||
world->state->playerInfo.money += 250000;
|
||||
// @todo ShowHelpMessage("CHEAT6"); // III: Inputting money cheat.
|
||||
});
|
||||
|
||||
checkForCheat("MOREPOLICEPLEASE", [&]{
|
||||
// @todo raise to next wanted level
|
||||
// @todo ShowHelpMessage("CHEAT5"); // III / VC: Inputting wanted level cheats.
|
||||
});
|
||||
|
||||
checkForCheat("NOPOLICEPLEASE", [&]{
|
||||
// @todo lower to next lower wanted level
|
||||
// @todo ShowHelpMessage("CHEAT5"); // III / VC: Inputting wanted level cheats.
|
||||
});
|
||||
}
|
||||
|
||||
// Misc cheats.
|
||||
{
|
||||
checkForCheat("BANGBANGBANG", [&]{
|
||||
// @todo Explode nearby vehicles
|
||||
// @todo What radius?
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("GIVEUSATANK", [&]{
|
||||
// The iPod / Android version of the game (10th year anniversary) spawns random (?) vehicles instead of always rhino
|
||||
#ifdef RW_GAME_GTA3_ANNIVERSARY
|
||||
uint16_t vehicleModel = 110; // @todo Which cars are spawned?!
|
||||
#else
|
||||
uint16_t vehicleModel = 122;
|
||||
#endif
|
||||
// @todo Spawn rhino
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("CORNERSLIKEMAD", [&]{
|
||||
// @todo Weird car handling
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("ANICESETOFWHEELS", [&]{
|
||||
// @todo Hide car bodies
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("CHITTYCHITTYBB", [&]{
|
||||
// @todo Cars can fly
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("NASTYLIMBCHEAT", [&]{
|
||||
// @todo Makes it possible to shoot limbs off, iirc?
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("ILIKEDRESSINGUP", [&]{
|
||||
// @todo Which skins will be chosen?
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
}
|
||||
|
||||
// Pedestrian cheats
|
||||
{
|
||||
checkForCheat("WEAPONSFORALL", [&]{
|
||||
// @todo Give all pedestrians weapons.. this is also saved in the savegame?!
|
||||
// @todo Which weapons do they get?
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("NOBODYLIKESME", [&]{
|
||||
// @todo Set all pedestrians hostile towards player.. this is also saved in the savegame?!
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("ITSALLGOINGMAAAD", [&]{
|
||||
// @todo Set all pedestrians to fighting each other.. this is also saved in the savegame?!
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
// Game speed cheats
|
||||
|
||||
checkForCheat("TIMEFLIESWHENYOU", [&]{
|
||||
// @todo Set fast gamespeed
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
|
||||
checkForCheat("BOOOOORING", [&]{
|
||||
// @todo Set slow gamespeed
|
||||
// @todo ShowHelpMessage("CHEAT1"); // III / VC: Inputting most cheats.
|
||||
});
|
||||
}
|
||||
|
||||
// Weather cheats
|
||||
{
|
||||
checkForCheat("ILIKESCOTLAND", [&]{
|
||||
// @todo Set weather to cloudy
|
||||
// @todo ShowHelpMessage("CHEAT7"); // III / VC: Inputting weather cheats.
|
||||
});
|
||||
|
||||
checkForCheat("SKINCANCERFORME", [&]{
|
||||
// @todo Set sunny / normal weather
|
||||
// @todo ShowHelpMessage("CHEAT7"); // III / VC: Inputting weather cheats.
|
||||
});
|
||||
|
||||
checkForCheat("MADWEATHER", [&]{
|
||||
// @todo Set bad weather
|
||||
// @todo ShowHelpMessage("CHEAT7"); // III / VC: Inputting weather cheats.
|
||||
});
|
||||
|
||||
checkForCheat("ILOVESCOTLAND", [&]{
|
||||
// @todo Set weather to rainy
|
||||
// @todo ShowHelpMessage("CHEAT7"); // III / VC: Inputting weather cheats.
|
||||
});
|
||||
|
||||
checkForCheat("PEASOUP", [&]{
|
||||
// @todo Set weather to foggy
|
||||
// @todo ShowHelpMessage("CHEAT7"); // III / VC: Inputting weather cheats.
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
int RWGame::run()
|
||||
{
|
||||
last_clock_time = clock.now();
|
||||
@ -797,4 +968,10 @@ void RWGame::globalKeyEvent(const SDL_Event& event)
|
||||
break;
|
||||
default: break;
|
||||
}
|
||||
|
||||
std::string keyName = SDL_GetKeyName(event.key.keysym.sym);
|
||||
if (keyName.length() == 1) {
|
||||
char symbol = keyName[0];
|
||||
handleCheatInput(symbol);
|
||||
}
|
||||
}
|
||||
|
@ -39,6 +39,8 @@ class RWGame
|
||||
bool showDebugPhysics = false;
|
||||
int lastDraws; /// Number of draws issued for the last frame.
|
||||
|
||||
std::string cheatInputWindow = std::string(32, ' ');
|
||||
|
||||
float accum = 0.f;
|
||||
float timescale = 1.f;
|
||||
public:
|
||||
@ -136,6 +138,8 @@ private:
|
||||
void renderDebugPaths(float time);
|
||||
void renderProfile();
|
||||
|
||||
void handleCheatInput(char symbol);
|
||||
|
||||
void globalKeyEvent(const SDL_Event& event);
|
||||
};
|
||||
|
||||
|
@ -174,10 +174,39 @@ void IngameState::exit()
|
||||
|
||||
void IngameState::tick(float dt)
|
||||
{
|
||||
auto world = getWorld();
|
||||
autolookTimer = std::max(autolookTimer - dt, 0.f);
|
||||
|
||||
// Update displayed money value
|
||||
// @todo the game uses another algorithm which is non-linear
|
||||
{
|
||||
float moneyFrequency = 1.0f / 30.0f;
|
||||
moneyTimer += dt;
|
||||
while (moneyTimer >= moneyFrequency) {
|
||||
int32_t difference = world->state->playerInfo.money - world->state->playerInfo.displayedMoney;
|
||||
|
||||
// Generates 0, 1 (difference < 100), 12 (difference < 1000), 123 (difference < 10000), .. etc.
|
||||
// Negative input will result in negative output
|
||||
auto GetIncrement = [](int32_t difference) -> int32_t {
|
||||
// @todo is this correct for difference >= 1000000000 ?
|
||||
int32_t r = 1;
|
||||
int32_t i = 2;
|
||||
if (difference == 0) { return 0; }
|
||||
while (std::abs(difference) >= 100) {
|
||||
difference /= 10;
|
||||
r = r * 10 + i;
|
||||
i++;
|
||||
}
|
||||
return (difference < 0) ? -r : r;
|
||||
};
|
||||
world->state->playerInfo.displayedMoney += GetIncrement(difference);
|
||||
|
||||
moneyTimer -= moneyFrequency;
|
||||
}
|
||||
}
|
||||
|
||||
auto player = game->getPlayer();
|
||||
const auto& input = getWorld()->state->input;
|
||||
const auto& input = world->state->input;
|
||||
if( player && player->isInputEnabled() )
|
||||
{
|
||||
float viewDistance = 4.f;
|
||||
@ -199,7 +228,7 @@ void IngameState::tick(float dt)
|
||||
viewDistance = 4.f;
|
||||
}
|
||||
|
||||
auto target = getWorld()->pedestrianPool.find(getWorld()->state->cameraTarget);
|
||||
auto target = world->pedestrianPool.find(world->state->cameraTarget);
|
||||
|
||||
if( target == nullptr )
|
||||
{
|
||||
@ -374,7 +403,7 @@ void IngameState::tick(float dt)
|
||||
auto from = btVector3(rayStart.x, rayStart.y, rayStart.z);
|
||||
ClosestNotMeRayResultCallback ray(physTarget, from, to);
|
||||
|
||||
getWorld()->dynamicsWorld->rayTest(from, to, ray);
|
||||
world->dynamicsWorld->rayTest(from, to, ray);
|
||||
if( ray.hasHit() && ray.m_closestHitFraction < 1.f )
|
||||
{
|
||||
cameraPosition = glm::vec3(ray.m_hitPointWorld.x(), ray.m_hitPointWorld.y(),
|
||||
|
@ -32,6 +32,8 @@ class IngameState : public State
|
||||
bool m_invertedY;
|
||||
/// Free look in vehicles.
|
||||
bool m_vehicleFreeLook;
|
||||
|
||||
float moneyTimer; // Timer used to updated displayed money value
|
||||
public:
|
||||
/**
|
||||
* @brief IngameState
|
||||
|
Loading…
Reference in New Issue
Block a user