From 0dc5ad61374dfd9c817967ca94afe5eca7b523fe Mon Sep 17 00:00:00 2001 From: Quentin Date: Wed, 10 Apr 2024 11:43:55 +0200 Subject: [PATCH] fix(lua): better error reporting when calling player commands (#2932) --- docs/lua/tables/command.md | 12 +++++++++++- docs/lua/tables/network.md | 15 ++++++++++++++- src/backend/player_command.cpp | 5 +++-- src/backend/player_command.hpp | 8 ++++++++ src/lua/bindings/command.cpp | 30 ++++++++++++++++++++++++++---- 5 files changed, 62 insertions(+), 8 deletions(-) diff --git a/docs/lua/tables/command.md b/docs/lua/tables/command.md index 45995829..5aeeced3 100644 --- a/docs/lua/tables/command.md +++ b/docs/lua/tables/command.md @@ -2,7 +2,7 @@ Table for calling menu commands. -## Functions (2) +## Functions (3) ### `call(command_name, _args)` @@ -31,4 +31,14 @@ Call a menu command on a given player. command.call_player(player_idx, command_name, _args) ``` +### `get_all_player_command_names()` + +- **Returns:** + - `table`: Table that contains the names of all the player commands. + +**Example Usage:** +```lua +table = command.get_all_player_command_names() +``` + diff --git a/docs/lua/tables/network.md b/docs/lua/tables/network.md index 3364ff0d..ff2703fc 100644 --- a/docs/lua/tables/network.md +++ b/docs/lua/tables/network.md @@ -2,7 +2,7 @@ Table containing helper functions for network related features. -## Functions (12) +## Functions (13) ### `trigger_script_event(bitset, _args)` @@ -157,4 +157,17 @@ Sends a message to the in game chat. network.send_chat_message(msg, team_only) ``` +### `send_chat_message_to_player(player_idx, msg)` + +Sends a chat message to the specified player. Other players would not be able to see the message + +- **Parameters:** + - `player_idx` (integer): Index of the player. + - `msg` (string): Message to be sent. + +**Example Usage:** +```lua +network.send_chat_message_to_player(player_idx, msg) +``` + diff --git a/src/backend/player_command.cpp b/src/backend/player_command.cpp index 7d7054d9..a124d963 100644 --- a/src/backend/player_command.cpp +++ b/src/backend/player_command.cpp @@ -29,6 +29,8 @@ namespace big { if (make_all_version) m_all_component = std::make_unique(this, name, label, description, num_args); + + g_player_commands[rage::joaat(name)] = this; } void player_command::execute(const command_arguments& args, const std::shared_ptr ctx) @@ -111,12 +113,11 @@ namespace big void player_command::call(player_ptr player, const command_arguments& args, const std::shared_ptr ctx) { - // TODO: Code duplication if (m_num_args.has_value() && args.size() != (m_num_args.value() - 1)) { ctx->report_error(std::format("Command {} called with the wrong number of arguments. Expected {}, got {}", m_name, - m_num_args.value(), + m_num_args.value() - 1, args.size())); return; } diff --git a/src/backend/player_command.hpp b/src/backend/player_command.hpp index ce3b2749..81e5a24a 100644 --- a/src/backend/player_command.hpp +++ b/src/backend/player_command.hpp @@ -18,6 +18,8 @@ namespace big player_all_component(player_command* parent, const std::string& name, const std::string& label, const std::string& description, std::optional num_args); }; + inline std::unordered_map g_player_commands; + class player_command : public command { friend player_all_component; @@ -33,7 +35,13 @@ namespace big }; public: + static player_command* get(rage::joaat_t command) + { + return g_player_commands[command]; + } + void call(player_ptr player, const command_arguments& args, const std::shared_ptr ctx = std::make_shared()); player_command(const std::string& name, const std::string& label, const std::string& description, std::optional num_args, bool make_all_version = true); }; + } \ No newline at end of file diff --git a/src/lua/bindings/command.cpp b/src/lua/bindings/command.cpp index 0b611ff0..e1e12adc 100644 --- a/src/lua/bindings/command.cpp +++ b/src/lua/bindings/command.cpp @@ -1,5 +1,6 @@ #pragma once #include "command.hpp" + #include "backend/command.hpp" #include "backend/player_command.hpp" #include "network.hpp" // for convert_sequence @@ -37,7 +38,7 @@ namespace lua::command { const auto args = convert_sequence(_args.value_or(sol::table())); - const auto command = (big::player_command*)big::command::get(rage::joaat(command_name)); + const auto command = big::player_command::get(rage::joaat(command_name)); if (command) { @@ -48,12 +49,33 @@ namespace lua::command command->call(player, args); } } + else + { + LOG(FATAL) << "No player command called " << command_name; + } + } + + // Lua API: Function + // Table: command + // Name: get_all_player_command_names + // Returns: table: Table that contains the names of all the player commands. + static std::vector get_all_player_command_names() + { + std::vector res; + + for (const auto& cmd : big::g_player_commands | std::ranges::views::values) + { + res.push_back(cmd->get_name()); + } + + return res; } void bind(sol::state& state) { - auto ns = state["command"].get_or_create(); - ns["call"] = call; - ns["call_player"] = call_player; + auto ns = state["command"].get_or_create(); + ns["call"] = call; + ns["call_player"] = call_player; + ns["get_all_player_command_names"] = get_all_player_command_names; } } \ No newline at end of file