mirror of
https://github.com/XLabsProject/s1x-client.git
synced 2023-08-02 15:02:12 +02:00
Bunch of new stuff
This commit is contained in:
parent
c6bbca328a
commit
7d559d5a31
@ -13,15 +13,11 @@ namespace bots
|
|||||||
{
|
{
|
||||||
bool can_spawn()
|
bool can_spawn()
|
||||||
{
|
{
|
||||||
// disable spawning for now, causes a crash if more than svs_numclients.
|
if (party::get_client_count() < *game::mp::svs_numclients)
|
||||||
|
{
|
||||||
//const auto index = *game::mp::svs_numclients - 1;
|
return true;
|
||||||
//const auto cant = game::mp::svs_clients[index].header.state;
|
}
|
||||||
//if (cant)
|
return false;
|
||||||
//{
|
|
||||||
return false;
|
|
||||||
//}
|
|
||||||
//return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void add_bot()
|
void add_bot()
|
||||||
|
@ -295,12 +295,92 @@ namespace command
|
|||||||
|
|
||||||
static void add_commands_sp()
|
static void add_commands_sp()
|
||||||
{
|
{
|
||||||
|
add("give", [](const params& params)
|
||||||
|
{
|
||||||
|
if (!game::SV_Loaded())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (params.size() < 2)
|
||||||
|
{
|
||||||
|
game::CG_GameMessage(0, "You did not specify a weapon name");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto ps = game::SV_GetPlayerstateForClientNum(0);
|
||||||
|
auto wp = game::G_GetWeaponForName(params.get(1));
|
||||||
|
if (game::G_GivePlayerWeapon(ps, wp, 0, 0, 0, 0, 0, 0))
|
||||||
|
{
|
||||||
|
game::G_InitializeAmmo(ps, wp, 0);
|
||||||
|
game::G_SelectWeapon(0, wp);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
add("take", [](const params& params)
|
||||||
|
{
|
||||||
|
if (!game::SV_Loaded())
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (params.size() < 2)
|
||||||
|
{
|
||||||
|
game::CG_GameMessage(0, "You did not specify a weapon name");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto ps = game::SV_GetPlayerstateForClientNum(0);
|
||||||
|
auto wp = game::G_GetWeaponForName(params.get(1));
|
||||||
|
game::G_TakePlayerWeapon(ps, wp);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
static void add_commands_mp()
|
static void add_commands_mp()
|
||||||
{
|
{
|
||||||
client_command_hook.create(0x1402E98F0, &client_command);
|
client_command_hook.create(0x1402E98F0, &client_command);
|
||||||
|
|
||||||
|
add_sv("give", [](const int client_num, const params_sv& params)
|
||||||
|
{
|
||||||
|
if (!game::Dvar_FindVar("sv_cheats")->current.enabled)
|
||||||
|
{
|
||||||
|
game::SV_GameSendServerCommand(client_num, 1, "f \"Cheats are not enabled on this server\"");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (params.size() < 2)
|
||||||
|
{
|
||||||
|
game::SV_GameSendServerCommand(client_num, 1, "f \"You did not specify a weapon name\"");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto ps = game::SV_GetPlayerstateForClientNum(client_num);
|
||||||
|
auto wp = game::G_GetWeaponForName(params.get(1));
|
||||||
|
if (game::G_GivePlayerWeapon(ps, wp, 0, 0, 0, 0, 0, 0))
|
||||||
|
{
|
||||||
|
game::G_InitializeAmmo(ps, wp, 0);
|
||||||
|
game::G_SelectWeapon(client_num, wp);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
add_sv("take", [](const int client_num, const params_sv& params)
|
||||||
|
{
|
||||||
|
if (!game::Dvar_FindVar("sv_cheats")->current.enabled)
|
||||||
|
{
|
||||||
|
game::SV_GameSendServerCommand(client_num, 1, "f \"Cheats are not enabled on this server\"");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (params.size() < 2)
|
||||||
|
{
|
||||||
|
game::SV_GameSendServerCommand(client_num, 1, "f \"You did not specify a weapon name\"");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto ps = game::SV_GetPlayerstateForClientNum(client_num);
|
||||||
|
auto wp = game::G_GetWeaponForName(params.get(1));
|
||||||
|
game::G_TakePlayerWeapon(ps, wp);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
52
src/client/component/filesystem.cpp
Normal file
52
src/client/component/filesystem.cpp
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
#include <std_include.hpp>
|
||||||
|
#include "loader/component_loader.hpp"
|
||||||
|
#include "filesystem.hpp"
|
||||||
|
|
||||||
|
#include "game/game.hpp"
|
||||||
|
#include "dvars.hpp"
|
||||||
|
|
||||||
|
#include <utils/hook.hpp>
|
||||||
|
|
||||||
|
namespace filesystem
|
||||||
|
{
|
||||||
|
file::file(std::string name)
|
||||||
|
: name_(std::move(name))
|
||||||
|
{
|
||||||
|
char* buffer{};
|
||||||
|
const auto size = game::FS_ReadFile(this->name_.data(), &buffer);
|
||||||
|
|
||||||
|
if (size >= 0 && buffer)
|
||||||
|
{
|
||||||
|
this->valid_ = true;
|
||||||
|
this->buffer_.append(buffer, size);
|
||||||
|
game::FS_FreeFile(buffer);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool file::exists() const
|
||||||
|
{
|
||||||
|
return this->valid_;
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string& file::get_buffer() const
|
||||||
|
{
|
||||||
|
return this->buffer_;
|
||||||
|
}
|
||||||
|
|
||||||
|
const std::string& file::get_name() const
|
||||||
|
{
|
||||||
|
return this->name_;
|
||||||
|
}
|
||||||
|
|
||||||
|
class component final : public component_interface
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
void post_unpack() override
|
||||||
|
{
|
||||||
|
// Set fs_basegame
|
||||||
|
dvars::override::Dvar_RegisterString("fs_basegame", "s1-mod", 2048);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
REGISTER_COMPONENT(filesystem::component)
|
19
src/client/component/filesystem.hpp
Normal file
19
src/client/component/filesystem.hpp
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
namespace filesystem
|
||||||
|
{
|
||||||
|
class file
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
file(std::string name);
|
||||||
|
|
||||||
|
bool exists() const;
|
||||||
|
const std::string& get_buffer() const;
|
||||||
|
const std::string& get_name() const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
bool valid_ = false;
|
||||||
|
std::string name_;
|
||||||
|
std::string buffer_;
|
||||||
|
};
|
||||||
|
}
|
@ -2,6 +2,7 @@
|
|||||||
#include "loader/component_loader.hpp"
|
#include "loader/component_loader.hpp"
|
||||||
#include "party.hpp"
|
#include "party.hpp"
|
||||||
|
|
||||||
|
#include "dvars.hpp"
|
||||||
#include "command.hpp"
|
#include "command.hpp"
|
||||||
#include "network.hpp"
|
#include "network.hpp"
|
||||||
#include "scheduler.hpp"
|
#include "scheduler.hpp"
|
||||||
@ -70,6 +71,40 @@ namespace party
|
|||||||
|
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int get_dvar_int(const std::string& dvar)
|
||||||
|
{
|
||||||
|
auto* dvar_value = game::Dvar_FindVar(dvar.data());
|
||||||
|
if (dvar_value && dvar_value->current.integer)
|
||||||
|
{
|
||||||
|
return dvar_value->current.integer;
|
||||||
|
}
|
||||||
|
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool get_dvar_bool(const std::string& dvar)
|
||||||
|
{
|
||||||
|
auto* dvar_value = game::Dvar_FindVar(dvar.data());
|
||||||
|
if (dvar_value && dvar_value->current.enabled)
|
||||||
|
{
|
||||||
|
return dvar_value->current.enabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void didyouknow_stub(const char* dvar_name, const char* string)
|
||||||
|
{
|
||||||
|
if (!party::sv_motd.empty())
|
||||||
|
{
|
||||||
|
string = party::sv_motd.data();
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function either does Dvar_SetString or Dvar_RegisterString for the given dvar
|
||||||
|
reinterpret_cast<void(*)(const char*, const char*)>(0x1404C39B0)(dvar_name, string);
|
||||||
|
party::sv_motd.clear();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int get_client_count()
|
int get_client_count()
|
||||||
@ -77,10 +112,10 @@ namespace party
|
|||||||
auto count = 0;
|
auto count = 0;
|
||||||
for (auto i = 0; i < *game::mp::svs_numclients; ++i)
|
for (auto i = 0; i < *game::mp::svs_numclients; ++i)
|
||||||
{
|
{
|
||||||
//if (game::mp::svs_clients[i].header.state >= 3)
|
if (game::mp::svs_clients[i].header.state >= 3)
|
||||||
//{
|
{
|
||||||
// ++count;
|
++count;
|
||||||
//}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return count;
|
return count;
|
||||||
@ -91,11 +126,11 @@ namespace party
|
|||||||
auto count = 0;
|
auto count = 0;
|
||||||
for (auto i = 0; i < *game::mp::svs_numclients; ++i)
|
for (auto i = 0; i < *game::mp::svs_numclients; ++i)
|
||||||
{
|
{
|
||||||
//if (game::mp::svs_clients[i].header.state >= 3 &&
|
if (game::mp::svs_clients[i].header.state >= 3 &&
|
||||||
// game::mp::svs_clients[i].testClient != game::TC_NONE)
|
game::SV_BotIsBot(i))
|
||||||
//{
|
{
|
||||||
// ++count;
|
++count;
|
||||||
//}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return count;
|
return count;
|
||||||
@ -146,10 +181,9 @@ namespace party
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// starting map doesn't work, only private match -> start
|
// starting map like this crashes the game.
|
||||||
printf("Starting map: %s\n", mapname.data());
|
printf("Starting map: %s\n", mapname.data());
|
||||||
game::SV_StartMapForParty(0, mapname.data(), true);
|
game::SV_StartMapForParty(0, mapname.data(), true);
|
||||||
//game::SV_StartMap(0, mapname.data());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -310,6 +344,8 @@ namespace party
|
|||||||
printf("%s\n", message.data());
|
printf("%s\n", message.data());
|
||||||
});
|
});
|
||||||
|
|
||||||
|
utils::hook::call(0x14048811C, didyouknow_stub); // allow custom didyouknow based on sv_motd
|
||||||
|
|
||||||
network::on("getInfo", [](const game::netadr_s& target, const std::string_view& data)
|
network::on("getInfo", [](const game::netadr_s& target, const std::string_view& data)
|
||||||
{
|
{
|
||||||
utils::info_string info{};
|
utils::info_string info{};
|
||||||
@ -326,8 +362,6 @@ namespace party
|
|||||||
info.set("sv_maxclients", utils::string::va("%i", *game::mp::svs_numclients));
|
info.set("sv_maxclients", utils::string::va("%i", *game::mp::svs_numclients));
|
||||||
info.set("protocol", utils::string::va("%i", PROTOCOL));
|
info.set("protocol", utils::string::va("%i", PROTOCOL));
|
||||||
info.set("playmode", utils::string::va("%i", game::Com_GetCurrentCoDPlayMode()));
|
info.set("playmode", utils::string::va("%i", game::Com_GetCurrentCoDPlayMode()));
|
||||||
//info.set("shortversion", SHORTVERSION);
|
|
||||||
//info.set("hc", (Dvar::Var("g_hardcore").get<bool>() ? "1" : "0"));
|
|
||||||
|
|
||||||
network::send(target, "infoResponse", info.build(), '\n');
|
network::send(target, "infoResponse", info.build(), '\n');
|
||||||
});
|
});
|
||||||
@ -350,8 +384,17 @@ namespace party
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const auto gamename = info.get("gamename");
|
||||||
|
if (gamename != "S1"s)
|
||||||
|
{
|
||||||
|
const auto str = "Invalid gamename.";
|
||||||
|
printf("%s\n", str);
|
||||||
|
game::Com_Error(game::ERR_DROP, str);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const auto playmode = info.get("playmode");
|
const auto playmode = info.get("playmode");
|
||||||
if (playmode.empty())
|
if (game::CodPlayMode(std::atoi(playmode.data())) != game::Com_GetCurrentCoDPlayMode())
|
||||||
{
|
{
|
||||||
const auto str = "Invalid playmode.";
|
const auto str = "Invalid playmode.";
|
||||||
printf("%s\n", str);
|
printf("%s\n", str);
|
||||||
@ -377,15 +420,6 @@ namespace party
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto gamename = info.get("gamename");
|
|
||||||
if (gamename != "S1"s)
|
|
||||||
{
|
|
||||||
const auto str = "Invalid gamename.";
|
|
||||||
printf("%s\n", str);
|
|
||||||
game::Com_Error(game::ERR_DROP, str);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
party::sv_motd = info.get("sv_motd");
|
party::sv_motd = info.get("sv_motd");
|
||||||
|
|
||||||
connect_to_party(target, mapname, gametype);
|
connect_to_party(target, mapname, gametype);
|
||||||
|
@ -5,8 +5,9 @@
|
|||||||
#include "game/game.hpp"
|
#include "game/game.hpp"
|
||||||
#include "game/dvars.hpp"
|
#include "game/dvars.hpp"
|
||||||
#include "scheduler.hpp"
|
#include "scheduler.hpp"
|
||||||
#include "dvars.hpp"
|
#include "filesystem.hpp"
|
||||||
#include "fastfiles.hpp"
|
#include "fastfiles.hpp"
|
||||||
|
#include "dvars.hpp"
|
||||||
|
|
||||||
#include <utils/string.hpp>
|
#include <utils/string.hpp>
|
||||||
#include <utils/hook.hpp>
|
#include <utils/hook.hpp>
|
||||||
@ -41,7 +42,7 @@ namespace patches
|
|||||||
if (game::environment::is_mp())
|
if (game::environment::is_mp())
|
||||||
{
|
{
|
||||||
// Make name save
|
// Make name save
|
||||||
game::Dvar_RegisterString("name", "Unknown Soldier", 0x1, "Player name.");
|
game::Dvar_RegisterString("name", "Unknown Soldier", game::DVAR_FLAG_SAVED, "Player name.");
|
||||||
|
|
||||||
// Disable data validation error popup
|
// Disable data validation error popup
|
||||||
game::Dvar_RegisterInt("data_validation_allow_drop", 0, 0, 0, 0, "");
|
game::Dvar_RegisterInt("data_validation_allow_drop", 0, 0, 0, 0, "");
|
||||||
@ -54,14 +55,14 @@ namespace patches
|
|||||||
const unsigned int /*flags*/,
|
const unsigned int /*flags*/,
|
||||||
const char* description)
|
const char* description)
|
||||||
{
|
{
|
||||||
return game::Dvar_RegisterInt(name, 0, 0, 1000, 0x1, description);
|
return game::Dvar_RegisterInt(name, 0, 0, 1000, game::DVAR_FLAG_SAVED, description);
|
||||||
}
|
}
|
||||||
|
|
||||||
game::dvar_t* register_cg_fov_stub(const char* name, float value, float min, float /*max*/,
|
game::dvar_t* register_cg_fov_stub(const char* name, float value, float min, float /*max*/,
|
||||||
const unsigned int flags,
|
const unsigned int flags,
|
||||||
const char* description)
|
const char* description)
|
||||||
{
|
{
|
||||||
return game::Dvar_RegisterFloat(name, value, min, 160, flags | 0x1, description);
|
return game::Dvar_RegisterFloat(name, value, min, 160, game::DVAR_FLAG_SAVED, description);
|
||||||
}
|
}
|
||||||
|
|
||||||
game::dvar_t* register_fovscale_stub(const char* name, float /*value*/, float /*min*/, float /*max*/,
|
game::dvar_t* register_fovscale_stub(const char* name, float /*value*/, float /*min*/, float /*max*/,
|
||||||
@ -69,7 +70,7 @@ namespace patches
|
|||||||
const char* desc)
|
const char* desc)
|
||||||
{
|
{
|
||||||
// changed max value from 2.0f -> 5.0f and min value from 0.5f -> 0.1f
|
// changed max value from 2.0f -> 5.0f and min value from 0.5f -> 0.1f
|
||||||
return game::Dvar_RegisterFloat(name, 1.0f, 0.1f, 5.0f, 0x1, desc);
|
return game::Dvar_RegisterFloat(name, 1.0f, 0.1f, 5.0f, game::DVAR_FLAG_SAVED, desc);
|
||||||
}
|
}
|
||||||
|
|
||||||
int dvar_command_patch() // game makes this return an int and compares with eax instead of al -_-
|
int dvar_command_patch() // game makes this return an int and compares with eax instead of al -_-
|
||||||
@ -104,6 +105,34 @@ namespace patches
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char* db_read_raw_file_stub(const char* filename, char* buf, int size)
|
||||||
|
{
|
||||||
|
std::string file_name = filename;
|
||||||
|
if (file_name.find(".cfg") == std::string::npos)
|
||||||
|
{
|
||||||
|
file_name.append(".cfg");
|
||||||
|
}
|
||||||
|
|
||||||
|
const auto file = filesystem::file(file_name);
|
||||||
|
if (file.exists())
|
||||||
|
{
|
||||||
|
snprintf(buf, size, "%s\n", file.get_buffer().data());
|
||||||
|
printf("%s\n", buf);
|
||||||
|
return buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
// DB_ReadRawFile
|
||||||
|
return reinterpret_cast<const char*(*)(const char*, char*, int)>(SELECT_VALUE(0x140180E30, 0x140273080))(filename, buf, size);
|
||||||
|
}
|
||||||
|
|
||||||
|
void aim_assist_add_to_target_list(void* a1, void* a2)
|
||||||
|
{
|
||||||
|
if (!dvars::aimassist_enabled->current.enabled)
|
||||||
|
return;
|
||||||
|
|
||||||
|
game::AimAssist_AddToTargetList(a1, a2);
|
||||||
|
}
|
||||||
|
|
||||||
void missing_content_error_stub(int /*mode*/, const char* /*message*/)
|
void missing_content_error_stub(int /*mode*/, const char* /*message*/)
|
||||||
{
|
{
|
||||||
game::Com_Error(game::ERR_DROP, utils::string::va("MISSING FILE\n%s.ff", fastfiles::get_current_fastfile()));
|
game::Com_Error(game::ERR_DROP, utils::string::va("MISSING FILE\n%s.ff", fastfiles::get_current_fastfile()));
|
||||||
@ -152,6 +181,9 @@ namespace patches
|
|||||||
// Show missing fastfiles
|
// Show missing fastfiles
|
||||||
utils::hook::call(SELECT_VALUE(0x1401817AF, 0x1402742A8), missing_content_error_stub);
|
utils::hook::call(SELECT_VALUE(0x1401817AF, 0x1402742A8), missing_content_error_stub);
|
||||||
|
|
||||||
|
// Allow executing custom cfg files with the "exec" command
|
||||||
|
utils::hook::call(SELECT_VALUE(0x1402EE225, 0x1403AF7CD), db_read_raw_file_stub);
|
||||||
|
|
||||||
// Fix mouse lag
|
// Fix mouse lag
|
||||||
utils::hook::nop(SELECT_VALUE(0x14038FAFF, 0x1404DB1AF), 6);
|
utils::hook::nop(SELECT_VALUE(0x14038FAFF, 0x1404DB1AF), 6);
|
||||||
scheduler::loop([]()
|
scheduler::loop([]()
|
||||||
@ -179,6 +211,12 @@ namespace patches
|
|||||||
|
|
||||||
// patch "Couldn't find the bsp for this map." error to not be fatal in mp
|
// patch "Couldn't find the bsp for this map." error to not be fatal in mp
|
||||||
utils::hook::call(0x14026E63B, bsp_sys_error_stub);
|
utils::hook::call(0x14026E63B, bsp_sys_error_stub);
|
||||||
|
|
||||||
|
//client side aim assist dvar
|
||||||
|
dvars::aimassist_enabled = game::Dvar_RegisterBool("aimassist_enabled", true,
|
||||||
|
game::DvarFlags::DVAR_FLAG_SAVED,
|
||||||
|
"Enables aim assist for controllers");
|
||||||
|
utils::hook::call(0x140003609, aim_assist_add_to_target_list);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void patch_sp()
|
static void patch_sp()
|
||||||
|
@ -5,6 +5,8 @@
|
|||||||
|
|
||||||
namespace dvars
|
namespace dvars
|
||||||
{
|
{
|
||||||
|
game::dvar_t* aimassist_enabled = nullptr;
|
||||||
|
|
||||||
game::dvar_t* con_inputBoxColor = nullptr;
|
game::dvar_t* con_inputBoxColor = nullptr;
|
||||||
game::dvar_t* con_inputHintBoxColor = nullptr;
|
game::dvar_t* con_inputHintBoxColor = nullptr;
|
||||||
game::dvar_t* con_outputBarColor = nullptr;
|
game::dvar_t* con_outputBarColor = nullptr;
|
||||||
|
@ -5,6 +5,8 @@
|
|||||||
|
|
||||||
namespace dvars
|
namespace dvars
|
||||||
{
|
{
|
||||||
|
extern game::dvar_t* aimassist_enabled;
|
||||||
|
|
||||||
extern game::dvar_t* con_inputBoxColor;
|
extern game::dvar_t* con_inputBoxColor;
|
||||||
extern game::dvar_t* con_inputHintBoxColor;
|
extern game::dvar_t* con_inputHintBoxColor;
|
||||||
extern game::dvar_t* con_outputBarColor;
|
extern game::dvar_t* con_outputBarColor;
|
||||||
|
Loading…
Reference in New Issue
Block a user