mirror of
https://github.com/alicealys/t5-gsc-utils.git
synced 2025-04-19 12:32:53 +00:00
Add addClientCommand function
This commit is contained in:
parent
a155638e87
commit
33eed76e63
@ -9,14 +9,19 @@
|
|||||||
|
|
||||||
#include <utils/string.hpp>
|
#include <utils/string.hpp>
|
||||||
#include <utils/memory.hpp>
|
#include <utils/memory.hpp>
|
||||||
|
#include <utils/hook.hpp>
|
||||||
|
|
||||||
namespace command
|
namespace command
|
||||||
{
|
{
|
||||||
std::unordered_map<std::string, std::function<void(params&)>> handlers;
|
std::unordered_map<std::string, std::function<void(params&)>> handlers;
|
||||||
|
std::unordered_map<std::string, std::function<void(int, params_sv&)>> handlers_sv;
|
||||||
|
|
||||||
std::vector<std::string> script_commands;
|
std::vector<std::string> script_commands;
|
||||||
|
std::vector<std::string> script_sv_commands;
|
||||||
utils::memory::allocator allocator;
|
utils::memory::allocator allocator;
|
||||||
|
|
||||||
|
utils::hook::detour client_command_hook;
|
||||||
|
|
||||||
game::CmdArgs* get_cmd_args()
|
game::CmdArgs* get_cmd_args()
|
||||||
{
|
{
|
||||||
return reinterpret_cast<game::CmdArgs*>(game::Sys_GetValue(4));
|
return reinterpret_cast<game::CmdArgs*>(game::Sys_GetValue(4));
|
||||||
@ -34,6 +39,19 @@ namespace command
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void client_command_stub(const int client_num)
|
||||||
|
{
|
||||||
|
params_sv params = {};
|
||||||
|
|
||||||
|
const auto command = utils::string::to_lower(params[0]);
|
||||||
|
if (handlers_sv.find(command) != handlers_sv.end())
|
||||||
|
{
|
||||||
|
handlers_sv[command](client_num, params);
|
||||||
|
}
|
||||||
|
|
||||||
|
client_command_hook.invoke<void>(client_num);
|
||||||
|
}
|
||||||
|
|
||||||
params::params()
|
params::params()
|
||||||
: nesting_(get_cmd_args()->nesting)
|
: nesting_(get_cmd_args()->nesting)
|
||||||
{
|
{
|
||||||
@ -73,6 +91,43 @@ namespace command
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
params_sv::params_sv()
|
||||||
|
: nesting_(game::sv_cmd_args->nesting)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
int params_sv::size() const
|
||||||
|
{
|
||||||
|
return game::sv_cmd_args->argc[this->nesting_];
|
||||||
|
}
|
||||||
|
|
||||||
|
const char* params_sv::get(const int index) const
|
||||||
|
{
|
||||||
|
if (index >= this->size())
|
||||||
|
{
|
||||||
|
return "";
|
||||||
|
}
|
||||||
|
|
||||||
|
return game::sv_cmd_args->argv[this->nesting_][index];
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string params_sv::join(const int index) const
|
||||||
|
{
|
||||||
|
std::string result = {};
|
||||||
|
|
||||||
|
for (auto i = index; i < this->size(); i++)
|
||||||
|
{
|
||||||
|
if (i > index)
|
||||||
|
{
|
||||||
|
result.append(" ");
|
||||||
|
}
|
||||||
|
|
||||||
|
result.append(this->get(i));
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
void add_raw(const char* name, void (*callback)())
|
void add_raw(const char* name, void (*callback)())
|
||||||
{
|
{
|
||||||
game::Cmd_AddCommandInternal(name, callback, utils::memory::get_allocator()->allocate<game::cmd_function_t>());
|
game::Cmd_AddCommandInternal(name, callback, utils::memory::get_allocator()->allocate<game::cmd_function_t>());
|
||||||
@ -90,6 +145,15 @@ namespace command
|
|||||||
handlers[command] = callback;
|
handlers[command] = callback;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void add_sv(const std::string& name, std::function<void(int, const params_sv&)> callback)
|
||||||
|
{
|
||||||
|
const auto command = utils::string::to_lower(name);
|
||||||
|
if (handlers_sv.find(command) == handlers_sv.end())
|
||||||
|
{
|
||||||
|
handlers_sv[command] = std::move(callback);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void add_script_command(const std::string& name, const std::function<void(const params&)>& callback)
|
void add_script_command(const std::string& name, const std::function<void(const params&)>& callback)
|
||||||
{
|
{
|
||||||
script_commands.push_back(name);
|
script_commands.push_back(name);
|
||||||
@ -97,6 +161,12 @@ namespace command
|
|||||||
add(name_, callback);
|
add(name_, callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void add_script_sv_command(const std::string& name, const std::function<void(int, const params_sv&)>& callback)
|
||||||
|
{
|
||||||
|
script_sv_commands.push_back(name);
|
||||||
|
add_sv(name, callback);
|
||||||
|
}
|
||||||
|
|
||||||
void clear_script_commands()
|
void clear_script_commands()
|
||||||
{
|
{
|
||||||
for (const auto& name : script_commands)
|
for (const auto& name : script_commands)
|
||||||
@ -105,8 +175,14 @@ namespace command
|
|||||||
game::Cmd_RemoveCommand(name.data());
|
game::Cmd_RemoveCommand(name.data());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (const auto& name : script_sv_commands)
|
||||||
|
{
|
||||||
|
handlers_sv.erase(name);
|
||||||
|
}
|
||||||
|
|
||||||
allocator.clear();
|
allocator.clear();
|
||||||
script_commands.clear();
|
script_commands.clear();
|
||||||
|
script_sv_commands.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
void execute(std::string command, const bool sync)
|
void execute(std::string command, const bool sync)
|
||||||
@ -129,33 +205,13 @@ namespace command
|
|||||||
void post_unpack() override
|
void post_unpack() override
|
||||||
{
|
{
|
||||||
scripting::on_shutdown(clear_script_commands);
|
scripting::on_shutdown(clear_script_commands);
|
||||||
|
client_command_hook.create(SELECT_VALUE(0x4AF770, 0x63DB70), client_command_stub);
|
||||||
const auto execute_command = [](const std::string& command)
|
|
||||||
{
|
|
||||||
execute(command, false);
|
|
||||||
};
|
|
||||||
|
|
||||||
const auto add_command = [](const std::string& name, const scripting::function& function)
|
|
||||||
{
|
|
||||||
command::add_script_command(name, [function](const command::params& params)
|
|
||||||
{
|
|
||||||
scripting::array array;
|
|
||||||
|
|
||||||
for (auto i = 0; i < params.size(); i++)
|
|
||||||
{
|
|
||||||
array.push(params[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
function({array});
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
gsc::function::add_multiple([](const std::string& command)
|
gsc::function::add_multiple([](const std::string& command)
|
||||||
{
|
{
|
||||||
execute(command, false);
|
execute(command, false);
|
||||||
}, "executecommand", "command::execute");
|
}, "executecommand", "command::execute");
|
||||||
|
|
||||||
|
|
||||||
gsc::function::add_multiple([](const std::string& name, const scripting::function& function)
|
gsc::function::add_multiple([](const std::string& name, const scripting::function& function)
|
||||||
{
|
{
|
||||||
command::add_script_command(name, [function](const command::params& params)
|
command::add_script_command(name, [function](const command::params& params)
|
||||||
@ -170,6 +226,23 @@ namespace command
|
|||||||
function({array});
|
function({array});
|
||||||
});
|
});
|
||||||
}, "addcommand", "command::add");
|
}, "addcommand", "command::add");
|
||||||
|
|
||||||
|
gsc::function::add_multiple([](const std::string& name, const scripting::function& function)
|
||||||
|
{
|
||||||
|
command::add_script_sv_command(name, [function](const int client_num, const command::params_sv& params)
|
||||||
|
{
|
||||||
|
const scripting::entity player = game::Scr_GetEntityId(game::SCRIPTINSTANCE_SERVER, client_num, 0, 0);
|
||||||
|
|
||||||
|
scripting::array array;
|
||||||
|
|
||||||
|
for (auto i = 0; i < params.size(); i++)
|
||||||
|
{
|
||||||
|
array.push(params[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
function(player, {array});
|
||||||
|
});
|
||||||
|
}, "addclientcommand", "command::add_sv");
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -20,10 +20,30 @@ namespace command
|
|||||||
int nesting_;
|
int nesting_;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class params_sv
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
params_sv();
|
||||||
|
|
||||||
|
int size() const;
|
||||||
|
const char* get(int index) const;
|
||||||
|
std::string join(int index) const;
|
||||||
|
|
||||||
|
const char* operator[](const int index) const
|
||||||
|
{
|
||||||
|
return this->get(index);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
int nesting_;
|
||||||
|
};
|
||||||
|
|
||||||
void add_raw(const char* name, void (*callback)());
|
void add_raw(const char* name, void (*callback)());
|
||||||
void add(const char* name, std::function<void(params&)> callback);
|
void add(const char* name, std::function<void(params&)> callback);
|
||||||
|
void add_sv(const std::string& name, std::function<void(int, const params_sv&)> callback);
|
||||||
|
|
||||||
void add_script_command(const std::string& name, const std::function<void(const params&)>& callback);
|
void add_script_command(const std::string& name, const std::function<void(const params&)>& callback);
|
||||||
|
void add_script_sv_command(const std::string& name, const std::function<void(int, const params_sv&)>& callback);
|
||||||
void clear_script_commands();
|
void clear_script_commands();
|
||||||
|
|
||||||
void execute(std::string command, const bool sync = false);
|
void execute(std::string command, const bool sync = false);
|
||||||
|
@ -49,9 +49,9 @@ namespace scripting
|
|||||||
public:
|
public:
|
||||||
void post_unpack() override
|
void post_unpack() override
|
||||||
{
|
{
|
||||||
//g_shutdown_game_hook.create(SELECT(0x60DCF0, 0x688A40), g_shutdown_game_stub);
|
g_shutdown_game_hook.create(SELECT_VALUE(0x607700, 0x540950), g_shutdown_game_stub);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
//REGISTER_COMPONENT(scripting::component)
|
REGISTER_COMPONENT(scripting::component)
|
||||||
|
@ -128,4 +128,6 @@ namespace game
|
|||||||
WEAK symbol<unsigned int> levelEntityId{0x32C86A0, 0x3DCB2A0};
|
WEAK symbol<unsigned int> levelEntityId{0x32C86A0, 0x3DCB2A0};
|
||||||
|
|
||||||
WEAK symbol<client_s> svs_clients{0x0, 0x0};
|
WEAK symbol<client_s> svs_clients{0x0, 0x0};
|
||||||
|
|
||||||
|
WEAK symbol<CmdArgs> sv_cmd_args{0x243D208, 0x355BD88};
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user